From e7732703a607d49104b85e186e4fff2b0c015cbb Mon Sep 17 00:00:00 2001 From: hsiegeln <37154749+hsiegeln@users.noreply.github.com> Date: Tue, 14 Apr 2026 23:21:26 +0200 Subject: [PATCH] feat: add StartupLogPanel component for deployment startup logs Co-Authored-By: Claude Opus 4.6 (1M context) --- ui/src/components/StartupLogPanel.module.css | 60 ++++++++++++++++++++ ui/src/components/StartupLogPanel.tsx | 46 +++++++++++++++ 2 files changed, 106 insertions(+) create mode 100644 ui/src/components/StartupLogPanel.module.css create mode 100644 ui/src/components/StartupLogPanel.tsx diff --git a/ui/src/components/StartupLogPanel.module.css b/ui/src/components/StartupLogPanel.module.css new file mode 100644 index 00000000..c6b724b5 --- /dev/null +++ b/ui/src/components/StartupLogPanel.module.css @@ -0,0 +1,60 @@ +.panel { + background: var(--bg-secondary); + border: 1px solid var(--border); + border-radius: 6px; + overflow: hidden; + margin-top: 8px; +} + +.header { + display: flex; + justify-content: space-between; + align-items: center; + padding: 8px 12px; + border-bottom: 1px solid var(--border); +} + +.headerLeft { + display: flex; + align-items: center; + gap: 8px; +} + +.title { + font-size: 13px; + font-weight: 600; + color: var(--text-primary); +} + +.badge { + font-size: 11px; + padding: 1px 8px; + border-radius: 10px; +} + +.badgeLive { + background: var(--success-muted); + color: var(--success); +} + +.badgeStopped { + background: var(--error-muted); + color: var(--error); +} + +.pollingHint { + font-size: 11px; + color: var(--text-muted); +} + +.lineCount { + font-size: 12px; + color: var(--text-muted); +} + +.empty { + padding: 16px; + text-align: center; + font-size: 13px; + color: var(--text-muted); +} diff --git a/ui/src/components/StartupLogPanel.tsx b/ui/src/components/StartupLogPanel.tsx new file mode 100644 index 00000000..7c976a19 --- /dev/null +++ b/ui/src/components/StartupLogPanel.tsx @@ -0,0 +1,46 @@ +import { LogViewer } from '@cameleer/design-system'; +import { useStartupLogs } from '../api/queries/logs'; +import type { Deployment } from '../api/queries/admin/apps'; +import styles from './StartupLogPanel.module.css'; + +interface StartupLogPanelProps { + deployment: Deployment; + appSlug: string; + envSlug: string; +} + +export function StartupLogPanel({ deployment, appSlug, envSlug }: StartupLogPanelProps) { + const isStarting = deployment.status === 'STARTING'; + const isFailed = deployment.status === 'FAILED'; + + const { data } = useStartupLogs(appSlug, envSlug, deployment.createdAt, isStarting); + + const entries = data?.data ?? []; + + if (entries.length === 0 && !isStarting) return null; + + return ( +
+
+
+ Startup Logs + {isStarting && ( + <> + ● live + polling every 3s + + )} + {isFailed && ( + stopped + )} +
+ {entries.length} lines +
+ {entries.length > 0 ? ( + + ) : ( +
Waiting for container output...
+ )} +
+ ); +}