'use client'; import { useState } from 'react'; import { Pencil, Save, X, Settings2 } from 'lucide-react'; import { Button } from '../ui/button'; import { Input } from '../ui/input'; import { Label } from '../ui/label'; import { Card, CardContent, CardDescription, CardHeader, CardTitle, } from '../ui/card'; export interface WorkflowSettingsCardProps { /** Workflow identifier — passed through to {@link onSave} so the consumer can persist. */ workflowId: string; /** Current workflow-level settings (arbitrary key/value map). */ settings: Record; /** * Persist edited settings. Supplied by the consumer (no API coupling here). * Rejecting the promise surfaces its message inline. When omitted the card * is read-only (the Edit affordance is hidden). */ onSave?: (settings: Record) => Promise; } /** Well-known settings with labels and descriptions */ const KNOWN_FIELDS: { key: string; label: string; hint: string; type: 'number' | 'text'; }[] = [ { key: 'timeout', label: 'Timeout', hint: 'seconds', type: 'number' }, { key: 'maxRetries', label: 'Max Retries', hint: 'attempts', type: 'number' }, ]; export function WorkflowSettingsCard({ workflowId: _workflowId, settings, onSave, }: WorkflowSettingsCardProps) { const [editing, setEditing] = useState(false); const [draft, setDraft] = useState>({ ...settings }); const [saving, setSaving] = useState(false); const [error, setError] = useState(null); const knownKeys = new Set(KNOWN_FIELDS.map((f) => f.key)); const unknownKeys = Object.keys(settings).filter((k) => !knownKeys.has(k)); function handleEdit() { setDraft({ ...settings }); setError(null); setEditing(true); } function handleCancel() { setDraft({ ...settings }); setError(null); setEditing(false); } async function handleSave() { if (!onSave) return; setSaving(true); setError(null); try { await onSave(draft); setEditing(false); } catch (err) { setError( err instanceof Error ? err.message : 'Failed to save settings' ); } finally { setSaving(false); } } function setField(key: string, value: unknown) { setDraft((prev) => ({ ...prev, [key]: value })); } const isEmpty = Object.keys(settings).length === 0; const canEdit = !!onSave; return (
Settings Workflow-level configuration
{!isEmpty && canEdit && (editing ? (
) : ( ))}
{isEmpty ? (

No settings configured.

) : ( <> {/* Known fields */} {KNOWN_FIELDS.filter((f) => f.key in settings).map((field) => (
{editing ? (
setField( field.key, field.type === 'number' ? Number(e.target.value) : e.target.value ) } className="max-w-[160px]" /> {field.hint}
) : (
{String(settings[field.key])} {field.hint}
)}
))} {/* Unknown / arbitrary keys */} {unknownKeys.map((key) => (
{editing ? ( setField(key, e.target.value)} className="font-mono text-sm" /> ) : ( {typeof settings[key] === 'object' ? JSON.stringify(settings[key]) : String(settings[key])} )}
))} {error &&

{error}

} )}
); }