@cat-factory/app 0.302.2 → 0.303.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (328) hide show
  1. package/README.md +16 -0
  2. package/app/app.config.ts +19 -10
  3. package/app/assets/css/main.css +13 -13
  4. package/app/assets/css/prose.css +22 -22
  5. package/app/assets/css/tokens.css +298 -0
  6. package/app/components/assistant/AssistantModal.vue +22 -22
  7. package/app/components/auth/AuthGate.vue +1 -1
  8. package/app/components/auth/BackendMisconfiguredScreen.vue +10 -10
  9. package/app/components/auth/LoginScreen.vue +34 -36
  10. package/app/components/auth/ResetPasswordScreen.vue +12 -12
  11. package/app/components/auth/UserMenu.vue +4 -4
  12. package/app/components/binaryCandidates/BinaryCandidatesWindow.vue +27 -25
  13. package/app/components/binaryOutput/BinaryOutputReport.vue +15 -15
  14. package/app/components/binaryOutput/StoredAssetView.vue +5 -5
  15. package/app/components/board/AddTaskModal.vue +17 -20
  16. package/app/components/board/AgentFailureCard.vue +11 -11
  17. package/app/components/board/AgentFailureHistory.vue +2 -2
  18. package/app/components/board/BoardCanvas.vue +6 -5
  19. package/app/components/board/CreateInitiativeModal.vue +8 -10
  20. package/app/components/board/DependencyConnectOverlay.vue +1 -1
  21. package/app/components/board/FailureHistoryList.vue +7 -7
  22. package/app/components/board/RecurringPipelineModal.vue +17 -17
  23. package/app/components/board/ReviewFrictionDialog.vue +6 -6
  24. package/app/components/board/StepExecutionHistory.vue +13 -13
  25. package/app/components/board/TaskDependencyEdges.vue +8 -8
  26. package/app/components/board/nodes/AgentChip.vue +10 -10
  27. package/app/components/board/nodes/BlockNode.vue +29 -29
  28. package/app/components/board/nodes/DecisionBadge.vue +2 -2
  29. package/app/components/board/nodes/EpicNode.vue +14 -10
  30. package/app/components/board/nodes/FrameSwimlanes.vue +7 -9
  31. package/app/components/board/nodes/InitiativeCard.vue +8 -8
  32. package/app/components/board/nodes/LaneGroup.vue +1 -1
  33. package/app/components/board/nodes/LaneTask.vue +2 -2
  34. package/app/components/board/nodes/ResizeGrips.vue +4 -4
  35. package/app/components/board/nodes/TaskCard.vue +18 -18
  36. package/app/components/board/nodes/TaskLane.vue +5 -5
  37. package/app/components/board/nodes/TaskPipelineMini.vue +18 -18
  38. package/app/components/bootstrap/AdoptionReviewModal.vue +29 -26
  39. package/app/components/bootstrap/BootstrapModal.vue +21 -23
  40. package/app/components/bootstrap/BootstrapRunSteps.vue +1 -1
  41. package/app/components/brainstorm/BrainstormWindow.vue +30 -33
  42. package/app/components/bugFishing/BugFishingWindow.vue +49 -49
  43. package/app/components/clarity/ClarityReviewWindow.vue +30 -30
  44. package/app/components/common/AsyncViewError.vue +5 -5
  45. package/app/components/common/ClarificationItem.vue +8 -13
  46. package/app/components/common/ConfirmDialog.vue +4 -2
  47. package/app/components/common/DescriptorFields.vue +1 -1
  48. package/app/components/common/EmptyState.vue +3 -3
  49. package/app/components/common/InterviewGateNotice.vue +7 -7
  50. package/app/components/common/KeyboardShortcutsHelp.vue +1 -1
  51. package/app/components/common/MarkdownProse.vue +14 -13
  52. package/app/components/consensus/ConsensusSessionWindow.vue +26 -26
  53. package/app/components/context/ContextAttachmentFields.vue +17 -17
  54. package/app/components/docs/DocInterviewWindow.vue +14 -14
  55. package/app/components/documents/ContextDocumentPicker.vue +17 -17
  56. package/app/components/documents/DocumentImportModal.vue +7 -7
  57. package/app/components/documents/DocumentSourceConnectModal.vue +3 -3
  58. package/app/components/documents/DocumentSyncState.vue +5 -5
  59. package/app/components/documents/DocumentTemplatesModal.vue +15 -15
  60. package/app/components/documents/RepoContextDocPicker.vue +5 -5
  61. package/app/components/documents/SpawnPreviewModal.vue +12 -12
  62. package/app/components/documents/StartFromDesignModal.vue +11 -11
  63. package/app/components/documents/TaskContextDocs.vue +5 -5
  64. package/app/components/environments/EnvSetupStepper.vue +6 -6
  65. package/app/components/environments/EnvironmentStatusPanel.vue +17 -17
  66. package/app/components/environments/steps/EnvPickStep.vue +3 -3
  67. package/app/components/environments/steps/EnvPreflightStep.vue +9 -9
  68. package/app/components/environments/steps/EnvReviewStep.vue +25 -22
  69. package/app/components/environments/steps/EnvSaveStep.vue +7 -5
  70. package/app/components/environments/steps/JourneyStepNav.vue +1 -1
  71. package/app/components/focus/BlockFocusView.vue +17 -19
  72. package/app/components/followUp/FollowUpWindow.vue +23 -23
  73. package/app/components/forkDecision/ForkDecisionWindow.vue +37 -39
  74. package/app/components/foundational/FoundationalContractSummary.vue +7 -7
  75. package/app/components/foundational/FoundationalServiceCatalogList.vue +11 -11
  76. package/app/components/foundational/FoundationalServiceManager.vue +1 -1
  77. package/app/components/foundational/FoundationalServiceRegistry.vue +13 -13
  78. package/app/components/foundational/FoundationalServiceSources.vue +13 -13
  79. package/app/components/foundational/FoundationalSuppressions.vue +7 -7
  80. package/app/components/foundational/ServiceCatalogConnection.vue +10 -10
  81. package/app/components/fragments/FragmentLibraryManager.vue +41 -44
  82. package/app/components/fragments/FragmentSelector.vue +13 -13
  83. package/app/components/fragments/GitHubDocUrlImport.vue +1 -1
  84. package/app/components/gates/GateFailingCheckList.vue +5 -5
  85. package/app/components/gates/GateResultView.vue +50 -47
  86. package/app/components/github/AddServiceFromRepoModal.vue +14 -14
  87. package/app/components/github/BranchProtectionPreflight.vue +13 -13
  88. package/app/components/github/GitHubConnect.vue +7 -7
  89. package/app/components/github/GitHubOnboarding.vue +7 -7
  90. package/app/components/github/GitHubPanel.vue +37 -40
  91. package/app/components/github/RepoTreeBrowser.vue +18 -18
  92. package/app/components/humanTest/HumanTestWindow.vue +30 -33
  93. package/app/components/initiative/InitiativePlanNotice.vue +5 -5
  94. package/app/components/initiative/InitiativePlanReview.vue +27 -29
  95. package/app/components/initiative/InitiativePlanningWindow.vue +10 -10
  96. package/app/components/initiative/InitiativeTrackerWindow.vue +71 -65
  97. package/app/components/inputGate/InputGateNotice.vue +2 -4
  98. package/app/components/judge/JudgeResultView.vue +30 -32
  99. package/app/components/kaizen/KaizenPanel.vue +40 -36
  100. package/app/components/kaizen/KaizenStepStatus.vue +21 -21
  101. package/app/components/layout/AccountAuditLog.vue +10 -10
  102. package/app/components/layout/AccountDeploymentSettings.vue +20 -20
  103. package/app/components/layout/AccountFailureKindRules.vue +13 -13
  104. package/app/components/layout/AccountFoundationalSettings.vue +1 -1
  105. package/app/components/layout/AccountFragmentSettings.vue +1 -1
  106. package/app/components/layout/AccountModelPolicySettings.vue +9 -9
  107. package/app/components/layout/AccountPlatformAlertSettings.vue +11 -11
  108. package/app/components/layout/AccountRiskPolicySettings.vue +2 -2
  109. package/app/components/layout/AccountRunCredentialSettings.vue +5 -5
  110. package/app/components/layout/AccountSkillSettings.vue +1 -1
  111. package/app/components/layout/AccountTeamSettings.vue +23 -15
  112. package/app/components/layout/AiProvidersBanner.vue +11 -8
  113. package/app/components/layout/AppearanceSwitcher.vue +108 -0
  114. package/app/components/layout/BoardSwitcher.vue +8 -11
  115. package/app/components/layout/BoardToolbar.vue +3 -3
  116. package/app/components/layout/CommandBar.vue +7 -9
  117. package/app/components/layout/ConnectionStatusBanner.vue +2 -2
  118. package/app/components/layout/DefaultTestEnvBanner.vue +5 -5
  119. package/app/components/layout/GitHubPatBanner.vue +5 -5
  120. package/app/components/layout/GitHubPatPermissionsBanner.vue +16 -10
  121. package/app/components/layout/InfraSetupBanner.vue +6 -6
  122. package/app/components/layout/IntegrationsHub.vue +15 -15
  123. package/app/components/layout/LanguageSwitcher.vue +5 -5
  124. package/app/components/layout/ModelProvidersHub.vue +13 -16
  125. package/app/components/layout/NotificationsInbox.vue +10 -10
  126. package/app/components/layout/PersonalSetupModal.vue +8 -8
  127. package/app/components/layout/ProviderConfigBanner.vue +4 -4
  128. package/app/components/layout/RolePrompt.vue +7 -7
  129. package/app/components/layout/SideBar.vue +6 -4
  130. package/app/components/layout/SpendWarningBanner.vue +17 -14
  131. package/app/components/layout/TranslationWarningBanner.vue +4 -4
  132. package/app/components/layout/UiModeSwitcher.vue +13 -13
  133. package/app/components/layout/UiRoleSwitcher.vue +8 -8
  134. package/app/components/layout/WorkspaceMembersSettings.vue +15 -11
  135. package/app/components/media/ArtifactLightbox.vue +13 -13
  136. package/app/components/media/ImageCompare.vue +31 -24
  137. package/app/components/merge/MergeEffortChips.vue +2 -2
  138. package/app/components/notifications/NotificationSettingsPanel.vue +14 -12
  139. package/app/components/observability/OutcomeFilterChips.vue +6 -6
  140. package/app/components/observability/RunFailureSummary.vue +28 -25
  141. package/app/components/observability/StepMetricsBar.vue +26 -28
  142. package/app/components/observability/StepModelActivity.vue +2 -2
  143. package/app/components/observability/ToolCallList.vue +24 -24
  144. package/app/components/outcome/OutcomeSummaryWindow.vue +47 -47
  145. package/app/components/palettes/AgentPalette.vue +8 -8
  146. package/app/components/palettes/AgentTierSelect.vue +1 -1
  147. package/app/components/palettes/PipelinePurposeSelect.vue +1 -1
  148. package/app/components/panels/AgentStepDetail.vue +52 -51
  149. package/app/components/panels/AttemptEntryHeader.vue +4 -6
  150. package/app/components/panels/DecisionModal.vue +7 -7
  151. package/app/components/panels/GenericStructuredResultView.vue +7 -7
  152. package/app/components/panels/InspectorPanel.vue +17 -17
  153. package/app/components/panels/MergerResultView.vue +19 -19
  154. package/app/components/panels/ObservabilityPanel.vue +115 -123
  155. package/app/components/panels/OperatorDashboardPanel.vue +89 -97
  156. package/app/components/panels/ReportsPanel.vue +69 -66
  157. package/app/components/panels/ReportsSpendBreakdown.vue +9 -9
  158. package/app/components/panels/ResultWindowShell.vue +38 -38
  159. package/app/components/panels/RunDetailLoadState.vue +2 -2
  160. package/app/components/panels/StepContainerStatus.vue +9 -9
  161. package/app/components/panels/StepDelegatedStatus.logic.spec.ts +135 -0
  162. package/app/components/panels/StepDelegatedStatus.logic.ts +160 -0
  163. package/app/components/panels/StepDelegatedStatus.vue +181 -0
  164. package/app/components/panels/StepEffortReport.vue +16 -15
  165. package/app/components/panels/StepFragmentAdherence.vue +14 -10
  166. package/app/components/panels/StepMetadataCard.vue +74 -45
  167. package/app/components/panels/StepReproductionReport.vue +25 -21
  168. package/app/components/panels/StepRunMeta.vue +20 -20
  169. package/app/components/panels/StepTestReport.logic.spec.ts +8 -3
  170. package/app/components/panels/StepTestReport.logic.ts +4 -4
  171. package/app/components/panels/StepTestReport.vue +28 -28
  172. package/app/components/panels/StepToolServers.vue +14 -11
  173. package/app/components/panels/StepValidationReport.vue +7 -7
  174. package/app/components/panels/inspector/ContainerSummary.vue +9 -9
  175. package/app/components/panels/inspector/DocReferenceRepos.vue +3 -3
  176. package/app/components/panels/inspector/EnvProbeReport.vue +24 -27
  177. package/app/components/panels/inspector/EpicChildren.vue +8 -12
  178. package/app/components/panels/inspector/FrontendBindingsResolved.vue +11 -11
  179. package/app/components/panels/inspector/FrontendConfig.vue +37 -41
  180. package/app/components/panels/inspector/InitiativeInspector.vue +3 -3
  181. package/app/components/panels/inspector/InspectorSection.vue +6 -6
  182. package/app/components/panels/inspector/RecurringScheduleSettings.vue +16 -19
  183. package/app/components/panels/inspector/ServiceConnections.vue +2 -2
  184. package/app/components/panels/inspector/ServiceReleaseHealthConfig.vue +2 -2
  185. package/app/components/panels/inspector/ServiceSelfTests.vue +21 -17
  186. package/app/components/panels/inspector/ServiceTestConfig.vue +51 -59
  187. package/app/components/panels/inspector/ServiceTestSecrets.vue +5 -5
  188. package/app/components/panels/inspector/ServiceTestingContext.vue +3 -3
  189. package/app/components/panels/inspector/ServiceValidationConfig.vue +2 -2
  190. package/app/components/panels/inspector/TaskAgentConfig.vue +3 -3
  191. package/app/components/panels/inspector/TaskAprioriBranches.vue +8 -5
  192. package/app/components/panels/inspector/TaskDependencies.vue +1 -1
  193. package/app/components/panels/inspector/TaskEstimateBadge.vue +11 -11
  194. package/app/components/panels/inspector/TaskExecution.vue +17 -17
  195. package/app/components/panels/inspector/TaskReviewTarget.vue +2 -2
  196. package/app/components/panels/inspector/TaskRunSettings.vue +35 -37
  197. package/app/components/panels/inspector/TaskStructure.vue +3 -3
  198. package/app/components/pipeline/AgentKindIcon.vue +1 -1
  199. package/app/components/pipeline/AgentPromptEditor.vue +17 -17
  200. package/app/components/pipeline/BinaryOutputStepPicker.vue +42 -56
  201. package/app/components/pipeline/EstimateThresholdFields.vue +4 -4
  202. package/app/components/pipeline/GateConfigFields.vue +13 -10
  203. package/app/components/pipeline/IterationCapPrompt.vue +4 -2
  204. package/app/components/pipeline/PipelineBuilder.vue +47 -55
  205. package/app/components/pipeline/PipelineHealthModal.vue +27 -29
  206. package/app/components/pipeline/PipelinePicker.vue +10 -10
  207. package/app/components/pipeline/PipelinePreview.vue +10 -10
  208. package/app/components/pipeline/PipelineProgress.vue +64 -67
  209. package/app/components/prReview/PrReviewPhaseBadge.vue +7 -7
  210. package/app/components/prReview/PrReviewWindow.vue +75 -77
  211. package/app/components/providers/AiPresetMismatchDialog.vue +5 -5
  212. package/app/components/providers/AiProviderOnboardingModal.vue +9 -9
  213. package/app/components/providers/ApiKeysSection.vue +13 -13
  214. package/app/components/providers/PersonalCredentialModal.vue +2 -2
  215. package/app/components/providers/PersonalSubscriptionSection.vue +10 -10
  216. package/app/components/providers/SignInRequiredNotice.vue +1 -1
  217. package/app/components/providers/VendorCredentialsModal.vue +10 -10
  218. package/app/components/provisioning/ProvisioningLogsDrawer.vue +13 -13
  219. package/app/components/ralph/RalphLoopResultView.vue +28 -30
  220. package/app/components/recurring/RecurrenceEditor.vue +2 -2
  221. package/app/components/requirements/RequirementsReviewWindow.vue +51 -58
  222. package/app/components/riskPolicy/RiskPolicyPicker.vue +12 -15
  223. package/app/components/riskPolicy/RiskPolicyPreview.vue +14 -14
  224. package/app/components/sandbox/SandboxPanel.vue +58 -59
  225. package/app/components/settings/AccountSettingsPanel.vue +1 -1
  226. package/app/components/settings/ApiTokensPanel.vue +10 -10
  227. package/app/components/settings/BudgetSettings.vue +18 -22
  228. package/app/components/settings/CapabilityCredentialsPanel.vue +15 -15
  229. package/app/components/settings/CloudflareHandlerSection.vue +20 -20
  230. package/app/components/settings/ComposeEnvironmentSetupSection.vue +13 -13
  231. package/app/components/settings/ConnectionTestVerdict.vue +3 -3
  232. package/app/components/settings/ConnectionWarnings.vue +1 -1
  233. package/app/components/settings/ConsensusGroupsSection.vue +27 -35
  234. package/app/components/settings/CustomManifestTypeEditor.vue +10 -10
  235. package/app/components/settings/DefaultProvisionTypeSection.vue +6 -6
  236. package/app/components/settings/InfraHandlersConfigurator.vue +24 -22
  237. package/app/components/settings/InfrastructureBackendPicker.vue +6 -6
  238. package/app/components/settings/InfrastructureWindow.vue +5 -5
  239. package/app/components/settings/IssueTrackerPanel.vue +29 -23
  240. package/app/components/settings/KubernetesEngineForm.vue +11 -11
  241. package/app/components/settings/KubernetesEnvironmentForm.vue +4 -4
  242. package/app/components/settings/LocalContainerPoolSettings.vue +6 -11
  243. package/app/components/settings/LocalModelEndpointsPanel.vue +20 -18
  244. package/app/components/settings/McpAuthorizeScreen.vue +13 -15
  245. package/app/components/settings/McpOAuthCallbackScreen.vue +16 -10
  246. package/app/components/settings/MergeClassRulesEditor.vue +6 -9
  247. package/app/components/settings/MergeRolePolicyEditor.vue +16 -16
  248. package/app/components/settings/ModelConfigurationPanel.vue +23 -30
  249. package/app/components/settings/ModelPresetHealthModal.vue +15 -13
  250. package/app/components/settings/ObservabilityConnectionPanel.vue +4 -4
  251. package/app/components/settings/OpenRouterCatalogPanel.vue +23 -19
  252. package/app/components/settings/PackageRegistriesPanel.vue +8 -8
  253. package/app/components/settings/ProviderConnectionTab.vue +8 -11
  254. package/app/components/settings/ProviderManifestEditor.vue +9 -9
  255. package/app/components/settings/ProviderPreferenceEditor.vue +8 -8
  256. package/app/components/settings/RiskPolicyCreateForm.vue +10 -10
  257. package/app/components/settings/RiskPolicyEditorRow.vue +14 -14
  258. package/app/components/settings/RiskPolicyHealthModal.vue +15 -13
  259. package/app/components/settings/RiskPolicyInheritedRow.vue +1 -1
  260. package/app/components/settings/RiskPolicyPanel.vue +10 -15
  261. package/app/components/settings/ServiceFragmentDefaultsPanel.vue +7 -7
  262. package/app/components/settings/SharedStacksPanel.vue +9 -12
  263. package/app/components/settings/TaskSourceCard.vue +4 -4
  264. package/app/components/settings/TaskTypeSuppressionsPanel.vue +6 -6
  265. package/app/components/settings/ToolServerChecklist.vue +36 -29
  266. package/app/components/settings/UsageSettings.vue +15 -15
  267. package/app/components/settings/UserSecretsSection.vue +9 -12
  268. package/app/components/settings/WorkspaceMetadataSettings.vue +5 -5
  269. package/app/components/settings/WorkspaceSettingsPanel.vue +47 -47
  270. package/app/components/skills/ReviewSkillQueue.vue +10 -10
  271. package/app/components/skills/SkillLibraryManager.vue +23 -20
  272. package/app/components/slack/SlackPanel.vue +13 -17
  273. package/app/components/spec/ServiceSpecWindow.vue +45 -42
  274. package/app/components/tasks/BugHuntModal.vue +24 -27
  275. package/app/components/tasks/ContextIssuePicker.vue +11 -11
  276. package/app/components/tasks/TaskContextIssues.vue +3 -3
  277. package/app/components/tasks/TaskImportModal.vue +7 -7
  278. package/app/components/tasks/TaskSourceConnectModal.vue +10 -8
  279. package/app/components/testing/TestReportWindow.vue +99 -82
  280. package/app/components/theme/ThemeImportModal.vue +115 -0
  281. package/app/components/tutorial/TutorialCatalogue.vue +9 -9
  282. package/app/components/tutorial/TutorialNudge.vue +5 -5
  283. package/app/components/tutorial/TutorialOverlay.vue +12 -12
  284. package/app/components/tutorial/TutorialPrompt.vue +6 -9
  285. package/app/components/vcs/GitLabConnect.vue +4 -4
  286. package/app/components/vcs/VcsConnectSurfaces.vue +2 -2
  287. package/app/components/visualConfirm/VisualConfirmationWindow.vue +36 -36
  288. package/app/composables/api/client.ts +6 -1
  289. package/app/composables/usePipelineErrorToast.ts +17 -0
  290. package/app/modular/agent-kinds.ts +24 -0
  291. package/app/pages/index.vue +5 -5
  292. package/app/plugins/theme.client.ts +125 -0
  293. package/app/spa-loading-template.html +52 -14
  294. package/app/stores/agents.ts +1 -1
  295. package/app/stores/theme.spec.ts +56 -0
  296. package/app/stores/theme.ts +87 -0
  297. package/app/types/domain.ts +19 -0
  298. package/app/types/execution.ts +4 -0
  299. package/app/utils/agentOutput.ts +1 -1
  300. package/app/utils/binaryOutput.ts +6 -6
  301. package/app/utils/bootstrapSteps.ts +14 -14
  302. package/app/utils/catalog.ts +87 -83
  303. package/app/utils/colorTint.ts +10 -0
  304. package/app/utils/failureKinds.ts +1 -0
  305. package/app/utils/observability.ts +3 -3
  306. package/app/utils/pipelineRender.ts +13 -17
  307. package/app/utils/swimlanes.ts +4 -4
  308. package/app/utils/theme/bootPalette.spec.ts +54 -0
  309. package/app/utils/theme/bootPalette.ts +108 -0
  310. package/app/utils/theme/builtins.spec.ts +38 -0
  311. package/app/utils/theme/builtins.ts +55 -0
  312. package/app/utils/theme/css.ts +162 -0
  313. package/app/utils/theme/doc.ts +353 -0
  314. package/app/utils/theme/link.ts +93 -0
  315. package/app/utils/theme/presets.ts +509 -0
  316. package/app/utils/theme/theme.spec.ts +224 -0
  317. package/i18n/locales/de.json +61 -4
  318. package/i18n/locales/en.json +70 -4
  319. package/i18n/locales/es.json +61 -4
  320. package/i18n/locales/fr.json +61 -4
  321. package/i18n/locales/he.json +61 -4
  322. package/i18n/locales/it.json +61 -4
  323. package/i18n/locales/ja.json +61 -4
  324. package/i18n/locales/pl.json +61 -4
  325. package/i18n/locales/tr.json +61 -4
  326. package/i18n/locales/uk.json +61 -4
  327. package/nuxt.config.ts +37 -11
  328. package/package.json +9 -8
@@ -120,12 +120,12 @@ const STATUS_META: Record<
120
120
  FollowUpItem['status'],
121
121
  { badge: 'neutral' | 'info' | 'success' | 'warning'; text: string }
122
122
  > = {
123
- pending: { badge: 'warning', text: 'text-amber-300' },
124
- filed: { badge: 'success', text: 'text-emerald-300' },
125
- queued: { badge: 'info', text: 'text-sky-300' },
126
- answered: { badge: 'info', text: 'text-sky-300' },
127
- closed: { badge: 'neutral', text: 'text-slate-300' },
128
- dismissed: { badge: 'neutral', text: 'text-slate-400' },
123
+ pending: { badge: 'warning', text: 'text-app-warning-300' },
124
+ filed: { badge: 'success', text: 'text-app-success-300' },
125
+ queued: { badge: 'info', text: 'text-app-info-300' },
126
+ answered: { badge: 'info', text: 'text-app-info-300' },
127
+ closed: { badge: 'neutral', text: 'text-toned' },
128
+ dismissed: { badge: 'neutral', text: 'text-muted' },
129
129
  }
130
130
 
131
131
  /** Whether a decided item carries a recorded reply to show ('answered' or 'closed'). */
@@ -138,7 +138,7 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
138
138
  <ResultWindowShell
139
139
  :open="open"
140
140
  :icon="FOLLOW_UP_COMPANION_META.icon"
141
- icon-class="bg-pink-500/15 text-pink-300"
141
+ icon-class="bg-app-hue-pink/15 text-app-hue-pink"
142
142
  :title="headerTitle"
143
143
  :subtitle="t('followUp.subtitle')"
144
144
  width="3xl"
@@ -158,11 +158,11 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
158
158
  <!-- Empty -->
159
159
  <div
160
160
  v-if="items.length === 0"
161
- class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-slate-400"
161
+ class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-muted"
162
162
  >
163
163
  <UIcon :name="FOLLOW_UP_COMPANION_META.icon" class="h-8 w-8 opacity-40" />
164
164
  <p class="text-sm">{{ t('followUp.empty.title') }}</p>
165
- <p class="max-w-sm text-[11px] text-slate-500">
165
+ <p class="max-w-sm text-[11px] text-dimmed">
166
166
  {{ t('followUp.empty.hint') }}
167
167
  </p>
168
168
  </div>
@@ -170,7 +170,7 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
170
170
  <div v-else class="space-y-3">
171
171
  <p
172
172
  v-if="followUps.error"
173
- class="rounded-md bg-rose-500/10 px-3 py-2 text-[12px] text-rose-300"
173
+ class="rounded-md bg-app-error-500/10 px-3 py-2 text-[12px] text-app-error-300"
174
174
  >
175
175
  {{ followUps.error }}
176
176
  </p>
@@ -178,29 +178,29 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
178
178
  <article
179
179
  v-for="item in items"
180
180
  :key="item.id"
181
- class="rounded-xl border border-slate-800 bg-slate-900/60 px-4 py-3"
182
- :class="item.status === 'pending' ? 'border-amber-500/40' : ''"
181
+ class="rounded-xl border border-default bg-default/60 px-4 py-3"
182
+ :class="item.status === 'pending' ? 'border-app-warning-500/40' : ''"
183
183
  >
184
184
  <div class="flex items-start gap-2">
185
185
  <UIcon
186
186
  :name="item.kind === 'question' ? 'i-lucide-circle-help' : 'i-lucide-compass'"
187
187
  class="mt-0.5 h-4 w-4 shrink-0"
188
- :class="item.kind === 'question' ? 'text-sky-300' : 'text-pink-300'"
188
+ :class="item.kind === 'question' ? 'text-app-info-300' : 'text-app-hue-pink'"
189
189
  />
190
190
  <div class="min-w-0 flex-1">
191
191
  <div class="flex items-center gap-2">
192
- <h3 class="min-w-0 flex-1 truncate text-[13px] font-medium text-slate-100">
192
+ <h3 class="min-w-0 flex-1 truncate text-[13px] font-medium text-app-100">
193
193
  {{ item.title }}
194
194
  </h3>
195
195
  <UBadge :color="STATUS_META[item.status].badge" variant="subtle" size="sm">
196
196
  {{ t(STATUS_LABEL_KEYS[item.status]) }}
197
197
  </UBadge>
198
198
  </div>
199
- <p v-if="item.detail" class="mt-1 whitespace-pre-wrap text-[12px] text-slate-300">
199
+ <p v-if="item.detail" class="mt-1 whitespace-pre-wrap text-[12px] text-toned">
200
200
  {{ item.detail }}
201
201
  </p>
202
- <p v-if="item.suggestedAction" class="mt-1 text-[11px] text-slate-400">
203
- <span class="text-slate-500">{{ t('followUp.suggested') }}</span>
202
+ <p v-if="item.suggestedAction" class="mt-1 text-[11px] text-muted">
203
+ <span class="text-dimmed">{{ t('followUp.suggested') }}</span>
204
204
  {{ item.suggestedAction }}
205
205
  </p>
206
206
  <p v-if="item.status === 'filed' && item.ticketUrl" class="mt-1 text-[11px]">
@@ -208,13 +208,13 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
208
208
  :href="item.ticketUrl"
209
209
  target="_blank"
210
210
  rel="noopener"
211
- class="text-emerald-300 hover:underline"
211
+ class="text-app-success-300 hover:underline"
212
212
  >
213
213
  {{ item.ticketExternalId ?? t('followUp.viewIssue') }}
214
214
  </a>
215
215
  </p>
216
- <p v-if="hasRecordedAnswer(item)" class="mt-1 text-[11px] text-slate-300">
217
- <span class="text-slate-500">
216
+ <p v-if="hasRecordedAnswer(item)" class="mt-1 text-[11px] text-toned">
217
+ <span class="text-dimmed">
218
218
  {{
219
219
  item.status === 'closed' ? t('followUp.yourRuling') : t('followUp.yourAnswer')
220
220
  }}
@@ -223,7 +223,7 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
223
223
  </p>
224
224
  <!-- A decision that was made and then thrown away when the budget ran out. It must
225
225
  not read like one the Coder acted on. -->
226
- <p v-if="item.sendBackDropped" class="mt-1 text-[11px] text-amber-300">
226
+ <p v-if="item.sendBackDropped" class="mt-1 text-[11px] text-app-warning-300">
227
227
  {{ t('followUp.sendBackDropped') }}
228
228
  </p>
229
229
 
@@ -235,7 +235,7 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
235
235
  v-model="drafts[item.id]"
236
236
  rows="2"
237
237
  :placeholder="t('followUp.answerPlaceholder')"
238
- class="w-full resize-y rounded-md border border-slate-700 bg-slate-950/60 px-2.5 py-1.5 text-[12px] text-slate-100 placeholder:text-slate-600 focus:border-sky-500 focus:outline-none focus-visible:ring-2 focus-visible:ring-sky-500/60"
238
+ class="w-full resize-y rounded-md border border-muted bg-app-950/60 px-2.5 py-1.5 text-[12px] text-app-100 placeholder:text-app-600 focus:border-app-info-500 focus:outline-none focus-visible:ring-2 focus-visible:ring-app-info-500/60"
239
239
  />
240
240
  <!-- Wraps, like the follow-up row below: three buttons whose labels are two
241
241
  words each in English are one long line in most of the other locales, and
@@ -323,7 +323,7 @@ function hasRecordedAnswer(item: FollowUpItem): boolean {
323
323
  </div>
324
324
 
325
325
  <footer
326
- class="flex items-center justify-between border-t border-slate-800 px-5 py-2.5 text-[11px] text-slate-400"
326
+ class="flex items-center justify-between border-t border-default px-5 py-2.5 text-[11px] text-muted"
327
327
  >
328
328
  <span>
329
329
  {{
@@ -151,7 +151,7 @@ const { requestClose } = useUnsavedGuard({
151
151
  <ResultWindowShell
152
152
  :open="open"
153
153
  :icon="FORK_DECISION_META.icon"
154
- icon-class="bg-violet-500/15 text-violet-300"
154
+ icon-class="bg-app-secondary-500/15 text-app-secondary-300"
155
155
  :title="headerTitle"
156
156
  :subtitle="t('forkDecision.subtitle')"
157
157
  width="3xl"
@@ -162,11 +162,11 @@ const { requestClose } = useUnsavedGuard({
162
162
  <!-- Proposing: the read-only proposer is still working. -->
163
163
  <div
164
164
  v-if="status === 'proposing'"
165
- class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-slate-400"
165
+ class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-muted"
166
166
  >
167
167
  <UIcon name="i-lucide-loader-circle" class="h-8 w-8 animate-spin opacity-60" />
168
168
  <p class="text-sm">{{ t('forkDecision.proposing.title') }}</p>
169
- <p class="max-w-sm text-[11px] text-slate-500">
169
+ <p class="max-w-sm text-[11px] text-dimmed">
170
170
  {{ t('forkDecision.proposing.hint') }}
171
171
  </p>
172
172
  </div>
@@ -174,9 +174,9 @@ const { requestClose } = useUnsavedGuard({
174
174
  <!-- A single path (no materially different alternatives): a read-only record. -->
175
175
  <div
176
176
  v-else-if="status === 'single_path'"
177
- class="rounded-xl border border-slate-800 bg-slate-900/60 px-4 py-3 text-slate-300"
177
+ class="rounded-xl border border-default bg-default/60 px-4 py-3 text-toned"
178
178
  >
179
- <p class="text-[13px] font-medium text-slate-100">
179
+ <p class="text-[13px] font-medium text-app-100">
180
180
  {{ t('forkDecision.singlePath.title') }}
181
181
  </p>
182
182
  <p v-if="state?.singlePathReason" class="mt-1 text-[12px]">
@@ -187,9 +187,9 @@ const { requestClose } = useUnsavedGuard({
187
187
  <!-- Chosen: a read-only record of what was decided. -->
188
188
  <div
189
189
  v-else-if="status === 'chosen'"
190
- class="rounded-xl border border-violet-500/40 bg-slate-900/60 px-4 py-3 text-slate-300"
190
+ class="rounded-xl border border-app-secondary-500/40 bg-default/60 px-4 py-3 text-toned"
191
191
  >
192
- <p class="text-[13px] font-medium text-violet-200">
192
+ <p class="text-[13px] font-medium text-app-secondary-200">
193
193
  {{ t('forkDecision.chosen.title') }}
194
194
  </p>
195
195
  <p v-if="state?.chosen?.custom" class="mt-1 whitespace-pre-wrap text-[12px]">
@@ -198,7 +198,7 @@ const { requestClose } = useUnsavedGuard({
198
198
  <p v-else-if="state?.chosen?.forkId" class="mt-1 text-[12px]">
199
199
  {{ forks.find((f) => f.id === state?.chosen?.forkId)?.title }}
200
200
  </p>
201
- <p v-if="state?.chosen?.note" class="mt-1 text-[11px] text-slate-400">
201
+ <p v-if="state?.chosen?.note" class="mt-1 text-[11px] text-muted">
202
202
  {{ t('forkDecision.chosen.note', { note: state.chosen.note }) }}
203
203
  </p>
204
204
  </div>
@@ -207,16 +207,16 @@ const { requestClose } = useUnsavedGuard({
207
207
  <div v-else-if="interactive" class="space-y-3">
208
208
  <p
209
209
  v-if="forkDecision.error"
210
- class="rounded-md bg-rose-500/10 px-3 py-2 text-[12px] text-rose-300"
210
+ class="rounded-md bg-app-error-500/10 px-3 py-2 text-[12px] text-app-error-300"
211
211
  >
212
212
  {{ forkDecision.error }}
213
213
  </p>
214
214
 
215
215
  <p
216
216
  v-if="state?.seamSummary"
217
- class="rounded-md bg-slate-800/50 px-3 py-2 text-[12px] text-slate-300"
217
+ class="rounded-md bg-elevated/50 px-3 py-2 text-[12px] text-toned"
218
218
  >
219
- <span class="text-slate-500">{{ t('forkDecision.seam') }}</span>
219
+ <span class="text-dimmed">{{ t('forkDecision.seam') }}</span>
220
220
  {{ state.seamSummary }}
221
221
  </p>
222
222
 
@@ -228,44 +228,44 @@ const { requestClose } = useUnsavedGuard({
228
228
  class="cursor-pointer rounded-xl border px-4 py-3 transition"
229
229
  :class="
230
230
  selected === fork.id
231
- ? 'border-violet-500/70 bg-violet-500/5'
232
- : 'border-slate-800 bg-slate-900/60 hover:border-slate-700'
231
+ ? 'border-app-secondary-500/70 bg-app-secondary-500/5'
232
+ : 'border-default bg-default/60 hover:border-muted'
233
233
  "
234
234
  @click="selected = fork.id"
235
235
  >
236
236
  <div class="flex items-start gap-2">
237
237
  <input
238
238
  type="radio"
239
- class="mt-1 accent-violet-500"
239
+ class="mt-1 accent-app-secondary-500"
240
240
  :checked="selected === fork.id"
241
241
  @change="selected = fork.id"
242
242
  />
243
243
  <div class="min-w-0 flex-1">
244
244
  <div class="flex items-center gap-2">
245
- <h3 class="min-w-0 flex-1 text-[13px] font-medium text-slate-100">
245
+ <h3 class="min-w-0 flex-1 text-[13px] font-medium text-app-100">
246
246
  {{ fork.title }}
247
247
  </h3>
248
248
  <UBadge v-if="fork.recommended" color="primary" variant="subtle" size="sm">
249
249
  {{ t('forkDecision.recommended') }}
250
250
  </UBadge>
251
251
  </div>
252
- <p v-if="fork.summary" class="mt-0.5 text-[12px] text-slate-400">
252
+ <p v-if="fork.summary" class="mt-0.5 text-[12px] text-muted">
253
253
  {{ fork.summary }}
254
254
  </p>
255
- <p class="mt-1.5 whitespace-pre-wrap text-[12px] text-slate-300">
255
+ <p class="mt-1.5 whitespace-pre-wrap text-[12px] text-toned">
256
256
  {{ fork.approach }}
257
257
  </p>
258
258
  <ul v-if="fork.tradeoffs.length" class="mt-1.5 space-y-0.5">
259
259
  <li
260
260
  v-for="(tr, i) in fork.tradeoffs"
261
261
  :key="i"
262
- class="flex gap-1.5 text-[11px] text-slate-400"
262
+ class="flex gap-1.5 text-[11px] text-muted"
263
263
  >
264
- <span class="text-slate-600">•</span>{{ tr }}
264
+ <span class="text-app-600">•</span>{{ tr }}
265
265
  </li>
266
266
  </ul>
267
- <p v-if="fork.riskNotes" class="mt-1.5 text-[11px] text-amber-300/90">
268
- <span class="text-amber-500/70">{{ t('forkDecision.riskNotes') }}</span>
267
+ <p v-if="fork.riskNotes" class="mt-1.5 text-[11px] text-app-warning-300/90">
268
+ <span class="text-app-warning-500/70">{{ t('forkDecision.riskNotes') }}</span>
269
269
  {{ fork.riskNotes }}
270
270
  </p>
271
271
  </div>
@@ -277,13 +277,13 @@ const { requestClose } = useUnsavedGuard({
277
277
  class="rounded-xl border px-4 py-3 transition"
278
278
  :class="
279
279
  selected === 'custom'
280
- ? 'border-violet-500/70 bg-violet-500/5'
281
- : 'border-slate-800 bg-slate-900/60'
280
+ ? 'border-app-secondary-500/70 bg-app-secondary-500/5'
281
+ : 'border-default bg-default/60'
282
282
  "
283
283
  >
284
284
  <label class="flex cursor-pointer items-center gap-2" @click="selected = 'custom'">
285
- <input type="radio" class="accent-violet-500" :checked="selected === 'custom'" />
286
- <span class="text-[13px] font-medium text-slate-100">{{
285
+ <input type="radio" class="accent-app-secondary-500" :checked="selected === 'custom'" />
286
+ <span class="text-[13px] font-medium text-app-100">{{
287
287
  t('forkDecision.custom.title')
288
288
  }}</span>
289
289
  </label>
@@ -292,27 +292,25 @@ const { requestClose } = useUnsavedGuard({
292
292
  data-testid="fork-custom-input"
293
293
  rows="3"
294
294
  :placeholder="t('forkDecision.custom.placeholder')"
295
- class="mt-2 w-full resize-y rounded-md border border-slate-700 bg-slate-950/60 px-2.5 py-1.5 text-[12px] text-slate-100 placeholder:text-slate-600 focus:border-violet-500 focus:outline-none focus-visible:ring-2 focus-visible:ring-violet-500/60"
295
+ class="mt-2 w-full resize-y rounded-md border border-muted bg-app-950/60 px-2.5 py-1.5 text-[12px] text-app-100 placeholder:text-app-600 focus:border-app-secondary-500 focus:outline-none focus-visible:ring-2 focus-visible:ring-app-secondary-500/60"
296
296
  @focus="selected = 'custom'"
297
297
  />
298
298
  </article>
299
299
 
300
300
  <!-- Optional steering note -->
301
301
  <div>
302
- <label class="mb-1 block text-[11px] text-slate-400">{{
303
- t('forkDecision.noteLabel')
304
- }}</label>
302
+ <label class="mb-1 block text-[11px] text-muted">{{ t('forkDecision.noteLabel') }}</label>
305
303
  <input
306
304
  v-model="note"
307
305
  type="text"
308
306
  :placeholder="t('forkDecision.notePlaceholder')"
309
- class="w-full rounded-md border border-slate-700 bg-slate-950/60 px-2.5 py-1.5 text-[12px] text-slate-100 placeholder:text-slate-600 focus:border-violet-500 focus:outline-none"
307
+ class="w-full rounded-md border border-muted bg-app-950/60 px-2.5 py-1.5 text-[12px] text-app-100 placeholder:text-app-600 focus:border-app-secondary-500 focus:outline-none"
310
308
  />
311
309
  </div>
312
310
 
313
311
  <!-- Grounded chat: ask about the forks before deciding. -->
314
- <section class="rounded-xl border border-slate-800 bg-slate-900/40 px-4 py-3">
315
- <p class="text-[11px] font-medium text-slate-400">
312
+ <section class="rounded-xl border border-default bg-default/40 px-4 py-3">
313
+ <p class="text-[11px] font-medium text-muted">
316
314
  {{ t('forkDecision.chat.title') }}
317
315
  </p>
318
316
  <div v-if="chat.length || answering" class="mt-2 max-h-64 space-y-2 overflow-y-auto pr-1">
@@ -327,8 +325,8 @@ const { requestClose } = useUnsavedGuard({
327
325
  class="max-w-[85%] whitespace-pre-wrap rounded-lg px-3 py-1.5 text-[12px]"
328
326
  :class="
329
327
  msg.role === 'human'
330
- ? 'bg-violet-500/15 text-violet-100'
331
- : 'bg-slate-800/70 text-slate-200'
328
+ ? 'bg-app-secondary-500/15 text-app-secondary-100'
329
+ : 'bg-elevated/70 text-default'
332
330
  "
333
331
  >
334
332
  {{ msg.text }}
@@ -336,14 +334,14 @@ const { requestClose } = useUnsavedGuard({
336
334
  </div>
337
335
  <div v-if="answering" class="flex justify-start">
338
336
  <p
339
- class="flex items-center gap-1.5 rounded-lg bg-slate-800/70 px-3 py-1.5 text-[12px] text-slate-400"
337
+ class="flex items-center gap-1.5 rounded-lg bg-elevated/70 px-3 py-1.5 text-[12px] text-muted"
340
338
  >
341
339
  <UIcon name="i-lucide-loader-circle" class="h-3.5 w-3.5 animate-spin" />
342
340
  {{ t('forkDecision.chat.thinking') }}
343
341
  </p>
344
342
  </div>
345
343
  </div>
346
- <p v-else class="mt-1 text-[11px] text-slate-500">
344
+ <p v-else class="mt-1 text-[11px] text-dimmed">
347
345
  {{ t('forkDecision.chat.hint') }}
348
346
  </p>
349
347
  <div class="mt-2 flex items-end gap-2">
@@ -357,7 +355,7 @@ const { requestClose } = useUnsavedGuard({
357
355
  ? t('forkDecision.chat.budgetSpent')
358
356
  : t('forkDecision.chat.placeholder')
359
357
  "
360
- class="min-h-0 flex-1 resize-y rounded-md border border-slate-700 bg-slate-950/60 px-2.5 py-1.5 text-[12px] text-slate-100 placeholder:text-slate-600 focus:border-violet-500 focus:outline-none disabled:opacity-50"
358
+ class="min-h-0 flex-1 resize-y rounded-md border border-muted bg-app-950/60 px-2.5 py-1.5 text-[12px] text-app-100 placeholder:text-app-600 focus:border-app-secondary-500 focus:outline-none disabled:opacity-50"
361
359
  @keydown.enter.exact.prevent="onSend"
362
360
  />
363
361
  <UButton
@@ -380,7 +378,7 @@ const { requestClose } = useUnsavedGuard({
380
378
  <!-- Skipped / no state: nothing to decide. -->
381
379
  <div
382
380
  v-else
383
- class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-slate-400"
381
+ class="flex h-full flex-col items-center justify-center gap-2 py-10 text-center text-muted"
384
382
  >
385
383
  <UIcon :name="FORK_DECISION_META.icon" class="h-8 w-8 opacity-40" />
386
384
  <p class="text-sm">{{ t('forkDecision.empty.title') }}</p>
@@ -389,7 +387,7 @@ const { requestClose } = useUnsavedGuard({
389
387
 
390
388
  <footer
391
389
  v-if="interactive"
392
- class="flex items-center justify-end gap-2 border-t border-slate-800 px-5 py-3"
390
+ class="flex items-center justify-end gap-2 border-t border-default px-5 py-3"
393
391
  >
394
392
  <UButton color="neutral" variant="ghost" size="sm" @click="requestClose">
395
393
  {{ t('common.cancel') }}
@@ -25,24 +25,24 @@ const { t, n } = useI18n()
25
25
 
26
26
  <template>
27
27
  <div v-if="contracts.length" class="mt-1 flex flex-col gap-1">
28
- <div v-for="c in contracts" :key="c.contractId" class="text-[11px] text-slate-500">
29
- <span class="text-slate-400">{{ c.title }}</span>
28
+ <div v-for="c in contracts" :key="c.contractId" class="text-[11px] text-dimmed">
29
+ <span class="text-muted">{{ c.title }}</span>
30
30
  <span class="ms-1">({{ formatLabel[c.format] }}, {{ n(c.size) }})</span>
31
- <span v-if="c.operations.length" class="ms-1 font-mono text-slate-500">
31
+ <span v-if="c.operations.length" class="ms-1 font-mono text-dimmed">
32
32
  {{ c.operations.join(' · ') }}
33
33
  </span>
34
- <span v-else-if="!operationsAreIndexable(c.format)" class="ms-1 text-slate-600">
34
+ <span v-else-if="!operationsAreIndexable(c.format)" class="ms-1 text-app-600">
35
35
  {{ t('foundational.contracts.notIndexed') }}
36
36
  </span>
37
- <span v-else-if="!c.omittedOperations" class="ms-1 text-slate-600">
37
+ <span v-else-if="!c.omittedOperations" class="ms-1 text-app-600">
38
38
  {{ t('foundational.contracts.noOperations') }}
39
39
  </span>
40
- <span v-if="c.omittedOperations > 0" class="ms-1 text-amber-500/80">
40
+ <span v-if="c.omittedOperations > 0" class="ms-1 text-app-warning-500/80">
41
41
  {{ t('foundational.contracts.omitted', { count: c.omittedOperations }) }}
42
42
  </span>
43
43
  </div>
44
44
  </div>
45
- <p v-else class="mt-1 text-[11px] text-amber-500/80">
45
+ <p v-else class="mt-1 text-[11px] text-app-warning-500/80">
46
46
  {{ t('foundational.contracts.none') }}
47
47
  </p>
48
48
  </template>
@@ -80,21 +80,21 @@ async function suppress(serviceId: string) {
80
80
 
81
81
  <template>
82
82
  <div class="flex flex-col gap-3" data-testid="foundational-catalog">
83
- <p class="text-xs text-slate-500">{{ t('foundational.catalog.intro') }}</p>
83
+ <p class="text-xs text-dimmed">{{ t('foundational.catalog.intro') }}</p>
84
84
 
85
85
  <div
86
86
  v-for="s in catalog.resolved"
87
87
  :key="s.id"
88
- class="rounded-md border border-slate-800 bg-slate-900/60 p-3"
88
+ class="rounded-md border border-default bg-default/60 p-3"
89
89
  >
90
90
  <div class="flex items-start gap-2">
91
- <UIcon name="i-lucide-boxes" class="mt-0.5 h-4 w-4 shrink-0 text-sky-400" />
91
+ <UIcon name="i-lucide-boxes" class="mt-0.5 h-4 w-4 shrink-0 text-app-info-400" />
92
92
  <div class="min-w-0 flex-1">
93
- <p class="truncate text-sm font-medium text-slate-100">
93
+ <p class="truncate text-sm font-medium text-app-100">
94
94
  {{ s.name }}
95
- <code class="ms-1 text-[11px] text-slate-500">{{ s.id }}</code>
95
+ <code class="ms-1 text-[11px] text-dimmed">{{ s.id }}</code>
96
96
  </p>
97
- <p class="text-xs text-slate-400">{{ s.summary }}</p>
97
+ <p class="text-xs text-muted">{{ s.summary }}</p>
98
98
  <div v-if="s.capabilities.length" class="mt-1 flex flex-wrap gap-1">
99
99
  <UBadge v-for="c in s.capabilities" :key="c" size="xs" variant="subtle" color="neutral">
100
100
  {{ c }}
@@ -122,13 +122,13 @@ async function suppress(serviceId: string) {
122
122
  <div
123
123
  v-for="doc in catalog.contractBodies[s.id] ?? []"
124
124
  :key="doc.contractId"
125
- class="rounded-md border border-slate-800 bg-slate-950/60 p-2"
125
+ class="rounded-md border border-default bg-app-950/60 p-2"
126
126
  >
127
- <p class="mb-1 text-[11px] text-slate-400">
127
+ <p class="mb-1 text-[11px] text-muted">
128
128
  {{ doc.title }}
129
- <span v-if="doc.path" class="ms-1 font-mono text-slate-600">{{ doc.path }}</span>
129
+ <span v-if="doc.path" class="ms-1 font-mono text-app-600">{{ doc.path }}</span>
130
130
  </p>
131
- <pre class="max-h-64 overflow-auto text-[11px] text-slate-300">{{ doc.body }}</pre>
131
+ <pre class="max-h-64 overflow-auto text-[11px] text-toned">{{ doc.body }}</pre>
132
132
  </div>
133
133
  </div>
134
134
  </div>
@@ -153,7 +153,7 @@ async function suppress(serviceId: string) {
153
153
  </div>
154
154
  </div>
155
155
 
156
- <p v-if="!catalog.resolved.length" class="text-sm text-slate-500">
156
+ <p v-if="!catalog.resolved.length" class="text-sm text-dimmed">
157
157
  {{ t('foundational.catalog.empty') }}
158
158
  </p>
159
159
  </div>
@@ -88,7 +88,7 @@ const activeTab = computed({
88
88
  forms that would fail with a raw 503. -->
89
89
  <div
90
90
  v-if="catalog.available === false"
91
- class="rounded-md border border-slate-800 bg-slate-900/40 p-3 text-sm text-slate-400"
91
+ class="rounded-md border border-default bg-default/40 p-3 text-sm text-muted"
92
92
  >
93
93
  {{ t('foundational.unavailable') }}
94
94
  </div>
@@ -182,23 +182,23 @@ async function remove(service: FoundationalService) {
182
182
  <div
183
183
  v-for="s in catalog.services"
184
184
  :key="s.id"
185
- class="rounded-md border border-slate-800 bg-slate-900/60 p-3"
185
+ class="rounded-md border border-default bg-default/60 p-3"
186
186
  >
187
187
  <div class="flex items-start gap-2">
188
- <UIcon name="i-lucide-boxes" class="mt-0.5 h-4 w-4 shrink-0 text-sky-400" />
188
+ <UIcon name="i-lucide-boxes" class="mt-0.5 h-4 w-4 shrink-0 text-app-info-400" />
189
189
  <div class="min-w-0 flex-1">
190
- <p class="truncate text-sm font-medium text-slate-100">
190
+ <p class="truncate text-sm font-medium text-app-100">
191
191
  {{ s.name }}
192
- <code class="ms-1 text-[11px] text-slate-500">{{ s.id }}</code>
192
+ <code class="ms-1 text-[11px] text-dimmed">{{ s.id }}</code>
193
193
  </p>
194
- <p class="text-xs text-slate-400">{{ s.summary }}</p>
194
+ <p class="text-xs text-muted">{{ s.summary }}</p>
195
195
  <div v-if="s.capabilities.length" class="mt-1 flex flex-wrap gap-1">
196
196
  <UBadge v-for="c in s.capabilities" :key="c" size="xs" variant="subtle" color="neutral">
197
197
  {{ c }}
198
198
  </UBadge>
199
199
  </div>
200
200
  <FoundationalContractSummary :contracts="s.contracts" :format-label="formatLabel" />
201
- <p v-if="s.sourceId" class="mt-1 text-[11px] text-slate-500">
201
+ <p v-if="s.sourceId" class="mt-1 text-[11px] text-dimmed">
202
202
  {{ t('foundational.registry.fromSource', { path: s.sourcePath ?? '' }) }}
203
203
  </p>
204
204
  </div>
@@ -222,7 +222,7 @@ async function remove(service: FoundationalService) {
222
222
  </div>
223
223
  </div>
224
224
  </div>
225
- <p v-if="!catalog.services.length" class="text-sm text-slate-500">
225
+ <p v-if="!catalog.services.length" class="text-sm text-dimmed">
226
226
  {{ t('foundational.registry.empty') }}
227
227
  </p>
228
228
 
@@ -238,7 +238,7 @@ async function remove(service: FoundationalService) {
238
238
  {{ t('foundational.registry.add') }}
239
239
  </UButton>
240
240
 
241
- <div v-else class="rounded-md border border-slate-800 p-3">
241
+ <div v-else class="rounded-md border border-default p-3">
242
242
  <p class="mb-2 text-sm font-medium">
243
243
  {{
244
244
  isCreating ? t('foundational.registry.addTitle') : t('foundational.registry.editTitle')
@@ -251,8 +251,8 @@ async function remove(service: FoundationalService) {
251
251
  v-model="draft.id"
252
252
  :placeholder="t('foundational.registry.idPlaceholder')"
253
253
  />
254
- <p v-else class="text-xs text-slate-500">
255
- <code class="text-slate-300">{{ draft.id }}</code>
254
+ <p v-else class="text-xs text-dimmed">
255
+ <code class="text-toned">{{ draft.id }}</code>
256
256
  — {{ t('foundational.registry.idFixed') }}
257
257
  </p>
258
258
  <UInput v-model="draft.name" :placeholder="t('foundational.registry.namePlaceholder')" />
@@ -270,11 +270,11 @@ async function remove(service: FoundationalService) {
270
270
  :placeholder="t('foundational.registry.capabilitiesPlaceholder')"
271
271
  />
272
272
 
273
- <div class="rounded-md border border-slate-800 p-2">
274
- <p class="text-xs font-medium text-slate-300">
273
+ <div class="rounded-md border border-default p-2">
274
+ <p class="text-xs font-medium text-toned">
275
275
  {{ t('foundational.registry.contractsTitle') }}
276
276
  </p>
277
- <p class="mb-2 text-[11px] text-slate-500">
277
+ <p class="mb-2 text-[11px] text-dimmed">
278
278
  {{
279
279
  draft.contractsTouched
280
280
  ? t('foundational.registry.contractsReplace')
@@ -245,14 +245,14 @@ async function unlink(id: string) {
245
245
  <div
246
246
  v-for="s in catalog.sources"
247
247
  :key="s.id"
248
- class="flex items-center gap-2 rounded-md border border-slate-800 bg-slate-900/60 p-3"
248
+ class="flex items-center gap-2 rounded-md border border-default bg-default/60 p-3"
249
249
  >
250
- <UIcon name="i-lucide-git-branch" class="h-4 w-4 shrink-0 text-slate-400" />
250
+ <UIcon name="i-lucide-git-branch" class="h-4 w-4 shrink-0 text-muted" />
251
251
  <div class="min-w-0">
252
- <span class="font-mono text-sm text-slate-100">
253
- {{ s.repoOwner }}/{{ s.repoName }}<span class="text-slate-500">/{{ s.dirPath }}</span>
252
+ <span class="font-mono text-sm text-app-100">
253
+ {{ s.repoOwner }}/{{ s.repoName }}<span class="text-dimmed">/{{ s.dirPath }}</span>
254
254
  </span>
255
- <p class="text-xs text-slate-500">
255
+ <p class="text-xs text-dimmed">
256
256
  <template v-if="s.mode === 'files'">
257
257
  {{
258
258
  t('foundational.sources.metaFiles', {
@@ -274,7 +274,7 @@ async function unlink(id: string) {
274
274
  </template>
275
275
  <template v-else>{{ t('foundational.sources.metaDirectory') }}</template>
276
276
  </p>
277
- <p class="text-xs text-slate-500">
277
+ <p class="text-xs text-dimmed">
278
278
  {{
279
279
  s.lastSyncedAt
280
280
  ? t('foundational.sources.metaSynced', {
@@ -322,29 +322,29 @@ async function unlink(id: string) {
322
322
  />
323
323
  </div>
324
324
  </div>
325
- <p v-if="!catalog.sources.length" class="text-sm text-slate-500">
325
+ <p v-if="!catalog.sources.length" class="text-sm text-dimmed">
326
326
  {{ t('foundational.sources.empty') }}
327
327
  </p>
328
328
 
329
329
  <!-- Linking needs the GitHub integration; say so rather than offering a form that 503s. -->
330
330
  <div
331
331
  v-if="!catalog.sourcesAvailable"
332
- class="rounded-md border border-slate-800 bg-slate-900/40 p-3 text-sm text-slate-500"
332
+ class="rounded-md border border-default bg-default/40 p-3 text-sm text-dimmed"
333
333
  >
334
334
  {{ t('foundational.sources.githubRequired') }}
335
335
  </div>
336
- <div v-else class="rounded-md border border-slate-800 p-3">
336
+ <div v-else class="rounded-md border border-default p-3">
337
337
  <p class="mb-2 text-sm font-medium">{{ t('foundational.sources.linkTitle') }}</p>
338
338
  <div class="flex flex-col gap-2">
339
339
  <URadioGroup v-model="mode" :items="modeItems" orientation="horizontal" size="sm" />
340
- <p class="text-xs text-slate-500">{{ modeHints[mode] }}</p>
340
+ <p class="text-xs text-dimmed">{{ modeHints[mode] }}</p>
341
341
 
342
342
  <!-- Connected: search a repo, then browse to the folder / pick the contract files -->
343
343
  <template v-if="githubReady">
344
344
  <GitHubRepoSearchSelect v-model="repoId" @update:repo="repo = $event" />
345
345
  <div
346
346
  v-if="repoId !== undefined"
347
- class="rounded-md border border-slate-800 bg-slate-900/40 p-2"
347
+ class="rounded-md border border-default bg-default/40 p-2"
348
348
  >
349
349
  <RepoTreeBrowser
350
350
  v-if="mode === 'files'"
@@ -355,13 +355,13 @@ async function unlink(id: string) {
355
355
  @toggle="toggleFile"
356
356
  />
357
357
  <RepoTreeBrowser v-else v-model="dirPath" :repo-github-id="repoId" mode="dir" />
358
- <p class="mt-2 truncate text-xs text-slate-400">
358
+ <p class="mt-2 truncate text-xs text-muted">
359
359
  <template v-if="mode === 'files'">
360
360
  {{ t('foundational.sources.selectedFiles', { count: filePaths.length }) }}
361
361
  </template>
362
362
  <template v-else-if="dirPath">
363
363
  {{ t('foundational.sources.selectedDir') }}
364
- <code class="text-slate-200">{{ dirPath }}</code>
364
+ <code class="text-default">{{ dirPath }}</code>
365
365
  </template>
366
366
  <template v-else>{{ t('foundational.sources.wholeRepo') }}</template>
367
367
  </p>