@cat-factory/app 0.308.0 → 0.310.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.
- package/README.md +32 -2
- package/app/assets/css/main.css +22 -0
- package/app/assets/css/prose.css +4 -4
- package/app/assets/css/type.css +24 -0
- package/app/components/assistant/AssistantModal.vue +8 -6
- package/app/components/auth/BackendMisconfiguredScreen.vue +4 -3
- package/app/components/auth/LoginScreen.vue +40 -26
- package/app/components/auth/ResetPasswordScreen.vue +9 -4
- package/app/components/auth/UserMenu.vue +5 -4
- package/app/components/binaryCandidates/BinaryCandidatesWindow.vue +48 -37
- package/app/components/binaryOutput/BinaryOutputReport.vue +10 -14
- package/app/components/binaryOutput/StoredAssetView.vue +13 -11
- package/app/components/board/AddTaskModal.vue +30 -27
- package/app/components/board/AgentFailureCard.vue +21 -18
- package/app/components/board/AgentFailureHistory.vue +18 -9
- package/app/components/board/CreateInitiativeModal.vue +7 -6
- package/app/components/board/FailureDetail.vue +22 -12
- package/app/components/board/FailureHistoryList.vue +5 -5
- package/app/components/board/RecurringPipelineModal.vue +12 -11
- package/app/components/board/ReviewFrictionDialog.vue +8 -6
- package/app/components/board/StepExecutionHistory.vue +8 -8
- package/app/components/board/nodes/AgentChip.vue +1 -1
- package/app/components/board/nodes/BlockNode.vue +25 -24
- package/app/components/board/nodes/DecisionBadge.vue +4 -3
- package/app/components/board/nodes/EpicNode.vue +4 -4
- package/app/components/board/nodes/FrameSwimlanes.vue +8 -10
- package/app/components/board/nodes/InitiativeCard.vue +4 -4
- package/app/components/board/nodes/LaneGroup.vue +3 -5
- package/app/components/board/nodes/TaskCard.vue +20 -15
- package/app/components/board/nodes/TaskLane.vue +3 -3
- package/app/components/board/nodes/TaskPipelineMini.vue +21 -18
- package/app/components/bootstrap/AdoptionReviewModal.vue +36 -26
- package/app/components/bootstrap/BootstrapModal.vue +14 -13
- package/app/components/bootstrap/BootstrapRunSteps.vue +1 -1
- package/app/components/brainstorm/BrainstormWindow.vue +13 -10
- package/app/components/bugFishing/BugFishingWindow.vue +81 -58
- package/app/components/clarity/ClarityReviewWindow.vue +13 -10
- package/app/components/common/AsyncViewError.vue +1 -1
- package/app/components/common/ClarificationItem.vue +6 -6
- package/app/components/common/CopyButton.vue +12 -11
- package/app/components/common/DescriptorFields.vue +1 -1
- package/app/components/common/EmptyState.vue +1 -1
- package/app/components/common/IconButton.vue +34 -9
- package/app/components/common/InterviewGateNotice.vue +4 -4
- package/app/components/common/MarkdownProse.vue +8 -2
- package/app/components/common/SectionLabel.vue +38 -0
- package/app/components/consensus/ConsensusSessionWindow.vue +10 -9
- package/app/components/context/ContextAttachmentFields.vue +32 -20
- package/app/components/docs/DocInterviewWindow.vue +10 -9
- package/app/components/documents/ContextDocumentPicker.vue +22 -21
- package/app/components/documents/DocumentImportModal.vue +7 -5
- package/app/components/documents/DocumentOriginLink.vue +12 -9
- package/app/components/documents/DocumentSourceConnectModal.vue +2 -2
- package/app/components/documents/DocumentSyncState.vue +4 -4
- package/app/components/documents/DocumentTemplatesModal.vue +5 -4
- package/app/components/documents/RepoContextDocPicker.vue +7 -9
- package/app/components/documents/StartFromDesignModal.vue +4 -4
- package/app/components/documents/TaskContextDocs.vue +1 -1
- package/app/components/environments/EnvSetupStepper.vue +3 -3
- package/app/components/environments/EnvironmentStatusPanel.vue +15 -13
- package/app/components/environments/steps/EnvPreflightStep.vue +8 -8
- package/app/components/environments/steps/EnvReviewStep.vue +23 -22
- package/app/components/environments/steps/EnvSaveStep.vue +5 -5
- package/app/components/focus/BlockFocusView.vue +11 -10
- package/app/components/followUp/FollowUpWindow.vue +18 -15
- package/app/components/forkDecision/ForkDecisionWindow.vue +85 -97
- package/app/components/foundational/FoundationalContractSummary.vue +2 -2
- package/app/components/foundational/FoundationalServiceCatalogList.vue +6 -5
- package/app/components/foundational/FoundationalServiceRegistry.vue +10 -9
- package/app/components/foundational/FoundationalServiceSources.vue +7 -6
- package/app/components/foundational/FoundationalSuppressions.vue +2 -2
- package/app/components/fragments/FragmentLibraryManager.vue +8 -7
- package/app/components/fragments/FragmentSelector.vue +22 -20
- package/app/components/gates/GateFailingCheckList.vue +7 -6
- package/app/components/gates/GateResultView.vue +55 -49
- package/app/components/github/AddServiceFromRepoModal.vue +16 -11
- package/app/components/github/BranchProtectionPreflight.vue +5 -5
- package/app/components/github/GitHubConnect.vue +5 -3
- package/app/components/github/GitHubOnboarding.vue +7 -2
- package/app/components/github/GitHubPanel.vue +23 -19
- package/app/components/github/RepoTreeBrowser.vue +16 -13
- package/app/components/humanTest/HumanTestWindow.vue +29 -24
- package/app/components/initiative/InitiativePlanNotice.vue +3 -3
- package/app/components/initiative/InitiativePlanReview.vue +46 -38
- package/app/components/initiative/InitiativePlanningWindow.vue +5 -5
- package/app/components/initiative/InitiativeTrackerWindow.vue +213 -165
- package/app/components/judge/JudgeResultView.vue +28 -27
- package/app/components/kaizen/KaizenPanel.vue +70 -56
- package/app/components/kaizen/KaizenStepStatus.vue +7 -6
- package/app/components/layout/AccountAuditLog.vue +1 -1
- package/app/components/layout/AccountDeploymentSettings.vue +10 -10
- package/app/components/layout/AccountFailureKindRules.vue +13 -13
- package/app/components/layout/AccountFoundationalSettings.vue +1 -1
- package/app/components/layout/AccountFragmentSettings.vue +1 -1
- package/app/components/layout/AccountModelPolicySettings.vue +7 -7
- package/app/components/layout/AccountPlatformAlertSettings.vue +8 -8
- package/app/components/layout/AccountRiskPolicySettings.vue +2 -2
- package/app/components/layout/AccountRunCredentialSettings.vue +3 -3
- package/app/components/layout/AccountSkillSettings.vue +1 -1
- package/app/components/layout/AccountTeamSettings.vue +13 -9
- package/app/components/layout/AiProvidersBanner.vue +1 -1
- package/app/components/layout/AppearanceSwitcher.vue +5 -4
- package/app/components/layout/BoardSwitcher.vue +13 -10
- package/app/components/layout/BoardToolbar.vue +10 -5
- package/app/components/layout/CommandBar.vue +8 -5
- package/app/components/layout/DefaultTestEnvBanner.vue +6 -5
- package/app/components/layout/IntegrationsHub.vue +12 -9
- package/app/components/layout/LanguageSwitcher.vue +5 -4
- package/app/components/layout/ModelProvidersHub.vue +10 -7
- package/app/components/layout/NotificationsInbox.vue +47 -36
- package/app/components/layout/PersonalSetupModal.vue +9 -6
- package/app/components/layout/RolePrompt.vue +5 -4
- package/app/components/layout/SideBar.vue +7 -8
- package/app/components/layout/SpendWarningBanner.vue +3 -3
- package/app/components/layout/TranslationWarningBanner.vue +5 -4
- package/app/components/layout/UiModeSwitcher.vue +15 -12
- package/app/components/layout/UiRoleSwitcher.vue +10 -8
- package/app/components/layout/WorkspaceMembersSettings.vue +2 -2
- package/app/components/media/ArtifactLightbox.vue +74 -44
- package/app/components/media/ImageCompare.vue +80 -85
- package/app/components/merge/MergeEffortChips.vue +4 -6
- package/app/components/notifications/NotificationSettingsPanel.vue +6 -5
- package/app/components/observability/OutcomeFilterChips.vue +6 -5
- package/app/components/observability/RunFailureSummary.vue +22 -23
- package/app/components/observability/StepMetricsBar.vue +9 -8
- package/app/components/observability/StepModelActivity.vue +8 -5
- package/app/components/observability/ToolCallList.vue +19 -20
- package/app/components/outcome/OutcomeSummaryWindow.vue +48 -46
- package/app/components/palettes/AgentPalette.vue +21 -15
- package/app/components/palettes/AgentTierSelect.vue +1 -1
- package/app/components/palettes/PipelinePurposeSelect.vue +1 -1
- package/app/components/panels/AgentStepDetail.vue +57 -49
- package/app/components/panels/AttemptEntryHeader.vue +2 -2
- package/app/components/panels/DecisionModal.vue +1 -1
- package/app/components/panels/GenericStructuredResultView.vue +6 -5
- package/app/components/panels/InspectorPanel.vue +15 -13
- package/app/components/panels/MergerResultView.vue +10 -9
- package/app/components/panels/ObservabilityPanel.vue +211 -186
- package/app/components/panels/OperatorDashboardPanel.vue +124 -115
- package/app/components/panels/ReportsPanel.vue +87 -83
- package/app/components/panels/ReportsSpendBreakdown.vue +2 -2
- package/app/components/panels/ResultWindowShell.vue +152 -137
- package/app/components/panels/RunDetailLoadState.vue +1 -1
- package/app/components/panels/StepContainerStatus.vue +17 -16
- package/app/components/panels/StepDelegatedStatus.vue +24 -21
- package/app/components/panels/StepEffortReport.vue +12 -17
- package/app/components/panels/StepFragmentAdherence.vue +9 -10
- package/app/components/panels/StepMetadataCard.vue +41 -43
- package/app/components/panels/StepReproductionReport.vue +18 -20
- package/app/components/panels/StepRestartControl.vue +3 -2
- package/app/components/panels/StepRunMeta.vue +27 -26
- package/app/components/panels/StepTestReport.vue +16 -15
- package/app/components/panels/StepToolServers.vue +7 -8
- package/app/components/panels/StepValidationReport.vue +5 -5
- package/app/components/panels/inspector/ContainerSummary.vue +4 -4
- package/app/components/panels/inspector/DocReferenceRepos.vue +5 -4
- package/app/components/panels/inspector/EnvProbeReport.vue +16 -13
- package/app/components/panels/inspector/EpicChildren.vue +12 -10
- package/app/components/panels/inspector/FrontendBindingsResolved.vue +5 -4
- package/app/components/panels/inspector/FrontendConfig.vue +29 -36
- package/app/components/panels/inspector/InitiativeInspector.vue +3 -3
- package/app/components/panels/inspector/InspectorSection.vue +25 -17
- package/app/components/panels/inspector/RecurringScheduleSettings.vue +9 -8
- package/app/components/panels/inspector/ServiceConnections.vue +5 -4
- package/app/components/panels/inspector/ServiceReleaseHealthConfig.vue +2 -2
- package/app/components/panels/inspector/ServiceSelfTests.vue +9 -13
- package/app/components/panels/inspector/ServiceTestConfig.vue +46 -49
- package/app/components/panels/inspector/ServiceTestSecrets.vue +3 -3
- package/app/components/panels/inspector/ServiceTestingContext.vue +2 -2
- package/app/components/panels/inspector/ServiceValidationConfig.vue +2 -2
- package/app/components/panels/inspector/TaskAgentConfig.vue +2 -2
- package/app/components/panels/inspector/TaskAprioriBranches.vue +6 -5
- package/app/components/panels/inspector/TaskDependencies.vue +1 -1
- package/app/components/panels/inspector/TaskEstimateBadge.vue +3 -7
- package/app/components/panels/inspector/TaskExecution.vue +18 -16
- package/app/components/panels/inspector/TaskRunSettings.vue +45 -44
- package/app/components/panels/inspector/TaskStructure.vue +5 -4
- package/app/components/pipeline/AgentPromptEditor.vue +15 -14
- package/app/components/pipeline/BinaryOutputStepPicker.vue +42 -52
- package/app/components/pipeline/EstimateThresholdFields.vue +14 -11
- package/app/components/pipeline/GateConfigFields.vue +19 -23
- package/app/components/pipeline/IterationCapPrompt.vue +1 -1
- package/app/components/pipeline/PipelineBuilder.vue +113 -99
- package/app/components/pipeline/PipelineHealthModal.vue +7 -7
- package/app/components/pipeline/PipelinePicker.vue +11 -9
- package/app/components/pipeline/PipelinePreview.vue +6 -7
- package/app/components/pipeline/PipelineProgress.vue +49 -45
- package/app/components/prReview/PrReviewWindow.vue +87 -65
- package/app/components/providers/AiPresetMismatchDialog.vue +4 -3
- package/app/components/providers/AiProviderOnboardingModal.vue +2 -2
- package/app/components/providers/ApiKeysSection.vue +11 -9
- package/app/components/providers/PersonalSubscriptionSection.vue +4 -3
- package/app/components/providers/VendorCredentialsModal.vue +5 -4
- package/app/components/provisioning/ProvisioningLogsDrawer.vue +10 -9
- package/app/components/ralph/RalphLoopResultView.vue +29 -29
- package/app/components/requirements/RequirementsReviewWindow.vue +22 -17
- package/app/components/riskPolicy/RiskPolicyPicker.vue +13 -11
- package/app/components/riskPolicy/RiskPolicyPreview.vue +16 -15
- package/app/components/sandbox/SandboxPanel.vue +93 -73
- package/app/components/settings/ApiTokensPanel.vue +1 -1
- package/app/components/settings/BudgetSettings.vue +18 -17
- package/app/components/settings/CapabilityCredentialsPanel.vue +5 -5
- package/app/components/settings/CloudflareHandlerSection.vue +44 -41
- package/app/components/settings/ComposeEnvironmentSetupSection.vue +14 -12
- package/app/components/settings/ConnectionTestVerdict.vue +1 -1
- package/app/components/settings/ConsensusGroupsSection.vue +58 -47
- package/app/components/settings/CustomManifestTypeEditor.vue +8 -7
- package/app/components/settings/DefaultProvisionTypeSection.vue +5 -5
- package/app/components/settings/InfraHandlersConfigurator.vue +26 -24
- package/app/components/settings/InfrastructureBackendPicker.vue +18 -18
- package/app/components/settings/IssueTrackerPanel.vue +30 -21
- package/app/components/settings/KubernetesEngineForm.vue +9 -8
- package/app/components/settings/KubernetesEnvironmentForm.vue +4 -3
- package/app/components/settings/LocalContainerPoolSettings.vue +2 -2
- package/app/components/settings/LocalModelEndpointsPanel.vue +13 -11
- package/app/components/settings/MergeClassRulesEditor.vue +6 -5
- package/app/components/settings/MergeRolePolicyEditor.vue +13 -12
- package/app/components/settings/ModelConfigurationPanel.vue +17 -19
- package/app/components/settings/ModelPresetHealthModal.vue +3 -3
- package/app/components/settings/ObservabilityConnectionPanel.vue +1 -1
- package/app/components/settings/OpenRouterCatalogPanel.vue +10 -8
- package/app/components/settings/PackageRegistriesPanel.vue +4 -4
- package/app/components/settings/ProviderConnectionTab.vue +5 -4
- package/app/components/settings/ProviderManifestEditor.vue +9 -8
- package/app/components/settings/ProviderPreferenceEditor.vue +13 -13
- package/app/components/settings/RiskPolicyCreateForm.vue +40 -26
- package/app/components/settings/RiskPolicyEditorRow.vue +21 -19
- package/app/components/settings/RiskPolicyHealthModal.vue +3 -3
- package/app/components/settings/RiskPolicyPanel.vue +11 -13
- package/app/components/settings/ServiceFragmentDefaultsPanel.vue +15 -12
- package/app/components/settings/SharedStacksPanel.vue +5 -5
- package/app/components/settings/TaskSourceCard.vue +2 -2
- package/app/components/settings/TaskTypeSuppressionsPanel.vue +4 -4
- package/app/components/settings/ToolServerChecklist.vue +22 -22
- package/app/components/settings/UsageSettings.vue +13 -13
- package/app/components/settings/UserSecretsSection.vue +4 -3
- package/app/components/settings/WorkspaceMetadataSettings.vue +6 -5
- package/app/components/settings/WorkspaceSettingsPanel.vue +72 -58
- package/app/components/skills/ReviewSkillQueue.vue +12 -10
- package/app/components/skills/SkillLibraryManager.vue +9 -8
- package/app/components/slack/SlackPanel.vue +17 -12
- package/app/components/spec/ServiceSpecWindow.vue +19 -19
- package/app/components/tasks/BugHuntModal.vue +1 -1
- package/app/components/tasks/ContextIssuePicker.vue +16 -15
- package/app/components/tasks/TaskContextIssues.vue +5 -4
- package/app/components/tasks/TaskImportModal.vue +3 -2
- package/app/components/tasks/TaskSourceConnectModal.vue +5 -5
- package/app/components/testing/TestReportWindow.vue +67 -60
- package/app/components/theme/ThemeImportModal.vue +2 -2
- package/app/components/tutorial/TutorialNudge.vue +3 -2
- package/app/components/tutorial/TutorialOverlay.vue +3 -2
- package/app/components/vcs/GitLabConnect.vue +1 -1
- package/app/components/visualConfirm/VisualConfirmationWindow.vue +79 -54
- package/app/utils/theme/builtins.ts +7 -1
- package/i18n/locales/de.json +7 -3
- package/i18n/locales/en.json +7 -3
- package/i18n/locales/es.json +7 -3
- package/i18n/locales/fr.json +7 -3
- package/i18n/locales/he.json +7 -3
- package/i18n/locales/it.json +7 -3
- package/i18n/locales/ja.json +7 -3
- package/i18n/locales/pl.json +7 -3
- package/i18n/locales/tr.json +7 -3
- package/i18n/locales/uk.json +7 -3
- package/package.json +1 -1
|
@@ -30,6 +30,7 @@ import ResultWindowShell from '~/components/panels/ResultWindowShell.vue'
|
|
|
30
30
|
import StepRunMeta from '~/components/panels/StepRunMeta.vue'
|
|
31
31
|
import StepFragmentAdherence from '~/components/panels/StepFragmentAdherence.vue'
|
|
32
32
|
import MarkdownProse from '~/components/common/MarkdownProse.vue'
|
|
33
|
+
import SectionLabel from '~/components/common/SectionLabel.vue'
|
|
33
34
|
|
|
34
35
|
const execution = useExecutionStore()
|
|
35
36
|
const board = useBoardStore()
|
|
@@ -291,14 +292,15 @@ const { requestClose } = useUnsavedGuard({
|
|
|
291
292
|
@close="requestClose"
|
|
292
293
|
>
|
|
293
294
|
<template v-if="state?.prUrl" #header-extras>
|
|
294
|
-
<
|
|
295
|
-
|
|
295
|
+
<ULink
|
|
296
|
+
raw
|
|
297
|
+
:to="state.prUrl"
|
|
296
298
|
target="_blank"
|
|
297
299
|
rel="noopener"
|
|
298
|
-
class="rounded-md px-2 py-1 text-
|
|
300
|
+
class="rounded-md px-2 py-1 text-2xs text-primary hover:bg-elevated"
|
|
299
301
|
>
|
|
300
302
|
{{ t('prReview.openPr') }}
|
|
301
|
-
</
|
|
303
|
+
</ULink>
|
|
302
304
|
</template>
|
|
303
305
|
|
|
304
306
|
<div class="flex min-h-0 flex-1">
|
|
@@ -320,7 +322,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
320
322
|
>
|
|
321
323
|
<UIcon name="i-lucide-loader-circle" class="h-8 w-8 animate-spin opacity-60" />
|
|
322
324
|
<p class="text-sm text-default">{{ t('prReview.reviewing.planning.title') }}</p>
|
|
323
|
-
<p class="max-w-sm text-
|
|
325
|
+
<p class="max-w-sm text-2xs text-dimmed">
|
|
324
326
|
{{ t('prReview.reviewing.planning.hint') }}
|
|
325
327
|
</p>
|
|
326
328
|
</div>
|
|
@@ -334,11 +336,11 @@ const { requestClose } = useUnsavedGuard({
|
|
|
334
336
|
/>
|
|
335
337
|
<span>{{ t('prReview.reviewing.reviewingChunks.title') }}</span>
|
|
336
338
|
</div>
|
|
337
|
-
<p class="mb-3 text-
|
|
339
|
+
<p class="mb-3 text-2xs text-dimmed">
|
|
338
340
|
{{ t('prReview.reviewing.reviewingChunks.hint') }}
|
|
339
341
|
</p>
|
|
340
342
|
|
|
341
|
-
<div class="flex items-center justify-between text-
|
|
343
|
+
<div class="flex items-center justify-between text-2xs text-muted">
|
|
342
344
|
<span data-testid="pr-review-chunk-count">
|
|
343
345
|
{{
|
|
344
346
|
t('prReview.reviewing.chunks', {
|
|
@@ -372,7 +374,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
372
374
|
"
|
|
373
375
|
>
|
|
374
376
|
<p
|
|
375
|
-
class="mb-1 text-
|
|
377
|
+
class="mb-1 text-3xs font-semibold uppercase tracking-wide"
|
|
376
378
|
:class="activeChunks.length ? 'text-primary' : 'text-dimmed'"
|
|
377
379
|
>
|
|
378
380
|
{{ t('prReview.reviewing.activeHeading') }}
|
|
@@ -381,7 +383,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
381
383
|
<li
|
|
382
384
|
v-for="(label, i) in activeChunks"
|
|
383
385
|
:key="i"
|
|
384
|
-
class="flex items-start gap-1.5 text-
|
|
386
|
+
class="flex items-start gap-1.5 text-xs text-app-100"
|
|
385
387
|
>
|
|
386
388
|
<UIcon
|
|
387
389
|
name="i-lucide-loader-circle"
|
|
@@ -390,22 +392,22 @@ const { requestClose } = useUnsavedGuard({
|
|
|
390
392
|
<span class="min-w-0">{{ label }}</span>
|
|
391
393
|
</li>
|
|
392
394
|
</ul>
|
|
393
|
-
<p v-else data-testid="pr-review-active-idle" class="text-
|
|
395
|
+
<p v-else data-testid="pr-review-active-idle" class="text-xs text-muted">
|
|
394
396
|
{{ t('prReview.reviewing.activeIdle') }}
|
|
395
397
|
</p>
|
|
396
398
|
</div>
|
|
397
399
|
|
|
398
400
|
<!-- Every chunk with its explicit status (Reviewed / Reviewing… / Queued). -->
|
|
399
401
|
<template v-if="subtasks!.items?.length">
|
|
400
|
-
<p class="mb-1.5 mt-3
|
|
402
|
+
<SectionLabel as="p" class="mb-1.5 mt-3">
|
|
401
403
|
{{ t('prReview.reviewing.chunksHeading') }}
|
|
402
|
-
</
|
|
404
|
+
</SectionLabel>
|
|
403
405
|
<ul class="space-y-1.5" data-testid="pr-review-chunks">
|
|
404
406
|
<li
|
|
405
407
|
v-for="(item, i) in subtasks!.items"
|
|
406
408
|
:key="i"
|
|
407
409
|
data-testid="pr-review-chunk"
|
|
408
|
-
class="flex items-center gap-1.5 text-
|
|
410
|
+
class="flex items-center gap-1.5 text-xs"
|
|
409
411
|
:class="
|
|
410
412
|
item.status === 'completed'
|
|
411
413
|
? 'text-dimmed'
|
|
@@ -427,7 +429,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
427
429
|
</span>
|
|
428
430
|
<span
|
|
429
431
|
data-testid="pr-review-chunk-status"
|
|
430
|
-
class="shrink-0 rounded px-1.5 py-0.5 text-
|
|
432
|
+
class="shrink-0 rounded-sm px-1.5 py-0.5 text-3xs font-medium uppercase"
|
|
431
433
|
:class="CHUNK_STATUS_CLASS[item.status]"
|
|
432
434
|
>
|
|
433
435
|
{{ chunkStatusLabel(item.status) }}
|
|
@@ -446,12 +448,12 @@ const { requestClose } = useUnsavedGuard({
|
|
|
446
448
|
<p
|
|
447
449
|
v-if="prReview.error"
|
|
448
450
|
data-testid="pr-review-resume-error"
|
|
449
|
-
class="mb-2 rounded-md bg-app-error-500/10 px-3 py-2 text-
|
|
451
|
+
class="mb-2 rounded-md bg-app-error-500/10 px-3 py-2 text-xs text-app-error-300"
|
|
450
452
|
>
|
|
451
453
|
{{ prReview.error }}
|
|
452
454
|
</p>
|
|
453
455
|
<div class="flex items-start justify-between gap-3">
|
|
454
|
-
<p class="min-w-0 text-
|
|
456
|
+
<p class="min-w-0 text-2xs text-dimmed">{{ t('prReview.resume.hint') }}</p>
|
|
455
457
|
<UButton
|
|
456
458
|
data-testid="pr-review-resume"
|
|
457
459
|
size="xs"
|
|
@@ -479,7 +481,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
479
481
|
<p class="text-sm">
|
|
480
482
|
{{ status === 'fixing' ? t('prReview.fixing.title') : t('prReview.posting.title') }}
|
|
481
483
|
</p>
|
|
482
|
-
<p class="max-w-sm text-
|
|
484
|
+
<p class="max-w-sm text-2xs text-dimmed">
|
|
483
485
|
{{ status === 'fixing' ? t('prReview.fixing.hint') : t('prReview.posting.hint') }}
|
|
484
486
|
</p>
|
|
485
487
|
</div>
|
|
@@ -487,7 +489,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
487
489
|
<template v-else>
|
|
488
490
|
<p
|
|
489
491
|
v-if="prReview.error"
|
|
490
|
-
class="mb-3 rounded-md bg-app-error-500/10 px-3 py-2 text-
|
|
492
|
+
class="mb-3 rounded-md bg-app-error-500/10 px-3 py-2 text-xs text-app-error-300"
|
|
491
493
|
>
|
|
492
494
|
{{ prReview.error }}
|
|
493
495
|
</p>
|
|
@@ -498,7 +500,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
498
500
|
<div
|
|
499
501
|
v-if="postReport"
|
|
500
502
|
data-testid="pr-review-post-report"
|
|
501
|
-
class="mb-3 rounded-lg border px-3 py-2 text-
|
|
503
|
+
class="mb-3 rounded-lg border px-3 py-2 text-xs"
|
|
502
504
|
:class="
|
|
503
505
|
postReport.failures.length > 0 || postReport.bodyPosted === false
|
|
504
506
|
? 'border-app-warning-500/40 bg-app-warning-500/10 text-app-warning-200'
|
|
@@ -547,7 +549,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
547
549
|
shell's `width` prop) — this window is `full`-width. -->
|
|
548
550
|
<div
|
|
549
551
|
v-if="state?.summary"
|
|
550
|
-
class="mb-3 max-w-3xl rounded-md bg-elevated/50 px-3 py-2 text-
|
|
552
|
+
class="mb-3 max-w-3xl rounded-md bg-elevated/50 px-3 py-2 text-xs text-toned"
|
|
551
553
|
>
|
|
552
554
|
<span class="mb-1 block text-dimmed">{{ t('prReview.summaryLabel') }}</span>
|
|
553
555
|
<MarkdownProse :text="state.summary" />
|
|
@@ -564,7 +566,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
564
566
|
<!-- A clean PR / resolved review with no findings. -->
|
|
565
567
|
<div
|
|
566
568
|
v-if="findings.length === 0"
|
|
567
|
-
class="rounded-xl border border-default bg-default/60 px-4 py-6 text-center text-
|
|
569
|
+
class="rounded-xl border border-default bg-default/60 px-4 py-6 text-center text-sm text-toned"
|
|
568
570
|
>
|
|
569
571
|
{{ t('prReview.noFindings') }}
|
|
570
572
|
</div>
|
|
@@ -574,31 +576,41 @@ const { requestClose } = useUnsavedGuard({
|
|
|
574
576
|
<div
|
|
575
577
|
v-if="challenging"
|
|
576
578
|
data-testid="pr-review-challenging"
|
|
577
|
-
class="mb-3 flex items-center gap-2 rounded-md border border-primary/40 bg-primary/10 px-3 py-2 text-
|
|
579
|
+
class="mb-3 flex items-center gap-2 rounded-md border border-primary/40 bg-primary/10 px-3 py-2 text-xs text-primary"
|
|
578
580
|
>
|
|
579
581
|
<UIcon name="i-lucide-loader-circle" class="h-4 w-4 shrink-0 animate-spin" />
|
|
580
582
|
<span>{{ t('prReview.challenge.investigatingBanner') }}</span>
|
|
581
583
|
</div>
|
|
582
584
|
|
|
583
585
|
<!-- Selection toolbar -->
|
|
584
|
-
<div v-if="awaiting" class="mb-2 flex items-center gap-3 text-
|
|
586
|
+
<div v-if="awaiting" class="mb-2 flex items-center gap-3 text-2xs text-muted">
|
|
585
587
|
<span data-testid="pr-review-selected-count">
|
|
586
588
|
{{ t('prReview.selectedCount', { count: activeSelectedIds.length }) }}
|
|
587
589
|
</span>
|
|
588
|
-
<
|
|
590
|
+
<UButton
|
|
591
|
+
color="primary"
|
|
592
|
+
variant="link"
|
|
593
|
+
class="p-0 text-2xs text-primary hover:underline"
|
|
594
|
+
@click="selectAll"
|
|
595
|
+
>
|
|
589
596
|
{{ t('prReview.selectAll') }}
|
|
590
|
-
</
|
|
591
|
-
<
|
|
597
|
+
</UButton>
|
|
598
|
+
<UButton
|
|
599
|
+
color="primary"
|
|
600
|
+
variant="link"
|
|
601
|
+
class="p-0 text-2xs text-primary hover:underline"
|
|
602
|
+
@click="clearAll"
|
|
603
|
+
>
|
|
592
604
|
{{ t('prReview.clear') }}
|
|
593
|
-
</
|
|
605
|
+
</UButton>
|
|
594
606
|
</div>
|
|
595
607
|
|
|
596
608
|
<!-- Findings grouped by slice -->
|
|
597
609
|
<section v-for="g in groups" :key="g.id" class="mb-4">
|
|
598
|
-
<h3 class="mb-1.5
|
|
610
|
+
<SectionLabel as="h3" class="mb-1.5">
|
|
599
611
|
{{ g.title }}
|
|
600
|
-
</
|
|
601
|
-
<p v-if="g.rationale" class="mb-1.5 max-w-3xl text-
|
|
612
|
+
</SectionLabel>
|
|
613
|
+
<p v-if="g.rationale" class="mb-1.5 max-w-3xl text-2xs text-dimmed">
|
|
602
614
|
{{ g.rationale }}
|
|
603
615
|
</p>
|
|
604
616
|
<article
|
|
@@ -614,30 +626,30 @@ const { requestClose } = useUnsavedGuard({
|
|
|
614
626
|
]"
|
|
615
627
|
>
|
|
616
628
|
<div class="flex items-start gap-2">
|
|
617
|
-
<
|
|
629
|
+
<UCheckbox
|
|
618
630
|
v-if="awaiting || challenging"
|
|
619
|
-
|
|
620
|
-
class="mt-1
|
|
631
|
+
size="xs"
|
|
632
|
+
class="mt-1"
|
|
621
633
|
data-testid="pr-review-finding-toggle"
|
|
622
|
-
:
|
|
634
|
+
:model-value="selected.has(f.id) && !isRetracted(f)"
|
|
623
635
|
:disabled="!awaiting || isRetracted(f)"
|
|
624
|
-
@
|
|
636
|
+
@update:model-value="toggle(f.id)"
|
|
625
637
|
/>
|
|
626
638
|
<div class="min-w-0 flex-1">
|
|
627
639
|
<div class="flex flex-wrap items-center gap-1.5">
|
|
628
640
|
<span
|
|
629
|
-
class="rounded px-1.5 py-0.5 text-
|
|
641
|
+
class="rounded-sm px-1.5 py-0.5 text-3xs font-semibold uppercase ring-1"
|
|
630
642
|
:class="SEVERITY_CLASS[f.severity]"
|
|
631
643
|
>
|
|
632
644
|
{{ t(`prReview.severity.${f.severity}`) }}
|
|
633
645
|
</span>
|
|
634
|
-
<span class="rounded bg-elevated px-1.5 py-0.5 text-
|
|
646
|
+
<span class="rounded-sm bg-elevated px-1.5 py-0.5 text-3xs text-toned">
|
|
635
647
|
{{ t(`prReview.category.${f.category}`) }}
|
|
636
648
|
</span>
|
|
637
649
|
<span
|
|
638
650
|
v-if="postedIds.has(f.id)"
|
|
639
651
|
data-testid="pr-review-finding-posted"
|
|
640
|
-
class="rounded bg-app-success-500/15 px-1.5 py-0.5 text-
|
|
652
|
+
class="rounded-sm bg-app-success-500/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-app-success-300 ring-1 ring-app-success-500/30"
|
|
641
653
|
>
|
|
642
654
|
{{ t('prReview.postReport.postedBadge') }}
|
|
643
655
|
</span>
|
|
@@ -645,47 +657,47 @@ const { requestClose } = useUnsavedGuard({
|
|
|
645
657
|
<span
|
|
646
658
|
v-if="isRetracted(f)"
|
|
647
659
|
data-testid="pr-review-finding-retracted"
|
|
648
|
-
class="rounded bg-app-error-500/15 px-1.5 py-0.5 text-
|
|
660
|
+
class="rounded-sm bg-app-error-500/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-app-error-300 ring-1 ring-app-error-500/30"
|
|
649
661
|
>
|
|
650
662
|
{{ t('prReview.challenge.retractedBadge') }}
|
|
651
663
|
</span>
|
|
652
664
|
<span
|
|
653
665
|
v-else-if="isAmended(f)"
|
|
654
666
|
data-testid="pr-review-finding-amended"
|
|
655
|
-
class="rounded bg-app-info-500/15 px-1.5 py-0.5 text-
|
|
667
|
+
class="rounded-sm bg-app-info-500/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-app-info-300 ring-1 ring-app-info-500/30"
|
|
656
668
|
>
|
|
657
669
|
{{ t('prReview.challenge.strengthenedBadge') }}
|
|
658
670
|
</span>
|
|
659
671
|
<span
|
|
660
672
|
v-else-if="isUpheld(f)"
|
|
661
673
|
data-testid="pr-review-finding-upheld"
|
|
662
|
-
class="rounded bg-app-success-500/15 px-1.5 py-0.5 text-
|
|
674
|
+
class="rounded-sm bg-app-success-500/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-app-success-300 ring-1 ring-app-success-500/30"
|
|
663
675
|
>
|
|
664
676
|
{{ t('prReview.challenge.upheldBadge') }}
|
|
665
677
|
</span>
|
|
666
678
|
<span
|
|
667
679
|
v-else-if="isChallengeFailed(f)"
|
|
668
680
|
data-testid="pr-review-finding-challenge-failed"
|
|
669
|
-
class="rounded bg-app-warning-500/15 px-1.5 py-0.5 text-
|
|
681
|
+
class="rounded-sm bg-app-warning-500/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-app-warning-300 ring-1 ring-app-warning-500/30"
|
|
670
682
|
>
|
|
671
683
|
{{ t('prReview.challenge.failedBadge') }}
|
|
672
684
|
</span>
|
|
673
685
|
<span
|
|
674
686
|
v-else-if="isInvestigating(f)"
|
|
675
687
|
data-testid="pr-review-finding-investigating"
|
|
676
|
-
class="flex items-center gap-1 rounded bg-primary/15 px-1.5 py-0.5 text-
|
|
688
|
+
class="flex items-center gap-1 rounded-sm bg-primary/15 px-1.5 py-0.5 text-3xs font-semibold uppercase text-primary ring-1 ring-primary/30"
|
|
677
689
|
>
|
|
678
690
|
<UIcon name="i-lucide-loader-circle" class="h-3 w-3 animate-spin" />
|
|
679
691
|
{{ t('prReview.challenge.investigatingBadge') }}
|
|
680
692
|
</span>
|
|
681
693
|
<h4
|
|
682
|
-
class="min-w-0 flex-1 text-
|
|
694
|
+
class="min-w-0 flex-1 text-sm font-medium text-app-100"
|
|
683
695
|
:class="isRetracted(f) ? 'line-through' : ''"
|
|
684
696
|
>
|
|
685
697
|
{{ f.title }}
|
|
686
698
|
</h4>
|
|
687
699
|
</div>
|
|
688
|
-
<p class="mt-0.5 text-
|
|
700
|
+
<p class="mt-0.5 text-2xs text-dimmed">
|
|
689
701
|
{{ f.path
|
|
690
702
|
}}<template v-if="f.line != null">
|
|
691
703
|
· {{ t('prReview.line', { line: f.line }) }}</template
|
|
@@ -701,7 +713,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
701
713
|
<MarkdownProse
|
|
702
714
|
v-if="f.detail"
|
|
703
715
|
:text="f.detail"
|
|
704
|
-
class="mt-1 max-w-3xl text-
|
|
716
|
+
class="mt-1 max-w-3xl text-xs text-toned"
|
|
705
717
|
:class="isRetracted(f) ? 'line-through' : ''"
|
|
706
718
|
/>
|
|
707
719
|
<!-- The suggested fix is a VALUE a human copies (a patch line, a command, a
|
|
@@ -711,7 +723,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
711
723
|
failure summary is left alone. -->
|
|
712
724
|
<p
|
|
713
725
|
v-if="f.suggestedFix"
|
|
714
|
-
class="mt-1 max-w-3xl whitespace-pre-wrap rounded-md bg-elevated/50 px-2 py-1 text-
|
|
726
|
+
class="mt-1 max-w-3xl whitespace-pre-wrap rounded-md bg-elevated/50 px-2 py-1 text-2xs text-toned"
|
|
715
727
|
>
|
|
716
728
|
<span class="text-dimmed">{{ t('prReview.suggestedFix') }}</span>
|
|
717
729
|
{{ f.suggestedFix }}
|
|
@@ -722,7 +734,7 @@ const { requestClose } = useUnsavedGuard({
|
|
|
722
734
|
<div
|
|
723
735
|
v-if="f.challenge?.justification"
|
|
724
736
|
data-testid="pr-review-finding-justification"
|
|
725
|
-
class="mt-1.5 max-w-3xl rounded-md px-2 py-1 text-
|
|
737
|
+
class="mt-1.5 max-w-3xl rounded-md px-2 py-1 text-2xs"
|
|
726
738
|
:class="
|
|
727
739
|
isRetracted(f)
|
|
728
740
|
? 'bg-app-error-500/10 text-app-error-200'
|
|
@@ -745,12 +757,14 @@ const { requestClose } = useUnsavedGuard({
|
|
|
745
757
|
<!-- Per-finding actions: Challenge + Dismiss (only while awaiting a selection). -->
|
|
746
758
|
<div
|
|
747
759
|
v-if="awaiting && !isInvestigating(f)"
|
|
748
|
-
class="mt-1.5 flex items-center gap-3 text-
|
|
760
|
+
class="mt-1.5 flex items-center gap-3 text-2xs"
|
|
749
761
|
>
|
|
750
|
-
<
|
|
762
|
+
<UButton
|
|
763
|
+
color="primary"
|
|
764
|
+
variant="link"
|
|
751
765
|
v-if="!isRetracted(f)"
|
|
752
766
|
data-testid="pr-review-finding-challenge"
|
|
753
|
-
class="flex items-center gap-1 text-primary hover:underline disabled:opacity-50"
|
|
767
|
+
class="p-0 text-2xs flex items-center gap-1 text-primary hover:underline disabled:opacity-50"
|
|
754
768
|
:disabled="!canResolve || !access.canExecuteRuns.value"
|
|
755
769
|
@click="openChallenge(f.id)"
|
|
756
770
|
>
|
|
@@ -760,16 +774,18 @@ const { requestClose } = useUnsavedGuard({
|
|
|
760
774
|
? t('prReview.challenge.reChallenge')
|
|
761
775
|
: t('prReview.challenge.action')
|
|
762
776
|
}}
|
|
763
|
-
</
|
|
764
|
-
<
|
|
777
|
+
</UButton>
|
|
778
|
+
<UButton
|
|
779
|
+
color="neutral"
|
|
780
|
+
variant="link"
|
|
765
781
|
data-testid="pr-review-finding-dismiss"
|
|
766
|
-
class="flex items-center gap-1 text-muted hover:text-app-error-300 hover:underline disabled:opacity-50"
|
|
782
|
+
class="p-0 text-xs flex items-center gap-1 text-muted hover:text-app-error-300 hover:underline disabled:opacity-50"
|
|
767
783
|
:disabled="!canResolve || !access.canExecuteRuns.value"
|
|
768
784
|
@click="onDismiss(f.id)"
|
|
769
785
|
>
|
|
770
786
|
<UIcon name="i-lucide-trash-2" class="h-3.5 w-3.5" />
|
|
771
787
|
{{ t('prReview.challenge.dismiss') }}
|
|
772
|
-
</
|
|
788
|
+
</UButton>
|
|
773
789
|
</div>
|
|
774
790
|
|
|
775
791
|
<!-- The inline challenge box: an OPTIONAL specific concern for the investigator. -->
|
|
@@ -778,31 +794,37 @@ const { requestClose } = useUnsavedGuard({
|
|
|
778
794
|
data-testid="pr-review-challenge-box"
|
|
779
795
|
class="mt-2 rounded-md border border-primary/40 bg-default/80 p-2"
|
|
780
796
|
>
|
|
781
|
-
<
|
|
797
|
+
<UTextarea
|
|
782
798
|
v-model="challengeText"
|
|
783
799
|
data-testid="pr-review-challenge-input"
|
|
784
|
-
rows="2"
|
|
800
|
+
:rows="2"
|
|
785
801
|
:placeholder="t('prReview.challenge.placeholder')"
|
|
786
|
-
|
|
802
|
+
size="xs"
|
|
803
|
+
class="w-full"
|
|
804
|
+
:ui="{ base: 'resize-y' }"
|
|
787
805
|
/>
|
|
788
|
-
<p class="mt-1 text-
|
|
806
|
+
<p class="mt-1 text-3xs text-dimmed">
|
|
789
807
|
{{ t('prReview.challenge.hint') }}
|
|
790
808
|
</p>
|
|
791
809
|
<div class="mt-1.5 flex justify-end gap-2">
|
|
792
|
-
<
|
|
793
|
-
|
|
810
|
+
<UButton
|
|
811
|
+
color="neutral"
|
|
812
|
+
variant="ghost"
|
|
813
|
+
class="rounded-sm px-2 py-1 text-2xs text-muted hover:text-default"
|
|
794
814
|
@click="cancelChallenge"
|
|
795
815
|
>
|
|
796
816
|
{{ t('common.cancel') }}
|
|
797
|
-
</
|
|
798
|
-
<
|
|
817
|
+
</UButton>
|
|
818
|
+
<UButton
|
|
819
|
+
color="neutral"
|
|
820
|
+
variant="ghost"
|
|
799
821
|
data-testid="pr-review-challenge-submit"
|
|
800
|
-
class="rounded bg-primary/80 px-2 py-1 text-
|
|
822
|
+
class="rounded-sm bg-primary/80 px-2 py-1 text-2xs font-medium text-inverted hover:bg-primary/90 disabled:opacity-50"
|
|
801
823
|
:disabled="!canResolve"
|
|
802
824
|
@click="submitChallenge(f.id)"
|
|
803
825
|
>
|
|
804
826
|
{{ t('prReview.challenge.submit') }}
|
|
805
|
-
</
|
|
827
|
+
</UButton>
|
|
806
828
|
</div>
|
|
807
829
|
</div>
|
|
808
830
|
</div>
|
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
// auto-opens once per session (driven from pages/index.vue) and clears once the preset is
|
|
8
8
|
// fixed (or all its models become available).
|
|
9
9
|
import { computed } from 'vue'
|
|
10
|
+
import SectionLabel from '~/components/common/SectionLabel.vue'
|
|
10
11
|
|
|
11
12
|
const { t } = useI18n()
|
|
12
13
|
const ui = useUiStore()
|
|
@@ -54,9 +55,9 @@ function go(action: () => void) {
|
|
|
54
55
|
</i18n-t>
|
|
55
56
|
|
|
56
57
|
<div class="rounded-lg border border-muted bg-default/50 p-3">
|
|
57
|
-
<p class="mb-1.5
|
|
58
|
+
<SectionLabel as="p" class="mb-1.5">
|
|
58
59
|
{{ t('providers.presetMismatch.unavailable') }}
|
|
59
|
-
</
|
|
60
|
+
</SectionLabel>
|
|
60
61
|
<div class="flex flex-wrap gap-1.5">
|
|
61
62
|
<UBadge
|
|
62
63
|
v-for="label in unavailableLabels"
|
|
@@ -70,7 +71,7 @@ function go(action: () => void) {
|
|
|
70
71
|
</div>
|
|
71
72
|
</div>
|
|
72
73
|
|
|
73
|
-
<p class="text-
|
|
74
|
+
<p class="text-sm text-muted">
|
|
74
75
|
{{ t('providers.presetMismatch.advice') }}
|
|
75
76
|
</p>
|
|
76
77
|
|
|
@@ -104,7 +104,7 @@ const routes = computed<Route[]>(() => [
|
|
|
104
104
|
{{ r.badge }}
|
|
105
105
|
</UBadge>
|
|
106
106
|
</div>
|
|
107
|
-
<p class="mt-0.5 text-
|
|
107
|
+
<p class="mt-0.5 text-sm leading-relaxed text-muted">{{ r.body }}</p>
|
|
108
108
|
</div>
|
|
109
109
|
<UButton
|
|
110
110
|
size="sm"
|
|
@@ -118,7 +118,7 @@ const routes = computed<Route[]>(() => [
|
|
|
118
118
|
</div>
|
|
119
119
|
</div>
|
|
120
120
|
|
|
121
|
-
<p class="text-
|
|
121
|
+
<p class="text-2xs leading-relaxed text-dimmed">
|
|
122
122
|
{{ t('providers.onboarding.operatorNote') }}
|
|
123
123
|
</p>
|
|
124
124
|
</div>
|
|
@@ -19,6 +19,7 @@ import { computed, ref, watch } from 'vue'
|
|
|
19
19
|
import { providerCachesPrompts } from '@cat-factory/contracts'
|
|
20
20
|
import type { ApiKey, ApiKeyProvider } from '~/types/domain'
|
|
21
21
|
import SecretInput from '~/components/common/SecretInput.vue'
|
|
22
|
+
import SectionLabel from '~/components/common/SectionLabel.vue'
|
|
22
23
|
|
|
23
24
|
const props = withDefaults(defineProps<{ accountId?: string; category?: 'direct' | 'proxy' }>(), {
|
|
24
25
|
category: 'direct',
|
|
@@ -264,13 +265,13 @@ async function remove(k: ApiKey) {
|
|
|
264
265
|
<template>
|
|
265
266
|
<div class="space-y-4">
|
|
266
267
|
<div>
|
|
267
|
-
<
|
|
268
|
+
<SectionLabel as="h4">
|
|
268
269
|
{{
|
|
269
270
|
category === 'proxy'
|
|
270
271
|
? t('providers.apiKeys.proxyHeading')
|
|
271
272
|
: t('providers.apiKeys.directHeading')
|
|
272
273
|
}}
|
|
273
|
-
</
|
|
274
|
+
</SectionLabel>
|
|
274
275
|
<template v-if="category === 'proxy'">
|
|
275
276
|
<p v-if="isAccount" class="mt-1 text-sm text-muted">
|
|
276
277
|
{{ t('providers.apiKeys.proxyAccountIntro') }}
|
|
@@ -328,14 +329,15 @@ async function remove(k: ApiKey) {
|
|
|
328
329
|
>
|
|
329
330
|
<li v-for="(step, i) in selected.steps" :key="i">{{ step }}</li>
|
|
330
331
|
<li>
|
|
331
|
-
<
|
|
332
|
-
|
|
332
|
+
<ULink
|
|
333
|
+
raw
|
|
334
|
+
:to="selected.url"
|
|
333
335
|
target="_blank"
|
|
334
336
|
rel="noopener noreferrer"
|
|
335
337
|
class="text-primary underline"
|
|
336
338
|
>
|
|
337
339
|
{{ t('providers.apiKeys.openKeys', { provider: selected.label }) }}
|
|
338
|
-
</
|
|
340
|
+
</ULink>
|
|
339
341
|
</li>
|
|
340
342
|
</ol>
|
|
341
343
|
|
|
@@ -343,7 +345,7 @@ async function remove(k: ApiKey) {
|
|
|
343
345
|
the caching flavour, so long agentic runs stop re-billing the whole prompt. -->
|
|
344
346
|
<p
|
|
345
347
|
v-if="cachesPrompts(selected.value)"
|
|
346
|
-
class="flex items-center gap-1.5 text-
|
|
348
|
+
class="flex items-center gap-1.5 text-xs text-app-success-400/90"
|
|
347
349
|
>
|
|
348
350
|
<UIcon name="i-lucide-zap" class="h-3.5 w-3.5 shrink-0" />
|
|
349
351
|
{{ t('providers.apiKeys.cachingNote', { provider: selected.label }) }}
|
|
@@ -380,9 +382,9 @@ async function remove(k: ApiKey) {
|
|
|
380
382
|
|
|
381
383
|
<!-- connected keys for the selected scope -->
|
|
382
384
|
<div v-if="connected.length" class="space-y-2">
|
|
383
|
-
<
|
|
385
|
+
<SectionLabel as="h5">
|
|
384
386
|
{{ t('providers.apiKeys.connected', { count: connected.length }) }}
|
|
385
|
-
</
|
|
387
|
+
</SectionLabel>
|
|
386
388
|
<div
|
|
387
389
|
v-for="k in connected"
|
|
388
390
|
:key="k.id"
|
|
@@ -395,7 +397,7 @@ async function remove(k: ApiKey) {
|
|
|
395
397
|
<UBadge v-if="!k.enabled" color="neutral" variant="subtle" size="sm" class="ms-2">
|
|
396
398
|
{{ t('providers.apiKeys.disabledBadge') }}
|
|
397
399
|
</UBadge>
|
|
398
|
-
<div class="text-
|
|
400
|
+
<div class="text-2xs tabular-nums text-dimmed">
|
|
399
401
|
{{
|
|
400
402
|
t(
|
|
401
403
|
'providers.apiKeys.usage',
|
|
@@ -7,6 +7,7 @@
|
|
|
7
7
|
import { computed, onBeforeUnmount, onMounted, ref, watch } from 'vue'
|
|
8
8
|
import type { SubscriptionVendor } from '~/types/domain'
|
|
9
9
|
import SecretInput from '~/components/common/SecretInput.vue'
|
|
10
|
+
import SectionLabel from '~/components/common/SectionLabel.vue'
|
|
10
11
|
|
|
11
12
|
const personal = usePersonalSubscriptionsStore()
|
|
12
13
|
const auth = useAuthStore()
|
|
@@ -208,9 +209,9 @@ async function disconnect(v: SubscriptionVendor) {
|
|
|
208
209
|
<template>
|
|
209
210
|
<div class="space-y-3">
|
|
210
211
|
<div>
|
|
211
|
-
<
|
|
212
|
+
<SectionLabel as="h4">
|
|
212
213
|
{{ t('personalSubscriptions.heading') }}
|
|
213
|
-
</
|
|
214
|
+
</SectionLabel>
|
|
214
215
|
<p class="mt-1 text-sm text-muted">{{ t('personalSubscriptions.intro') }}</p>
|
|
215
216
|
</div>
|
|
216
217
|
|
|
@@ -228,7 +229,7 @@ async function disconnect(v: SubscriptionVendor) {
|
|
|
228
229
|
<div>
|
|
229
230
|
<span class="font-medium text-default">{{ sub.label }}</span>
|
|
230
231
|
<span class="ms-2 text-xs text-dimmed">{{ vendorLabel(sub.vendor) }}</span>
|
|
231
|
-
<div class="text-
|
|
232
|
+
<div class="text-2xs text-dimmed">
|
|
232
233
|
<template v-if="sub.expiresAt">
|
|
233
234
|
{{ t('personalSubscriptions.expires', { date: d(new Date(sub.expiresAt), 'short') }) }}
|
|
234
235
|
</template>
|
|
@@ -9,6 +9,7 @@ import { computed, ref, watch } from 'vue'
|
|
|
9
9
|
import type { SubscriptionVendor } from '~/types/domain'
|
|
10
10
|
import IntegrationBackTitle from '~/components/layout/IntegrationBackTitle.vue'
|
|
11
11
|
import SecretInput from '~/components/common/SecretInput.vue'
|
|
12
|
+
import SectionLabel from '~/components/common/SectionLabel.vue'
|
|
12
13
|
|
|
13
14
|
const { t, n } = useI18n()
|
|
14
15
|
const ui = useUiStore()
|
|
@@ -202,7 +203,7 @@ function vendorLabel(v: SubscriptionVendor): string {
|
|
|
202
203
|
class="flex items-center gap-3 rounded-lg border border-primary/30 bg-primary/10 px-3 py-2.5"
|
|
203
204
|
>
|
|
204
205
|
<UIcon name="i-lucide-user" class="h-5 w-5 shrink-0 text-primary" />
|
|
205
|
-
<p class="min-w-0 flex-1 text-
|
|
206
|
+
<p class="min-w-0 flex-1 text-sm text-toned">
|
|
206
207
|
{{ t('providers.vendorCredentials.personalCallout.text') }}
|
|
207
208
|
</p>
|
|
208
209
|
<UButton
|
|
@@ -267,11 +268,11 @@ function vendorLabel(v: SubscriptionVendor): string {
|
|
|
267
268
|
|
|
268
269
|
<!-- connected pool -->
|
|
269
270
|
<div v-if="creds.credentials.length" class="space-y-2">
|
|
270
|
-
<
|
|
271
|
+
<SectionLabel as="h4">
|
|
271
272
|
{{
|
|
272
273
|
t('providers.vendorCredentials.connected', { count: creds.credentials.length })
|
|
273
274
|
}}
|
|
274
|
-
</
|
|
275
|
+
</SectionLabel>
|
|
275
276
|
<div
|
|
276
277
|
v-for="c in creds.credentials"
|
|
277
278
|
:key="c.id"
|
|
@@ -284,7 +285,7 @@ function vendorLabel(v: SubscriptionVendor): string {
|
|
|
284
285
|
<UBadge v-if="!c.enabled" color="neutral" variant="subtle" size="sm" class="ms-2">
|
|
285
286
|
{{ t('providers.vendorCredentials.disabledBadge') }}
|
|
286
287
|
</UBadge>
|
|
287
|
-
<div class="text-
|
|
288
|
+
<div class="text-2xs tabular-nums text-dimmed">
|
|
288
289
|
{{
|
|
289
290
|
t(
|
|
290
291
|
'providers.vendorCredentials.usage',
|