@cat-factory/app 0.307.1 → 0.309.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 (255) hide show
  1. package/README.md +21 -0
  2. package/app/assets/css/main.css +22 -0
  3. package/app/assets/css/prose.css +4 -4
  4. package/app/assets/css/type.css +24 -0
  5. package/app/components/assistant/AssistantModal.vue +3 -2
  6. package/app/components/auth/UserMenu.vue +1 -1
  7. package/app/components/binaryCandidates/BinaryCandidatesWindow.vue +15 -15
  8. package/app/components/binaryOutput/BinaryOutputReport.vue +10 -14
  9. package/app/components/binaryOutput/StoredAssetView.vue +5 -5
  10. package/app/components/board/AddTaskModal.vue +16 -14
  11. package/app/components/board/AgentFailureCard.vue +9 -9
  12. package/app/components/board/AgentFailureHistory.vue +1 -1
  13. package/app/components/board/CreateInitiativeModal.vue +2 -2
  14. package/app/components/board/FailureDetail.vue +1 -1
  15. package/app/components/board/FailureHistoryList.vue +5 -5
  16. package/app/components/board/RecurringPipelineModal.vue +12 -11
  17. package/app/components/board/ReviewFrictionDialog.vue +4 -3
  18. package/app/components/board/StepExecutionHistory.vue +8 -8
  19. package/app/components/board/nodes/AgentChip.vue +1 -1
  20. package/app/components/board/nodes/BlockNode.vue +8 -9
  21. package/app/components/board/nodes/EpicNode.vue +4 -4
  22. package/app/components/board/nodes/FrameSwimlanes.vue +4 -7
  23. package/app/components/board/nodes/InitiativeCard.vue +4 -4
  24. package/app/components/board/nodes/LaneGroup.vue +3 -5
  25. package/app/components/board/nodes/TaskCard.vue +8 -8
  26. package/app/components/board/nodes/TaskLane.vue +3 -3
  27. package/app/components/board/nodes/TaskPipelineMini.vue +13 -12
  28. package/app/components/bootstrap/AdoptionReviewModal.vue +7 -6
  29. package/app/components/bootstrap/BootstrapModal.vue +11 -10
  30. package/app/components/bootstrap/BootstrapRunSteps.vue +1 -1
  31. package/app/components/brainstorm/BrainstormWindow.vue +8 -7
  32. package/app/components/bugFishing/BugFishingWindow.vue +37 -36
  33. package/app/components/clarity/ClarityReviewWindow.vue +8 -7
  34. package/app/components/common/AsyncViewError.vue +1 -1
  35. package/app/components/common/ClarificationItem.vue +6 -6
  36. package/app/components/common/DescriptorFields.vue +1 -1
  37. package/app/components/common/EmptyState.vue +1 -1
  38. package/app/components/common/InterviewGateNotice.vue +4 -4
  39. package/app/components/common/MarkdownProse.vue +8 -2
  40. package/app/components/common/SectionLabel.vue +38 -0
  41. package/app/components/consensus/ConsensusSessionWindow.vue +10 -9
  42. package/app/components/context/ContextAttachmentFields.vue +9 -8
  43. package/app/components/docs/DocInterviewWindow.vue +10 -9
  44. package/app/components/documents/ContextDocumentPicker.vue +10 -12
  45. package/app/components/documents/DocumentImportModal.vue +3 -2
  46. package/app/components/documents/DocumentSourceConnectModal.vue +2 -2
  47. package/app/components/documents/DocumentSyncState.vue +1 -1
  48. package/app/components/documents/DocumentTemplatesModal.vue +5 -4
  49. package/app/components/documents/RepoContextDocPicker.vue +3 -6
  50. package/app/components/documents/StartFromDesignModal.vue +4 -4
  51. package/app/components/documents/TaskContextDocs.vue +1 -1
  52. package/app/components/environments/EnvSetupStepper.vue +3 -3
  53. package/app/components/environments/EnvironmentStatusPanel.vue +11 -10
  54. package/app/components/environments/steps/EnvPreflightStep.vue +8 -8
  55. package/app/components/environments/steps/EnvReviewStep.vue +23 -22
  56. package/app/components/environments/steps/EnvSaveStep.vue +5 -5
  57. package/app/components/focus/BlockFocusView.vue +11 -10
  58. package/app/components/followUp/FollowUpWindow.vue +10 -10
  59. package/app/components/forkDecision/ForkDecisionWindow.vue +23 -26
  60. package/app/components/foundational/FoundationalContractSummary.vue +2 -2
  61. package/app/components/foundational/FoundationalServiceCatalogList.vue +3 -3
  62. package/app/components/foundational/FoundationalServiceRegistry.vue +3 -3
  63. package/app/components/foundational/FoundationalSuppressions.vue +2 -2
  64. package/app/components/fragments/FragmentLibraryManager.vue +3 -3
  65. package/app/components/fragments/FragmentSelector.vue +10 -11
  66. package/app/components/gates/GateFailingCheckList.vue +3 -3
  67. package/app/components/gates/GateResultView.vue +39 -38
  68. package/app/components/github/AddServiceFromRepoModal.vue +5 -4
  69. package/app/components/github/BranchProtectionPreflight.vue +5 -5
  70. package/app/components/github/GitHubConnect.vue +5 -3
  71. package/app/components/github/GitHubPanel.vue +14 -13
  72. package/app/components/github/RepoTreeBrowser.vue +1 -1
  73. package/app/components/humanTest/HumanTestWindow.vue +18 -17
  74. package/app/components/initiative/InitiativePlanNotice.vue +3 -3
  75. package/app/components/initiative/InitiativePlanReview.vue +19 -21
  76. package/app/components/initiative/InitiativePlanningWindow.vue +5 -5
  77. package/app/components/initiative/InitiativeTrackerWindow.vue +54 -53
  78. package/app/components/judge/JudgeResultView.vue +24 -25
  79. package/app/components/kaizen/KaizenPanel.vue +4 -4
  80. package/app/components/kaizen/KaizenStepStatus.vue +7 -6
  81. package/app/components/layout/AccountAuditLog.vue +1 -1
  82. package/app/components/layout/AccountDeploymentSettings.vue +10 -10
  83. package/app/components/layout/AccountFailureKindRules.vue +13 -13
  84. package/app/components/layout/AccountFoundationalSettings.vue +1 -1
  85. package/app/components/layout/AccountFragmentSettings.vue +1 -1
  86. package/app/components/layout/AccountModelPolicySettings.vue +7 -7
  87. package/app/components/layout/AccountPlatformAlertSettings.vue +8 -8
  88. package/app/components/layout/AccountRiskPolicySettings.vue +2 -2
  89. package/app/components/layout/AccountRunCredentialSettings.vue +3 -3
  90. package/app/components/layout/AccountSkillSettings.vue +1 -1
  91. package/app/components/layout/AccountTeamSettings.vue +4 -0
  92. package/app/components/layout/AiProvidersBanner.vue +1 -1
  93. package/app/components/layout/AppearanceSwitcher.vue +1 -1
  94. package/app/components/layout/BoardSwitcher.vue +3 -2
  95. package/app/components/layout/BoardToolbar.vue +6 -2
  96. package/app/components/layout/CommandBar.vue +4 -2
  97. package/app/components/layout/DefaultTestEnvBanner.vue +2 -2
  98. package/app/components/layout/IntegrationsHub.vue +4 -3
  99. package/app/components/layout/LanguageSwitcher.vue +1 -1
  100. package/app/components/layout/ModelProvidersHub.vue +6 -4
  101. package/app/components/layout/NotificationsInbox.vue +8 -7
  102. package/app/components/layout/PersonalSetupModal.vue +5 -3
  103. package/app/components/layout/RolePrompt.vue +1 -1
  104. package/app/components/layout/SideBar.vue +3 -5
  105. package/app/components/layout/SpendWarningBanner.vue +3 -3
  106. package/app/components/layout/TranslationWarningBanner.vue +1 -1
  107. package/app/components/layout/UiModeSwitcher.vue +7 -6
  108. package/app/components/layout/UiRoleSwitcher.vue +2 -2
  109. package/app/components/media/ArtifactLightbox.vue +6 -6
  110. package/app/components/media/ImageCompare.vue +16 -16
  111. package/app/components/merge/MergeEffortChips.vue +4 -6
  112. package/app/components/notifications/NotificationSettingsPanel.vue +6 -5
  113. package/app/components/observability/OutcomeFilterChips.vue +1 -1
  114. package/app/components/observability/RunFailureSummary.vue +14 -17
  115. package/app/components/observability/StepMetricsBar.vue +9 -8
  116. package/app/components/observability/StepModelActivity.vue +4 -3
  117. package/app/components/observability/ToolCallList.vue +15 -18
  118. package/app/components/outcome/OutcomeSummaryWindow.vue +43 -42
  119. package/app/components/palettes/AgentPalette.vue +7 -5
  120. package/app/components/palettes/AgentTierSelect.vue +1 -1
  121. package/app/components/palettes/PipelinePurposeSelect.vue +2 -1
  122. package/app/components/panels/AgentStepDetail.vue +27 -30
  123. package/app/components/panels/AttemptEntryHeader.vue +2 -2
  124. package/app/components/panels/DecisionModal.vue +1 -1
  125. package/app/components/panels/GenericStructuredResultView.vue +6 -5
  126. package/app/components/panels/InspectorPanel.vue +15 -13
  127. package/app/components/panels/MergerResultView.vue +10 -9
  128. package/app/components/panels/ObservabilityPanel.vue +66 -76
  129. package/app/components/panels/OperatorDashboardPanel.vue +27 -26
  130. package/app/components/panels/ReportsPanel.vue +26 -25
  131. package/app/components/panels/ReportsSpendBreakdown.vue +2 -2
  132. package/app/components/panels/ResultWindowShell.vue +19 -18
  133. package/app/components/panels/RunDetailLoadState.vue +1 -1
  134. package/app/components/panels/StepContainerStatus.vue +8 -7
  135. package/app/components/panels/StepDelegatedStatus.vue +13 -12
  136. package/app/components/panels/StepEffortReport.vue +12 -17
  137. package/app/components/panels/StepFragmentAdherence.vue +9 -10
  138. package/app/components/panels/StepMetadataCard.vue +41 -43
  139. package/app/components/panels/StepReproductionReport.vue +18 -20
  140. package/app/components/panels/StepRunMeta.vue +27 -26
  141. package/app/components/panels/StepTestReport.vue +16 -15
  142. package/app/components/panels/StepToolServers.vue +7 -8
  143. package/app/components/panels/StepValidationReport.vue +5 -5
  144. package/app/components/panels/inspector/ContainerSummary.vue +4 -4
  145. package/app/components/panels/inspector/DocReferenceRepos.vue +5 -4
  146. package/app/components/panels/inspector/EnvProbeReport.vue +16 -13
  147. package/app/components/panels/inspector/EpicChildren.vue +8 -7
  148. package/app/components/panels/inspector/FrontendBindingsResolved.vue +5 -4
  149. package/app/components/panels/inspector/FrontendConfig.vue +26 -34
  150. package/app/components/panels/inspector/InitiativeInspector.vue +3 -3
  151. package/app/components/panels/inspector/InspectorSection.vue +7 -4
  152. package/app/components/panels/inspector/RecurringScheduleSettings.vue +9 -8
  153. package/app/components/panels/inspector/ServiceConnections.vue +2 -2
  154. package/app/components/panels/inspector/ServiceReleaseHealthConfig.vue +2 -2
  155. package/app/components/panels/inspector/ServiceSelfTests.vue +9 -13
  156. package/app/components/panels/inspector/ServiceTestConfig.vue +41 -45
  157. package/app/components/panels/inspector/ServiceTestSecrets.vue +3 -3
  158. package/app/components/panels/inspector/ServiceTestingContext.vue +2 -2
  159. package/app/components/panels/inspector/ServiceValidationConfig.vue +2 -2
  160. package/app/components/panels/inspector/TaskAgentConfig.vue +2 -2
  161. package/app/components/panels/inspector/TaskAprioriBranches.vue +6 -5
  162. package/app/components/panels/inspector/TaskDependencies.vue +1 -1
  163. package/app/components/panels/inspector/TaskEstimateBadge.vue +3 -7
  164. package/app/components/panels/inspector/TaskExecution.vue +13 -12
  165. package/app/components/panels/inspector/TaskRunSettings.vue +35 -38
  166. package/app/components/panels/inspector/TaskStructure.vue +5 -4
  167. package/app/components/pipeline/AgentPromptEditor.vue +15 -14
  168. package/app/components/pipeline/BinaryOutputStepPicker.vue +42 -52
  169. package/app/components/pipeline/EstimateThresholdFields.vue +2 -2
  170. package/app/components/pipeline/GateConfigFields.vue +6 -6
  171. package/app/components/pipeline/IterationCapPrompt.vue +1 -1
  172. package/app/components/pipeline/PipelineBuilder.vue +28 -27
  173. package/app/components/pipeline/PipelineHealthModal.vue +7 -7
  174. package/app/components/pipeline/PipelinePicker.vue +3 -3
  175. package/app/components/pipeline/PipelinePreview.vue +6 -7
  176. package/app/components/pipeline/PipelineProgress.vue +23 -24
  177. package/app/components/prReview/PrReviewWindow.vue +42 -41
  178. package/app/components/providers/AiPresetMismatchDialog.vue +4 -3
  179. package/app/components/providers/AiProviderOnboardingModal.vue +2 -2
  180. package/app/components/providers/ApiKeysSection.vue +7 -6
  181. package/app/components/providers/PersonalSubscriptionSection.vue +4 -3
  182. package/app/components/providers/VendorCredentialsModal.vue +5 -4
  183. package/app/components/provisioning/ProvisioningLogsDrawer.vue +10 -9
  184. package/app/components/ralph/RalphLoopResultView.vue +25 -26
  185. package/app/components/requirements/RequirementsReviewWindow.vue +13 -12
  186. package/app/components/riskPolicy/RiskPolicyPicker.vue +5 -5
  187. package/app/components/riskPolicy/RiskPolicyPreview.vue +16 -15
  188. package/app/components/sandbox/SandboxPanel.vue +21 -20
  189. package/app/components/settings/ApiTokensPanel.vue +1 -1
  190. package/app/components/settings/BudgetSettings.vue +18 -17
  191. package/app/components/settings/CapabilityCredentialsPanel.vue +5 -5
  192. package/app/components/settings/CloudflareHandlerSection.vue +16 -16
  193. package/app/components/settings/ComposeEnvironmentSetupSection.vue +14 -12
  194. package/app/components/settings/ConnectionTestVerdict.vue +1 -1
  195. package/app/components/settings/ConsensusGroupsSection.vue +21 -20
  196. package/app/components/settings/CustomManifestTypeEditor.vue +8 -7
  197. package/app/components/settings/DefaultProvisionTypeSection.vue +5 -5
  198. package/app/components/settings/InfraHandlersConfigurator.vue +14 -15
  199. package/app/components/settings/InfrastructureBackendPicker.vue +2 -2
  200. package/app/components/settings/IssueTrackerPanel.vue +9 -15
  201. package/app/components/settings/KubernetesEngineForm.vue +9 -8
  202. package/app/components/settings/KubernetesEnvironmentForm.vue +4 -3
  203. package/app/components/settings/LocalContainerPoolSettings.vue +2 -2
  204. package/app/components/settings/LocalModelEndpointsPanel.vue +10 -9
  205. package/app/components/settings/MergeClassRulesEditor.vue +6 -5
  206. package/app/components/settings/MergeRolePolicyEditor.vue +13 -12
  207. package/app/components/settings/ModelConfigurationPanel.vue +8 -11
  208. package/app/components/settings/ModelPresetHealthModal.vue +3 -3
  209. package/app/components/settings/ObservabilityConnectionPanel.vue +1 -1
  210. package/app/components/settings/OpenRouterCatalogPanel.vue +6 -5
  211. package/app/components/settings/PackageRegistriesPanel.vue +4 -4
  212. package/app/components/settings/ProviderConnectionTab.vue +5 -4
  213. package/app/components/settings/ProviderManifestEditor.vue +9 -8
  214. package/app/components/settings/ProviderPreferenceEditor.vue +8 -7
  215. package/app/components/settings/RiskPolicyCreateForm.vue +40 -26
  216. package/app/components/settings/RiskPolicyEditorRow.vue +18 -17
  217. package/app/components/settings/RiskPolicyHealthModal.vue +3 -3
  218. package/app/components/settings/RiskPolicyPanel.vue +11 -13
  219. package/app/components/settings/ServiceFragmentDefaultsPanel.vue +5 -4
  220. package/app/components/settings/SharedStacksPanel.vue +5 -5
  221. package/app/components/settings/TaskSourceCard.vue +2 -2
  222. package/app/components/settings/TaskTypeSuppressionsPanel.vue +4 -4
  223. package/app/components/settings/ToolServerChecklist.vue +22 -22
  224. package/app/components/settings/UsageSettings.vue +13 -13
  225. package/app/components/settings/UserSecretsSection.vue +4 -3
  226. package/app/components/settings/WorkspaceMetadataSettings.vue +6 -5
  227. package/app/components/settings/WorkspaceSettingsPanel.vue +72 -58
  228. package/app/components/skills/ReviewSkillQueue.vue +8 -7
  229. package/app/components/skills/SkillLibraryManager.vue +2 -2
  230. package/app/components/slack/SlackPanel.vue +8 -7
  231. package/app/components/spec/ServiceSpecWindow.vue +15 -16
  232. package/app/components/tasks/BugHuntModal.vue +1 -1
  233. package/app/components/tasks/ContextIssuePicker.vue +4 -6
  234. package/app/components/tasks/TaskContextIssues.vue +1 -1
  235. package/app/components/tasks/TaskImportModal.vue +3 -2
  236. package/app/components/tasks/TaskSourceConnectModal.vue +5 -5
  237. package/app/components/testing/TestReportWindow.vue +54 -53
  238. package/app/components/tutorial/TutorialNudge.vue +3 -2
  239. package/app/components/tutorial/TutorialOverlay.vue +3 -2
  240. package/app/components/vcs/GitLabConnect.vue +1 -1
  241. package/app/components/visualConfirm/VisualConfirmationWindow.vue +23 -25
  242. package/app/composables/usePipelineErrorToast.ts +2 -0
  243. package/app/utils/catalog.ts +8 -0
  244. package/app/utils/theme/builtins.ts +7 -1
  245. package/i18n/locales/de.json +6 -3
  246. package/i18n/locales/en.json +6 -3
  247. package/i18n/locales/es.json +6 -3
  248. package/i18n/locales/fr.json +6 -3
  249. package/i18n/locales/he.json +6 -3
  250. package/i18n/locales/it.json +6 -3
  251. package/i18n/locales/ja.json +6 -3
  252. package/i18n/locales/pl.json +6 -3
  253. package/i18n/locales/tr.json +6 -3
  254. package/i18n/locales/uk.json +6 -3
  255. package/package.json +2 -2
@@ -188,17 +188,17 @@ async function stop(mode: EnvironmentTestMode) {
188
188
  <div class="mt-3 space-y-3 border-t border-default pt-3" data-testid="env-test-section">
189
189
  <!-- The precondition both self-tests share, stated once at the top: with no provision type
190
190
  there is no environment to stand up and therefore nothing for an agent to drive either. -->
191
- <p v-if="!canTest" class="text-[11px] text-dimmed">
191
+ <p v-if="!canTest" class="text-2xs text-dimmed">
192
192
  {{ t('inspector.testConfig.envTest.infraless') }}
193
193
  </p>
194
194
 
195
195
  <!-- 1. The provisioning self-test: the whole lifecycle against a throwaway branch. -->
196
196
  <div class="flex items-center justify-between gap-2">
197
197
  <div class="min-w-0">
198
- <p class="text-[11px] font-medium text-toned">
198
+ <p class="text-2xs font-medium text-toned">
199
199
  {{ t('inspector.testConfig.envTest.title') }}
200
200
  </p>
201
- <p class="text-[11px] text-muted">{{ t('inspector.testConfig.envTest.hint') }}</p>
201
+ <p class="text-2xs text-muted">{{ t('inspector.testConfig.envTest.hint') }}</p>
202
202
  </div>
203
203
  <UButton
204
204
  v-if="!isRunning('provision')"
@@ -228,7 +228,7 @@ async function stop(mode: EnvironmentTestMode) {
228
228
 
229
229
  <p
230
230
  v-if="provisionRun"
231
- class="text-[11px]"
231
+ class="text-2xs"
232
232
  :class="{
233
233
  'text-app-info-300/80': provisionRun.status === 'running',
234
234
  'text-app-success-300/80': provisionRun.status === 'succeeded',
@@ -253,11 +253,7 @@ async function stop(mode: EnvironmentTestMode) {
253
253
  </template>
254
254
  </p>
255
255
 
256
- <div
257
- v-if="errors.provision"
258
- class="text-[11px] text-app-error-400"
259
- data-testid="env-test-error"
260
- >
256
+ <div v-if="errors.provision" class="text-2xs text-app-error-400" data-testid="env-test-error">
261
257
  <p>{{ errors.provision.text }}</p>
262
258
  <!-- Only the not-provisionable handler case is one-click fixable: jump to Infrastructure →
263
259
  Test environments, where the workspace's per-type environment handler is registered. -->
@@ -279,10 +275,10 @@ async function stop(mode: EnvironmentTestMode) {
279
275
  and could not do with the environment it was handed. -->
280
276
  <div class="flex items-center justify-between gap-2 border-t border-default pt-3">
281
277
  <div class="min-w-0">
282
- <p class="text-[11px] font-medium text-toned">
278
+ <p class="text-2xs font-medium text-toned">
283
279
  {{ t('inspector.testConfig.envProbe.title') }}
284
280
  </p>
285
- <p class="text-[11px] text-muted">
281
+ <p class="text-2xs text-muted">
286
282
  {{ t('inspector.testConfig.envProbe.hint') }}
287
283
  {{
288
284
  probeSurface === 'ui'
@@ -319,7 +315,7 @@ async function stop(mode: EnvironmentTestMode) {
319
315
 
320
316
  <p
321
317
  v-if="probeRun"
322
- class="text-[11px]"
318
+ class="text-2xs"
323
319
  :class="{
324
320
  'text-app-info-300/80': probeRun.status === 'running',
325
321
  'text-app-success-300/80': probeRun.status === 'succeeded',
@@ -355,7 +351,7 @@ async function stop(mode: EnvironmentTestMode) {
355
351
 
356
352
  <div
357
353
  v-if="errors['agent-probe']"
358
- class="text-[11px] text-app-error-400"
354
+ class="text-2xs text-app-error-400"
359
355
  data-testid="env-probe-error"
360
356
  >
361
357
  <p>{{ errors['agent-probe']!.text }}</p>
@@ -429,7 +429,7 @@ function setSize(value: InstanceSize) {
429
429
  :default-open="props.defaultOpen"
430
430
  >
431
431
  <div class="space-y-1">
432
- <span class="text-[11px] text-muted">{{ t('inspector.testConfig.provisionType') }}</span>
432
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.provisionType') }}</span>
433
433
  <div class="flex flex-wrap gap-1">
434
434
  <UButton
435
435
  v-for="p in PROVISION_TYPES"
@@ -442,7 +442,7 @@ function setSize(value: InstanceSize) {
442
442
  {{ p.label }}
443
443
  </UButton>
444
444
  </div>
445
- <p class="text-[11px] leading-snug text-dimmed">
445
+ <p class="text-2xs leading-snug text-dimmed">
446
446
  {{ t('inspector.testConfig.provisionTypeHint') }}
447
447
  </p>
448
448
  </div>
@@ -452,14 +452,14 @@ function setSize(value: InstanceSize) {
452
452
  provisions the compose stack, rather than editing the raw path inline. -->
453
453
  <div
454
454
  v-if="provisionType === 'docker-compose'"
455
- class="flex items-center justify-between gap-2 rounded border border-primary/40 bg-primary/10 p-2"
455
+ class="flex items-center justify-between gap-2 rounded-sm border border-primary/40 bg-primary/10 p-2"
456
456
  data-testid="env-setup-nudge"
457
457
  >
458
458
  <div class="min-w-0">
459
- <p class="text-[11px] font-medium text-primary/90">
459
+ <p class="text-2xs font-medium text-primary/90">
460
460
  {{ t('inspector.testConfig.envWizard.title') }}
461
461
  </p>
462
- <p class="text-[11px] leading-snug text-dimmed">
462
+ <p class="text-2xs leading-snug text-dimmed">
463
463
  {{ t('inspector.testConfig.envWizard.hint') }}
464
464
  </p>
465
465
  </div>
@@ -477,9 +477,9 @@ function setSize(value: InstanceSize) {
477
477
 
478
478
  <!-- Auto-detect a recommended provisioning config from the repo (slice 11). Non-binding:
479
479
  it prefills the form below + the kube edit refs; the user confirms/edits everything. -->
480
- <div v-if="repoContext" class="space-y-2 rounded border border-default bg-default/40 p-2">
480
+ <div v-if="repoContext" class="space-y-2 rounded-sm border border-default bg-default/40 p-2">
481
481
  <div class="flex items-center justify-between gap-2">
482
- <span class="text-[11px] text-muted">{{ t('inspector.testConfig.detect.title') }}</span>
482
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.detect.title') }}</span>
483
483
  <UButton
484
484
  size="xs"
485
485
  variant="soft"
@@ -491,23 +491,23 @@ function setSize(value: InstanceSize) {
491
491
  {{ t('inspector.testConfig.detect.button') }}
492
492
  </UButton>
493
493
  </div>
494
- <p class="text-[11px] leading-snug text-dimmed">
494
+ <p class="text-2xs leading-snug text-dimmed">
495
495
  {{ t('inspector.testConfig.detect.hint') }}
496
496
  </p>
497
497
 
498
- <p v-if="detectError" class="text-[11px] text-app-error-300/80">
498
+ <p v-if="detectError" class="text-2xs text-app-error-300/80">
499
499
  {{ detectError }}
500
500
  </p>
501
501
 
502
502
  <template v-if="detectResult && !detecting">
503
503
  <p
504
504
  v-if="!detectResult.detected && detectResult.provisioning.type !== 'custom'"
505
- class="text-[11px] text-app-warning-300/80"
505
+ class="text-2xs text-app-warning-300/80"
506
506
  >
507
507
  {{ t('inspector.testConfig.detect.none') }}
508
508
  </p>
509
509
  <template v-else>
510
- <p class="text-[11px] text-app-success-300/80">
510
+ <p class="text-2xs text-app-success-300/80">
511
511
  {{
512
512
  t('inspector.testConfig.detect.applied', {
513
513
  type: provisionTypeLabel(detectResult.provisioning.type),
@@ -516,7 +516,7 @@ function setSize(value: InstanceSize) {
516
516
  </p>
517
517
 
518
518
  <div v-if="detectResult.serviceDirCandidates?.length" class="space-y-1">
519
- <span class="text-[11px] text-muted">{{
519
+ <span class="text-2xs text-muted">{{
520
520
  t('inspector.testConfig.detect.serviceDirTitle')
521
521
  }}</span>
522
522
  <div class="flex flex-wrap gap-1">
@@ -534,7 +534,7 @@ function setSize(value: InstanceSize) {
534
534
  </div>
535
535
 
536
536
  <div v-if="detectResult.manifestRootCandidates?.length" class="space-y-1">
537
- <span class="text-[11px] text-muted">{{
537
+ <span class="text-2xs text-muted">{{
538
538
  t('inspector.testConfig.detect.manifestRootTitle')
539
539
  }}</span>
540
540
  <div class="flex flex-wrap gap-1">
@@ -552,7 +552,7 @@ function setSize(value: InstanceSize) {
552
552
  </div>
553
553
 
554
554
  <div v-if="detectResult.overlayCandidates?.length" class="space-y-1">
555
- <span class="text-[11px] text-muted">{{
555
+ <span class="text-2xs text-muted">{{
556
556
  t('inspector.testConfig.detect.overlayTitle')
557
557
  }}</span>
558
558
  <div class="flex flex-wrap gap-1">
@@ -570,7 +570,7 @@ function setSize(value: InstanceSize) {
570
570
  </div>
571
571
 
572
572
  <div v-if="detectResult.composeServiceCandidates?.length" class="space-y-1">
573
- <span class="text-[11px] text-muted">{{
573
+ <span class="text-2xs text-muted">{{
574
574
  t('inspector.testConfig.detect.composeServiceTitle')
575
575
  }}</span>
576
576
  <div class="flex flex-wrap gap-1">
@@ -587,12 +587,12 @@ function setSize(value: InstanceSize) {
587
587
  </div>
588
588
  </div>
589
589
 
590
- <p v-if="detectResult.urlSource" class="text-[11px] text-dimmed">
590
+ <p v-if="detectResult.urlSource" class="text-2xs text-dimmed">
591
591
  {{
592
592
  t('inspector.testConfig.detect.urlSource', { source: detectResult.urlSource.source })
593
593
  }}
594
594
  </p>
595
- <p v-if="detectResult.namespace" class="text-[11px] text-dimmed">
595
+ <p v-if="detectResult.namespace" class="text-2xs text-dimmed">
596
596
  {{ t('inspector.testConfig.detect.namespace', { namespace: detectResult.namespace }) }}
597
597
  </p>
598
598
 
@@ -600,7 +600,7 @@ function setSize(value: InstanceSize) {
600
600
  <li
601
601
  v-for="(n, i) in detectResult.notes"
602
602
  :key="i"
603
- class="flex items-start gap-1.5 text-[11px] leading-snug text-dimmed"
603
+ class="flex items-start gap-1.5 text-2xs leading-snug text-dimmed"
604
604
  >
605
605
  <span
606
606
  :class="
@@ -622,7 +622,7 @@ function setSize(value: InstanceSize) {
622
622
 
623
623
  <div v-if="provisionType === 'docker-compose'" class="space-y-2">
624
624
  <div class="space-y-1">
625
- <label class="text-[11px] text-muted">{{ t('inspector.testConfig.composePath') }}</label>
625
+ <label class="text-2xs text-muted">{{ t('inspector.testConfig.composePath') }}</label>
626
626
  <div class="flex items-center gap-1">
627
627
  <UInput
628
628
  :model-value="composePath"
@@ -644,7 +644,7 @@ function setSize(value: InstanceSize) {
644
644
  @click="openBrowse('compose')"
645
645
  />
646
646
  </div>
647
- <p class="text-[11px] leading-snug text-dimmed">
647
+ <p class="text-2xs leading-snug text-dimmed">
648
648
  {{ t('inspector.testConfig.composeHint') }}
649
649
  </p>
650
650
  </div>
@@ -660,9 +660,7 @@ function setSize(value: InstanceSize) {
660
660
  connection (the "how") is configured per-type in the Infrastructure window. -->
661
661
  <div v-if="provisionType === 'kubernetes'" class="space-y-2">
662
662
  <div class="space-y-1">
663
- <span class="text-[11px] text-muted">{{
664
- t('inspector.testConfig.manifestSourceLabel')
665
- }}</span>
663
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.manifestSourceLabel') }}</span>
666
664
  <div class="flex flex-wrap gap-1">
667
665
  <UButton
668
666
  :color="kubeSourceType === 'colocated' ? 'primary' : 'neutral'"
@@ -684,7 +682,7 @@ function setSize(value: InstanceSize) {
684
682
  </div>
685
683
 
686
684
  <div v-if="kubeSourceType === 'separate'" class="space-y-1">
687
- <label class="text-[11px] text-muted">{{ t('inspector.testConfig.manifestRepo') }}</label>
685
+ <label class="text-2xs text-muted">{{ t('inspector.testConfig.manifestRepo') }}</label>
688
686
  <UInput
689
687
  :model-value="kubeRepo"
690
688
  size="xs"
@@ -695,7 +693,7 @@ function setSize(value: InstanceSize) {
695
693
  />
696
694
  </div>
697
695
  <div v-if="kubeSourceType === 'separate'" class="space-y-1">
698
- <label class="text-[11px] text-muted">{{ t('inspector.testConfig.manifestRef') }}</label>
696
+ <label class="text-2xs text-muted">{{ t('inspector.testConfig.manifestRef') }}</label>
699
697
  <UInput
700
698
  :model-value="kubeRef"
701
699
  size="xs"
@@ -707,7 +705,7 @@ function setSize(value: InstanceSize) {
707
705
  </div>
708
706
 
709
707
  <div class="space-y-1">
710
- <label class="text-[11px] text-muted">{{ t('inspector.testConfig.manifestPath') }}</label>
708
+ <label class="text-2xs text-muted">{{ t('inspector.testConfig.manifestPath') }}</label>
711
709
  <div class="flex items-center gap-1">
712
710
  <UInput
713
711
  :model-value="kubePath"
@@ -727,13 +725,13 @@ function setSize(value: InstanceSize) {
727
725
  @click="openBrowse('k8s')"
728
726
  />
729
727
  </div>
730
- <p class="text-[11px] leading-snug text-dimmed">
728
+ <p class="text-2xs leading-snug text-dimmed">
731
729
  {{ t('inspector.testConfig.manifestPathHint') }}
732
730
  </p>
733
731
  </div>
734
732
 
735
733
  <div class="space-y-1">
736
- <span class="text-[11px] text-muted">{{ t('inspector.testConfig.rendererLabel') }}</span>
734
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.rendererLabel') }}</span>
737
735
  <div class="flex flex-wrap gap-1">
738
736
  <UButton
739
737
  v-for="r in RENDERERS"
@@ -746,7 +744,7 @@ function setSize(value: InstanceSize) {
746
744
  {{ r.label }}
747
745
  </UButton>
748
746
  </div>
749
- <p class="text-[11px] leading-snug text-dimmed">
747
+ <p class="text-2xs leading-snug text-dimmed">
750
748
  {{ t('inspector.testConfig.rendererHint') }}
751
749
  </p>
752
750
  </div>
@@ -756,7 +754,7 @@ function setSize(value: InstanceSize) {
756
754
  source), the per-PR recipe lives in the target repository's own preview workflow, so
757
755
  declaring the type IS the whole service-side configuration. Say so explicitly rather
758
756
  than rendering an empty panel that reads like something failed to load. -->
759
- <p v-if="provisionType === 'cloudflare'" class="text-[11px] text-dimmed">
757
+ <p v-if="provisionType === 'cloudflare'" class="text-2xs text-dimmed">
760
758
  {{ t('inspector.testConfig.cloudflareHint') }}
761
759
  </p>
762
760
 
@@ -764,9 +762,7 @@ function setSize(value: InstanceSize) {
764
762
  handler the workspace configures). -->
765
763
  <div v-if="provisionType === 'custom'" class="space-y-2">
766
764
  <div class="space-y-1">
767
- <label class="text-[11px] text-muted">{{
768
- t('inspector.testConfig.customManifestId')
769
- }}</label>
765
+ <label class="text-2xs text-muted">{{ t('inspector.testConfig.customManifestId') }}</label>
770
766
  <USelect
771
767
  v-if="customTypeItems.length"
772
768
  :model-value="customManifestId"
@@ -776,15 +772,15 @@ function setSize(value: InstanceSize) {
776
772
  :placeholder="t('inspector.testConfig.customManifestIdPlaceholder')"
777
773
  @update:model-value="(v: string) => setCustomManifestId(v)"
778
774
  />
779
- <p v-else class="text-[11px] leading-snug text-app-warning-300/80">
775
+ <p v-else class="text-2xs leading-snug text-app-warning-300/80">
780
776
  {{ t('inspector.testConfig.customNoTypes') }}
781
777
  </p>
782
- <p class="text-[11px] leading-snug text-dimmed">
778
+ <p class="text-2xs leading-snug text-dimmed">
783
779
  {{ t('inspector.testConfig.customManifestIdHint') }}
784
780
  </p>
785
781
  </div>
786
782
  <div class="space-y-1">
787
- <label class="text-[11px] text-muted">{{
783
+ <label class="text-2xs text-muted">{{
788
784
  t('inspector.testConfig.customManifestPath')
789
785
  }}</label>
790
786
  <UInput
@@ -796,7 +792,7 @@ function setSize(value: InstanceSize) {
796
792
  (e: KeyboardEvent) => setCustomManifestPath((e.target as HTMLInputElement).value)
797
793
  "
798
794
  />
799
- <p class="text-[11px] leading-snug text-dimmed">
795
+ <p class="text-2xs leading-snug text-dimmed">
800
796
  {{ t('inspector.testConfig.customManifestPathHint') }}
801
797
  </p>
802
798
  </div>
@@ -805,10 +801,10 @@ function setSize(value: InstanceSize) {
805
801
  shown when the selected type declares a fixer prompt. -->
806
802
  <div
807
803
  v-if="manifestFixerAvailable && repoContext"
808
- class="space-y-1.5 rounded border border-default bg-default/40 p-2"
804
+ class="space-y-1.5 rounded-sm border border-default bg-default/40 p-2"
809
805
  >
810
806
  <div class="flex items-center justify-between gap-2">
811
- <span class="text-[11px] text-muted">{{
807
+ <span class="text-2xs text-muted">{{
812
808
  t('inspector.testConfig.generateManifest.title')
813
809
  }}</span>
814
810
  <UButton
@@ -823,15 +819,15 @@ function setSize(value: InstanceSize) {
823
819
  {{ t('inspector.testConfig.generateManifest.button') }}
824
820
  </UButton>
825
821
  </div>
826
- <p class="text-[11px] leading-snug text-dimmed">
822
+ <p class="text-2xs leading-snug text-dimmed">
827
823
  {{ t('inspector.testConfig.generateManifest.hint') }}
828
824
  </p>
829
- <p v-if="manifestRepairError" class="text-[11px] text-app-error-300/80">
825
+ <p v-if="manifestRepairError" class="text-2xs text-app-error-300/80">
830
826
  {{ t('inspector.testConfig.generateManifest.error') }}
831
827
  </p>
832
828
  <p
833
829
  v-else-if="manifestRepairJob"
834
- class="text-[11px]"
830
+ class="text-2xs"
835
831
  :class="{
836
832
  'text-app-info-300/80': manifestRepairJob.status === 'running',
837
833
  'text-app-success-300/80': manifestRepairJob.status === 'succeeded',
@@ -840,7 +836,7 @@ function setSize(value: InstanceSize) {
840
836
  >
841
837
  {{ t(`inspector.testConfig.generateManifest.status.${manifestRepairJob.status}`) }}
842
838
  </p>
843
- <p v-else-if="manifestRepairJobId" class="text-[11px] text-app-info-300/80">
839
+ <p v-else-if="manifestRepairJobId" class="text-2xs text-app-info-300/80">
844
840
  {{ t('inspector.testConfig.generateManifest.dispatched') }}
845
841
  </p>
846
842
  </div>
@@ -896,7 +892,7 @@ function setSize(value: InstanceSize) {
896
892
  :hint="t('inspector.testConfig.provisioningHint')"
897
893
  >
898
894
  <div class="space-y-1">
899
- <span class="text-[11px] text-muted">{{ t('inspector.testConfig.cloudProvider') }}</span>
895
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.cloudProvider') }}</span>
900
896
  <div class="flex flex-wrap gap-1">
901
897
  <UButton
902
898
  v-for="p in PROVIDERS"
@@ -912,7 +908,7 @@ function setSize(value: InstanceSize) {
912
908
  </div>
913
909
 
914
910
  <div class="space-y-1">
915
- <span class="text-[11px] text-muted">{{ t('inspector.testConfig.instanceSize') }}</span>
911
+ <span class="text-2xs text-muted">{{ t('inspector.testConfig.instanceSize') }}</span>
916
912
  <div class="flex flex-wrap gap-1">
917
913
  <UButton
918
914
  v-for="s in SIZES"
@@ -165,13 +165,13 @@ async function clearAll() {
165
165
 
166
166
  <!-- These are REAL secrets: an unmistakable sensitivity + replace-all warning. -->
167
167
  <div
168
- class="flex items-start gap-2 rounded-md border border-app-warning-500/40 bg-app-warning-500/10 px-2.5 py-2 text-[11px] leading-snug text-app-warning-200"
168
+ class="flex items-start gap-2 rounded-md border border-app-warning-500/40 bg-app-warning-500/10 px-2.5 py-2 text-2xs leading-snug text-app-warning-200"
169
169
  >
170
170
  <UIcon name="i-lucide-shield-alert" class="mt-0.5 h-4 w-4 shrink-0 text-app-warning-400" />
171
171
  <span>{{ t('inspector.testSecrets.warning') }}</span>
172
172
  </div>
173
173
 
174
- <p class="text-[11px] leading-snug text-dimmed">
174
+ <p class="text-2xs leading-snug text-dimmed">
175
175
  {{ t('inspector.testSecrets.replaceNote') }}
176
176
  </p>
177
177
 
@@ -234,7 +234,7 @@ async function clearAll() {
234
234
  </UFormField>
235
235
  </div>
236
236
 
237
- <p v-if="duplicateKeys.size" class="text-[11px] text-app-error-400">
237
+ <p v-if="duplicateKeys.size" class="text-2xs text-app-error-400">
238
238
  {{ t('inspector.testSecrets.duplicateKey') }}
239
239
  </p>
240
240
 
@@ -89,7 +89,7 @@ function revert() {
89
89
  >
90
90
  <!-- This text reaches the model in the prompt, so it must never hold a real secret. -->
91
91
  <div
92
- class="flex items-start gap-2 rounded-md border border-muted bg-elevated/40 px-2.5 py-2 text-[11px] leading-snug text-toned"
92
+ class="flex items-start gap-2 rounded-md border border-muted bg-elevated/40 px-2.5 py-2 text-2xs leading-snug text-toned"
93
93
  >
94
94
  <UIcon name="i-lucide-info" class="mt-0.5 h-4 w-4 shrink-0 text-muted" />
95
95
  <span>{{ t('inspector.testingContext.notSecret') }}</span>
@@ -104,7 +104,7 @@ function revert() {
104
104
  />
105
105
 
106
106
  <div class="flex items-center justify-between gap-2">
107
- <p class="text-[11px] text-dimmed" :class="{ 'text-app-error-400': tooLong }">
107
+ <p class="text-2xs text-dimmed" :class="{ 'text-app-error-400': tooLong }">
108
108
  {{
109
109
  t('inspector.testingContext.length', {
110
110
  count: outgoing.length,
@@ -234,7 +234,7 @@ async function clear() {
234
234
  />
235
235
  </UFormField>
236
236
 
237
- <p class="text-[11px] text-dimmed">
237
+ <p class="text-2xs text-dimmed">
238
238
  {{ t('inspector.validationChecks.hint') }}
239
239
  </p>
240
240
 
@@ -273,7 +273,7 @@ async function clear() {
273
273
  />
274
274
  </div>
275
275
 
276
- <p v-if="rows.length === 0" class="text-[11px] text-dimmed" data-testid="validation-empty">
276
+ <p v-if="rows.length === 0" class="text-2xs text-dimmed" data-testid="validation-empty">
277
277
  {{ t('inspector.validationChecks.empty') }}
278
278
  </p>
279
279
 
@@ -58,7 +58,7 @@ function setValue(id: string, value: string) {
58
58
  >
59
59
  <div v-for="d in descriptors" :key="d.id" class="space-y-1">
60
60
  <div class="flex items-center justify-between">
61
- <span class="text-[11px] text-muted">{{ d.label }}</span>
61
+ <span class="text-2xs text-muted">{{ d.label }}</span>
62
62
  <div class="flex items-center gap-1.5">
63
63
  <UIcon
64
64
  v-if="isFrozen(d.agentKind)"
@@ -81,7 +81,7 @@ function setValue(id: string, value: string) {
81
81
  {{ opt.label }}
82
82
  </UButton>
83
83
  </div>
84
- <p class="text-[11px] leading-snug text-dimmed">{{ d.description }}</p>
84
+ <p class="text-2xs leading-snug text-dimmed">{{ d.description }}</p>
85
85
  </div>
86
86
  </InspectorSection>
87
87
  </template>
@@ -15,6 +15,7 @@
15
15
  // mint the user's branch name across every involved repo).
16
16
  import { aprioriWorkingBranch } from '@cat-factory/contracts'
17
17
  import type { AprioriBranch, Block } from '~/types/domain'
18
+ import SectionLabel from '~/components/common/SectionLabel.vue'
18
19
 
19
20
  const props = defineProps<{ block: Block }>()
20
21
 
@@ -150,9 +151,9 @@ function removeDisabled(entry: AprioriBranch): boolean {
150
151
  <template>
151
152
  <div v-if="repo" data-testid="apriori-branches">
152
153
  <div class="mb-1 flex items-center justify-between">
153
- <span class="text-[11px] font-semibold uppercase tracking-wide text-muted">
154
+ <SectionLabel as="span">
154
155
  {{ t('inspector.aprioriBranches.title') }}
155
- </span>
156
+ </SectionLabel>
156
157
  </div>
157
158
 
158
159
  <!-- Attached branches: one row each — name, mode badge + toggle, remove. -->
@@ -220,14 +221,14 @@ function removeDisabled(entry: AprioriBranch): boolean {
220
221
  class="w-full"
221
222
  data-testid="apriori-branch-search"
222
223
  />
223
- <div v-else class="text-[11px] text-dimmed">
224
+ <div v-else class="text-2xs text-dimmed">
224
225
  {{ t('inspector.aprioriBranches.connectFirst') }}
225
226
  </div>
226
227
 
227
228
  <!-- A protected branch pushed to by the run is likely to be rejected — warn, don't block. -->
228
229
  <div
229
230
  v-if="workingName && isProtected(workingName)"
230
- class="mt-1.5 flex items-start gap-1.5 rounded-md border border-app-warning-500/40 bg-app-warning-950/40 p-2 text-[11px] text-app-warning-200/90"
231
+ class="mt-1.5 flex items-start gap-1.5 rounded-md border border-app-warning-500/40 bg-app-warning-950/40 p-2 text-2xs text-app-warning-200/90"
231
232
  data-testid="apriori-branch-protected-warning"
232
233
  >
233
234
  <UIcon
@@ -237,7 +238,7 @@ function removeDisabled(entry: AprioriBranch): boolean {
237
238
  <span>{{ t('inspector.aprioriBranches.protectedWarning', { branch: workingName }) }}</span>
238
239
  </div>
239
240
 
240
- <div class="mt-1 text-[11px] text-dimmed">
241
+ <div class="mt-1 text-2xs text-dimmed">
241
242
  {{ t('inspector.aprioriBranches.hint') }}
242
243
  <template v-if="isMultiRepo">
243
244
  {{ t('inspector.aprioriBranches.multiRepoHint') }}
@@ -86,7 +86,7 @@ async function removeDep(dep: Block) {
86
86
  icon="i-lucide-git-branch"
87
87
  :title="t('inspector.dependencies.empty')"
88
88
  />
89
- <div v-if="!runnable" class="text-[10px] text-app-warning-400">
89
+ <div v-if="!runnable" class="text-3xs text-app-warning-400">
90
90
  {{ t('inspector.dependencies.blocked') }}
91
91
  </div>
92
92
  </InspectorSection>
@@ -79,12 +79,8 @@ function barClass(n: number): string {
79
79
  default-open
80
80
  >
81
81
  <div class="space-y-1.5 rounded-lg border border-default bg-default/40 p-2.5">
82
- <p class="text-[11px] text-dimmed" data-testid="task-estimate-basis">{{ basisLabel }}</p>
83
- <p
84
- v-if="supersededLabel"
85
- class="text-[11px] text-dimmed"
86
- data-testid="task-estimate-superseded"
87
- >
82
+ <p class="text-2xs text-dimmed" data-testid="task-estimate-basis">{{ basisLabel }}</p>
83
+ <p v-if="supersededLabel" class="text-2xs text-dimmed" data-testid="task-estimate-superseded">
88
84
  {{ supersededLabel }}
89
85
  </p>
90
86
  <div v-for="axis in AXES" :key="axis.key" class="flex items-center gap-2">
@@ -98,7 +94,7 @@ function barClass(n: number): string {
98
94
  </div>
99
95
  <span
100
96
  v-if="axis.was"
101
- class="shrink-0 text-[11px] tabular-nums text-dimmed"
97
+ class="shrink-0 text-2xs tabular-nums text-dimmed"
102
98
  :data-testid="`task-estimate-was-${axis.key}`"
103
99
  >{{ t('inspector.estimate.was', { value: axis.was }) }}</span
104
100
  >