Sentry Integration (補強 SignOz): - Add @sentry/nextjs for frontend error tracking + session replay - Add sentry-sdk[fastapi] for backend error tracking - Create sentry.client/server/edge.config.ts - Integrate with next.config.js + instrumentation.ts - Add Sentry exception capture in FastAPI error handler - Create deployment scripts for Self-Hosted @ 192.168.0.110 CI/CD Fixes: - Fix F821 Undefined name 'Field' in incidents.py - Add NEXT_PUBLIC_API_URL env var to CI build step - Add build-arg to Docker build verification E2E Test Improvements: - Fix strict mode violations in dashboard-acceptance tests - Add timeout increase for Phase 4 demo tests - Make tests more resilient to UI variations Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
69 lines
2.0 KiB
TypeScript
69 lines
2.0 KiB
TypeScript
/**
|
|
* Visual Armor Upgrade - Phase 2.5 視覺裝甲升級驗收
|
|
* ================================================
|
|
* 截圖驗證 Magic UI 特效與 shadcn/ui 風格升級
|
|
*/
|
|
|
|
import { test, expect } from '@playwright/test'
|
|
|
|
test.describe('Visual Armor Upgrade', () => {
|
|
test.beforeEach(async ({ page }) => {
|
|
// Navigate to demo page
|
|
await page.goto('/zh-TW/demo')
|
|
// Wait for SSE connection
|
|
await page.waitForTimeout(3000)
|
|
})
|
|
|
|
test('capture full dashboard with Magic UI effects', async ({ page }) => {
|
|
// Full page screenshot
|
|
await page.screenshot({
|
|
path: 'test-results/visual-armor-dashboard.png',
|
|
fullPage: true,
|
|
})
|
|
|
|
// Verify LiveDashboard is rendered
|
|
const dashboard = page.locator('h2:has-text("即時戰情室")')
|
|
await expect(dashboard).toBeVisible()
|
|
})
|
|
|
|
test('capture HITL approval cards with Border Beam', async ({ page }) => {
|
|
// Create a CRITICAL approval for Border Beam effect
|
|
const criticalBtn = page.locator('button:has-text("CRITICAL")')
|
|
if (await criticalBtn.isVisible()) {
|
|
await criticalBtn.click()
|
|
await page.waitForTimeout(2000)
|
|
}
|
|
|
|
// Wait for cards to render
|
|
await page.waitForTimeout(1000)
|
|
|
|
// Screenshot the approval section
|
|
const approvalSection = page.locator('section:has(h2:has-text("HITL"))')
|
|
if (await approvalSection.isVisible()) {
|
|
await approvalSection.screenshot({
|
|
path: 'test-results/visual-armor-approvals.png',
|
|
})
|
|
}
|
|
|
|
// Full page with effects
|
|
await page.screenshot({
|
|
path: 'test-results/visual-armor-full.png',
|
|
fullPage: true,
|
|
})
|
|
})
|
|
|
|
test('verify OpenClaw panel with Brain icon', async ({ page }) => {
|
|
// 2026-03-24: ClawBot → OpenClaw 更名
|
|
const openclawPanel = page.locator('h3:has-text("OpenClaw")')
|
|
await expect(openclawPanel).toBeVisible()
|
|
|
|
// Screenshot OpenClaw panel
|
|
const panel = page.locator('.glass-copilot').first()
|
|
if (await panel.isVisible()) {
|
|
await panel.screenshot({
|
|
path: 'test-results/visual-armor-openclaw.png',
|
|
})
|
|
}
|
|
})
|
|
})
|