@cat-factory/app 0.112.0 → 0.114.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.
@@ -41,6 +41,16 @@ function reload() {
41
41
  <span class="font-medium text-slate-300">{{ t('app.misconfigured.howToFix') }}</span>
42
42
  {{ problem.remedy }}
43
43
  </p>
44
+ <a
45
+ v-if="problem.docsUrl"
46
+ :href="problem.docsUrl"
47
+ target="_blank"
48
+ rel="noopener noreferrer"
49
+ class="mt-2 inline-flex items-center gap-1 text-sm text-amber-300 hover:text-amber-200"
50
+ >
51
+ <UIcon name="i-lucide-book-open" class="h-4 w-4" />
52
+ {{ t('app.misconfigured.viewDocs') }}
53
+ </a>
44
54
  </li>
45
55
  </ul>
46
56
 
@@ -0,0 +1,247 @@
1
+ <script setup lang="ts">
2
+ // Pre-existing branches of a task's PRIMARY target repo handed to the run as input, in two
3
+ // deliberately-disjoint modes (see `backend/docs/adr/0021-apriori-branches.md`):
4
+ //
5
+ // - `reference` — read-only context (a spike / prototype / prior-art branch). The consuming
6
+ // agents may read it (log/diff/open files) but never commit to or push it.
7
+ // - `working` — the branch the run keeps building inside: it starts from and continues
8
+ // committing into this branch instead of minting `cat-factory/<blockId>` off the default,
9
+ // and the PR / CI-gate / merger all ride it.
10
+ //
11
+ // The cross-entry invariants the backend enforces at the write boundary are mirrored here so a
12
+ // forbidden combination is prevented in the UI rather than surfaced as a rejected write: at most
13
+ // ONE working entry, no duplicate names, the working entry frozen once a PR exists (its head is
14
+ // already pinned everywhere), and no working entry on a multi-repo task (v1 — peer legs would
15
+ // mint the user's branch name across every involved repo).
16
+ import { aprioriWorkingBranch } from '@cat-factory/contracts'
17
+ import type { AprioriBranch, Block } from '~/types/domain'
18
+
19
+ const props = defineProps<{ block: Block }>()
20
+
21
+ const { t } = useI18n()
22
+ const github = useGitHubStore()
23
+ const board = useBoardStore()
24
+
25
+ // The primary target repo is the one bound to the task's owning service frame — the sole
26
+ // repo↔frame linkage. Branch options come from the existing per-repo branches projection.
27
+ const frame = computed(() => board.serviceOf(props.block))
28
+ const repo = computed(() => (frame.value ? github.repoForBlock(frame.value.id) : undefined))
29
+ const repoBranches = computed(() => {
30
+ const id = repo.value?.githubId
31
+ return id != null ? (github.branches[id] ?? []) : []
32
+ })
33
+
34
+ // Load (and cache) the target repo's branches once it's resolved. Best-effort — a fetch failure
35
+ // just leaves the picker empty (the same repo the run clones, so a real failure is rare).
36
+ watch(
37
+ () => repo.value?.githubId,
38
+ (id) => {
39
+ if (id != null) void github.loadBranches(id).catch(() => {})
40
+ },
41
+ { immediate: true },
42
+ )
43
+
44
+ // Write-boundary mirrors:
45
+ // - a PR pins the run's branch, so the working entry is FROZEN (references stay editable);
46
+ // - a multi-repo task (any involved service) BLOCKS working mode entirely.
47
+ const hasPullRequest = computed(() => !!props.block.pullRequest)
48
+ const isMultiRepo = computed(() => (props.block.involvedServiceIds ?? []).length > 0)
49
+
50
+ // A working entry set while single-repo becomes invalid the moment the task gains a second
51
+ // involved service (the backend rejects a working entry on a multi-repo task). Rather than let
52
+ // that stale entry ride along and fail the NEXT write wholesale, demote any working entry to
53
+ // `reference` on a multi-repo task — applied both to what we render and to what we persist, so
54
+ // the invariant is mirrored (not surfaced as a rejected write) and self-heals on the next save.
55
+ function normalize(entries: AprioriBranch[]): AprioriBranch[] {
56
+ if (!isMultiRepo.value) return entries
57
+ return entries.map((b) => (b.mode === 'working' ? { ...b, mode: 'reference' } : b))
58
+ }
59
+
60
+ const attached = computed<AprioriBranch[]>(() => normalize(props.block.aprioriBranches ?? []))
61
+ const attachedNames = computed(() => new Set(attached.value.map((b) => b.name)))
62
+ const workingName = computed(() => aprioriWorkingBranch(attached.value))
63
+
64
+ function isProtected(name: string): boolean {
65
+ return repoBranches.value.find((b) => b.name === name)?.protected === true
66
+ }
67
+ // Building the run inside the repo's base branch has nothing to diff and no PR to open, so it's
68
+ // rejected at dispatch — surface it here as a non-selectable working target.
69
+ function isBaseBranch(name: string): boolean {
70
+ return repo.value?.defaultBranch != null && name === repo.value.defaultBranch
71
+ }
72
+
73
+ function save(next: AprioriBranch[]) {
74
+ board.updateBlock(props.block.id, { aprioriBranches: normalize(next) })
75
+ }
76
+
77
+ // ---- add / remove -----------------------------------------------------------
78
+ // The picker adds a branch as `reference` (the safe default — promoting to working is an
79
+ // explicit second action, guarded below).
80
+ const pickedName = ref<string | undefined>(undefined)
81
+ watch(pickedName, (name) => {
82
+ if (name === undefined) return
83
+ pickedName.value = undefined
84
+ if (attachedNames.value.has(name)) return
85
+ save([...attached.value, { name, mode: 'reference' }])
86
+ })
87
+
88
+ const branchItems = computed(() =>
89
+ repoBranches.value.map((b) => ({
90
+ label: b.name,
91
+ value: b.name,
92
+ disabled: attachedNames.value.has(b.name),
93
+ })),
94
+ )
95
+
96
+ function remove(name: string) {
97
+ save(attached.value.filter((b) => b.name !== name))
98
+ }
99
+
100
+ // ---- mode toggle ------------------------------------------------------------
101
+ // Promoting an entry to `working` demotes any existing working entry to `reference` in the same
102
+ // write, so the single-working invariant holds without an intermediate rejected state.
103
+ function setMode(name: string, mode: AprioriBranch['mode']) {
104
+ save(
105
+ attached.value.map((b) => {
106
+ if (b.name === name) return { ...b, mode }
107
+ if (mode === 'working' && b.mode === 'working') return { ...b, mode: 'reference' }
108
+ return b
109
+ }),
110
+ )
111
+ }
112
+
113
+ // Whether a reference entry may be promoted to working: blocked outright on a multi-repo task,
114
+ // on the base branch, and once a PR has frozen the working slot.
115
+ function canPromote(name: string): boolean {
116
+ return !isMultiRepo.value && !hasPullRequest.value && !isBaseBranch(name)
117
+ }
118
+ // The working entry is frozen once the PR exists (changing/dropping it would silently diverge).
119
+ const workingFrozen = computed(() => hasPullRequest.value && workingName.value !== undefined)
120
+
121
+ function modeMenu(entry: AprioriBranch) {
122
+ const items: Array<{ label: string; icon: string; onSelect: () => void }> = []
123
+ if (entry.mode === 'working') {
124
+ if (!workingFrozen.value) {
125
+ items.push({
126
+ label: t('inspector.aprioriBranches.mode.reference'),
127
+ icon: 'i-lucide-book-open-text',
128
+ onSelect: () => setMode(entry.name, 'reference'),
129
+ })
130
+ }
131
+ } else if (canPromote(entry.name)) {
132
+ items.push({
133
+ label: t('inspector.aprioriBranches.mode.working'),
134
+ icon: 'i-lucide-hammer',
135
+ onSelect: () => setMode(entry.name, 'working'),
136
+ })
137
+ }
138
+ return [items]
139
+ }
140
+ // The mode dropdown is inert when there's no alternative mode to switch to.
141
+ function modeToggleDisabled(entry: AprioriBranch): boolean {
142
+ return modeMenu(entry)[0]!.length === 0
143
+ }
144
+ // The working entry can't be removed while frozen by a PR; reference entries are always removable.
145
+ function removeDisabled(entry: AprioriBranch): boolean {
146
+ return entry.mode === 'working' && workingFrozen.value
147
+ }
148
+ </script>
149
+
150
+ <template>
151
+ <div v-if="repo" data-testid="apriori-branches">
152
+ <div class="mb-1 flex items-center justify-between">
153
+ <span class="text-[11px] font-semibold uppercase tracking-wide text-slate-400">
154
+ {{ t('inspector.aprioriBranches.title') }}
155
+ </span>
156
+ </div>
157
+
158
+ <!-- Attached branches: one row each — name, mode badge + toggle, remove. -->
159
+ <div v-if="attached.length" class="mb-1.5 space-y-1">
160
+ <div
161
+ v-for="entry in attached"
162
+ :key="entry.name"
163
+ class="flex items-center gap-1.5"
164
+ data-testid="apriori-branch-row"
165
+ >
166
+ <UBadge
167
+ size="sm"
168
+ variant="soft"
169
+ :color="entry.mode === 'working' ? 'primary' : 'neutral'"
170
+ class="min-w-0"
171
+ :data-mode="entry.mode"
172
+ data-testid="apriori-branch-chip"
173
+ >
174
+ <UIcon
175
+ :name="entry.mode === 'working' ? 'i-lucide-hammer' : 'i-lucide-book-open-text'"
176
+ class="me-1 h-3 w-3 shrink-0"
177
+ />
178
+ <span class="truncate">{{ entry.name }}</span>
179
+ </UBadge>
180
+
181
+ <UDropdownMenu :items="modeMenu(entry)">
182
+ <UButton
183
+ size="xs"
184
+ variant="ghost"
185
+ color="neutral"
186
+ trailing-icon="i-lucide-chevron-down"
187
+ :disabled="modeToggleDisabled(entry)"
188
+ data-testid="apriori-branch-mode"
189
+ >
190
+ {{
191
+ entry.mode === 'working'
192
+ ? t('inspector.aprioriBranches.mode.working')
193
+ : t('inspector.aprioriBranches.mode.reference')
194
+ }}
195
+ </UButton>
196
+ </UDropdownMenu>
197
+
198
+ <UButton
199
+ color="neutral"
200
+ variant="link"
201
+ size="xs"
202
+ icon="i-lucide-x"
203
+ class="ms-auto"
204
+ :disabled="removeDisabled(entry)"
205
+ :aria-label="t('inspector.aprioriBranches.remove', { branch: entry.name })"
206
+ data-testid="apriori-branch-remove"
207
+ @click="remove(entry.name)"
208
+ />
209
+ </div>
210
+ </div>
211
+
212
+ <!-- The picker: only usable once the workspace's GitHub App is connected. -->
213
+ <UInputMenu
214
+ v-if="github.connected"
215
+ v-model="pickedName"
216
+ :items="branchItems"
217
+ value-key="value"
218
+ icon="i-lucide-git-branch"
219
+ :placeholder="t('inspector.aprioriBranches.searchPlaceholder')"
220
+ class="w-full"
221
+ data-testid="apriori-branch-search"
222
+ />
223
+ <div v-else class="text-[11px] text-slate-500">
224
+ {{ t('inspector.aprioriBranches.connectFirst') }}
225
+ </div>
226
+
227
+ <!-- A protected branch pushed to by the run is likely to be rejected — warn, don't block. -->
228
+ <div
229
+ v-if="workingName && isProtected(workingName)"
230
+ class="mt-1.5 flex items-start gap-1.5 rounded-md border border-amber-500/40 bg-amber-950/40 p-2 text-[11px] text-amber-200/90"
231
+ data-testid="apriori-branch-protected-warning"
232
+ >
233
+ <UIcon name="i-lucide-triangle-alert" class="mt-0.5 h-3.5 w-3.5 shrink-0 text-amber-400" />
234
+ <span>{{ t('inspector.aprioriBranches.protectedWarning', { branch: workingName }) }}</span>
235
+ </div>
236
+
237
+ <div class="mt-1 text-[11px] text-slate-500">
238
+ {{ t('inspector.aprioriBranches.hint') }}
239
+ <template v-if="isMultiRepo">
240
+ {{ t('inspector.aprioriBranches.multiRepoHint') }}
241
+ </template>
242
+ <template v-else-if="workingFrozen">
243
+ {{ t('inspector.aprioriBranches.frozenHint') }}
244
+ </template>
245
+ </div>
246
+ </div>
247
+ </template>
@@ -6,6 +6,7 @@ import type { WritebackOverride } from '~/types/tracker'
6
6
  import { riskPolicyOptionLabel, riskPolicySummary } from '~/utils/riskPolicy'
7
7
  import { pipelineAllowedForManualStart } from '~/utils/pipeline'
8
8
  import InspectorSection from '~/components/panels/inspector/InspectorSection.vue'
9
+ import TaskAprioriBranches from '~/components/panels/inspector/TaskAprioriBranches.vue'
9
10
 
10
11
  const props = defineProps<{ block: Block }>()
11
12
 
@@ -480,6 +481,10 @@ const technicalLabel = computed(() => {
480
481
  </div>
481
482
  </div>
482
483
 
484
+ <!-- apriori branches: pre-existing branches of the target repo handed to the run as input
485
+ (a read-only reference, or the working branch the run builds inside) -->
486
+ <TaskAprioriBranches :block="block" />
487
+
483
488
  <!-- reference repositories: read-only repos the doc-writer reads while drafting (doc tasks) -->
484
489
  <DocReferenceRepos v-if="block.taskType === 'document'" :block="block" />
485
490
 
@@ -29,6 +29,7 @@ export type {
29
29
  Block,
30
30
  PullRequestRef,
31
31
  ReferenceRepo,
32
+ AprioriBranch,
32
33
  CloudProvider,
33
34
  InstanceSize,
34
35
  ProvisionType,
@@ -1240,6 +1240,20 @@
1240
1240
  "involvedServicesEmpty": "Keine verbundenen Services. Verbinde Services am Service-Frame, um sie hier auszuwählen.",
1241
1241
  "involvedServiceStale": "Nicht mehr mit dem Service dieser Aufgabe verbunden; wird bei der nächsten Änderung entfernt."
1242
1242
  },
1243
+ "aprioriBranches": {
1244
+ "title": "Vorhandene Branches",
1245
+ "mode": {
1246
+ "reference": "Referenz",
1247
+ "working": "Arbeitsbranch"
1248
+ },
1249
+ "remove": "{branch} entfernen",
1250
+ "searchPlaceholder": "Vorhandenen Branch hinzufügen…",
1251
+ "connectFirst": "Verbinde GitHub, um vorhandene Branches hinzuzufügen.",
1252
+ "protectedWarning": "{branch} ist ein geschützter Branch. Pushes aus dem Lauf werden möglicherweise abgelehnt.",
1253
+ "multiRepoHint": "Der Arbeitsmodus ist nicht verfügbar, solange diese Aufgabe mehr als einen Service umfasst.",
1254
+ "frozenHint": "Der Arbeitsbranch ist gesperrt, da für diese Aufgabe bereits ein Pull Request existiert.",
1255
+ "hint": "Übergib dieser Aufgabe vorhandene Branches ihres Repositorys. Ein Referenzbranch ist schreibgeschützter Kontext, den die Agenten einsehen dürfen; im einzelnen Arbeitsbranch baut der Lauf weiter, statt einen neuen Branch anzulegen."
1256
+ },
1243
1257
  "referenceRepos": {
1244
1258
  "title": "Referenz-Repositories",
1245
1259
  "remove": "{repo} entfernen",
@@ -3640,6 +3654,7 @@
3640
3654
  "title": "Backend nicht konfiguriert",
3641
3655
  "intro": "Der Server wurde gestartet, kann aber erst laufen, wenn die folgenden Einstellungen vorhanden sind. Ergänze die fehlenden Werte in deiner Umgebung und lade neu.",
3642
3656
  "howToFix": "So behebst du es:",
3657
+ "viewDocs": "Dokumentation ansehen",
3643
3658
  "reload": "Neu laden",
3644
3659
  "hint": "Hier werden nur Variablennamen und deren Einrichtung angezeigt, niemals geheime Werte."
3645
3660
  }
@@ -9,6 +9,7 @@
9
9
  "title": "Backend not configured",
10
10
  "intro": "The server started but can't run until the settings below are provided. Add the missing values to your environment, then reload.",
11
11
  "howToFix": "How to fix:",
12
+ "viewDocs": "View documentation",
12
13
  "reload": "Reload",
13
14
  "hint": "Only variable names and how to set them are shown here, never any secret values."
14
15
  }
@@ -978,6 +979,20 @@
978
979
  "involvedServicesEmpty": "No connected services. Connect services on the service frame to select them here.",
979
980
  "involvedServiceStale": "No longer connected to this task's service; it is dropped on the next change."
980
981
  },
982
+ "aprioriBranches": {
983
+ "title": "Existing branches",
984
+ "mode": {
985
+ "reference": "Reference",
986
+ "working": "Working"
987
+ },
988
+ "remove": "Remove {branch}",
989
+ "searchPlaceholder": "Add an existing branch…",
990
+ "connectFirst": "Connect GitHub to add existing branches.",
991
+ "protectedWarning": "{branch} is a protected branch. Pushes from the run may be rejected.",
992
+ "multiRepoHint": "Working mode is unavailable while this task involves more than one service.",
993
+ "frozenHint": "The working branch is locked because a pull request already exists for this task.",
994
+ "hint": "Hand this task pre-existing branches of its repository. A reference branch is read-only context the agents may inspect; the single working branch is where the run keeps building instead of a new branch."
995
+ },
981
996
  "referenceRepos": {
982
997
  "title": "Reference repositories",
983
998
  "remove": "Remove {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "Backend sin configurar",
10
10
  "intro": "El servidor se inició pero no puede funcionar hasta que se proporcionen los ajustes siguientes. Añade los valores que faltan a tu entorno y vuelve a cargar.",
11
11
  "howToFix": "Cómo solucionarlo:",
12
+ "viewDocs": "Ver la documentación",
12
13
  "reload": "Recargar",
13
14
  "hint": "Aquí solo se muestran los nombres de las variables y cómo definirlas, nunca valores secretos."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "No hay servicios conectados. Conecta servicios en el marco del servicio para seleccionarlos aquí.",
925
926
  "involvedServiceStale": "Ya no está conectado al servicio de esta tarea; se eliminará con el próximo cambio."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "Ramas existentes",
930
+ "mode": {
931
+ "reference": "Referencia",
932
+ "working": "Trabajo"
933
+ },
934
+ "remove": "Eliminar {branch}",
935
+ "searchPlaceholder": "Añadir una rama existente…",
936
+ "connectFirst": "Conecta GitHub para añadir ramas existentes.",
937
+ "protectedWarning": "{branch} es una rama protegida. Los envíos de la ejecución podrían ser rechazados.",
938
+ "multiRepoHint": "El modo de trabajo no está disponible mientras esta tarea involucre más de un servicio.",
939
+ "frozenHint": "La rama de trabajo está bloqueada porque ya existe una solicitud de incorporación para esta tarea.",
940
+ "hint": "Entrega a esta tarea ramas ya existentes de su repositorio. Una rama de referencia es contexto de solo lectura que los agentes pueden inspeccionar; en la única rama de trabajo la ejecución sigue construyendo en lugar de crear una rama nueva."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Repositorios de referencia",
929
944
  "remove": "Quitar {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "Backend non configuré",
10
10
  "intro": "Le serveur a démarré mais ne peut pas fonctionner tant que les paramètres ci-dessous ne sont pas fournis. Ajoutez les valeurs manquantes à votre environnement, puis rechargez.",
11
11
  "howToFix": "Comment corriger :",
12
+ "viewDocs": "Voir la documentation",
12
13
  "reload": "Recharger",
13
14
  "hint": "Seuls les noms des variables et la façon de les définir sont affichés ici, jamais de valeurs secrètes."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "Aucun service connecté. Connectez des services sur le cadre du service pour les sélectionner ici.",
925
926
  "involvedServiceStale": "N'est plus connecté au service de cette tâche ; il sera retiré au prochain changement."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "Branches existantes",
930
+ "mode": {
931
+ "reference": "Référence",
932
+ "working": "Travail"
933
+ },
934
+ "remove": "Supprimer {branch}",
935
+ "searchPlaceholder": "Ajouter une branche existante…",
936
+ "connectFirst": "Connectez GitHub pour ajouter des branches existantes.",
937
+ "protectedWarning": "{branch} est une branche protégée. Les poussées de l'exécution peuvent être rejetées.",
938
+ "multiRepoHint": "Le mode travail est indisponible tant que cette tâche implique plusieurs services.",
939
+ "frozenHint": "La branche de travail est verrouillée car une pull request existe déjà pour cette tâche.",
940
+ "hint": "Confiez à cette tâche des branches déjà existantes de son dépôt. Une branche de référence est un contexte en lecture seule que les agents peuvent consulter ; sur l'unique branche de travail, l'exécution continue de construire au lieu de créer une nouvelle branche."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Dépôts de référence",
929
944
  "remove": "Retirer {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "השרת אינו מוגדר",
10
10
  "intro": "השרת עלה אך אינו יכול לפעול עד שהערכים הבאים יסופקו. הוסיפו את הערכים החסרים לסביבה שלכם וטענו מחדש.",
11
11
  "howToFix": "איך לתקן:",
12
+ "viewDocs": "צפייה בתיעוד",
12
13
  "reload": "טעינה מחדש",
13
14
  "hint": "כאן מוצגים רק שמות המשתנים וכיצד להגדיר אותם, לעולם לא ערכים סודיים."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "אין שירותים מחוברים. חברו שירותים במסגרת השירות כדי לבחור אותם כאן.",
925
926
  "involvedServiceStale": "כבר לא מחובר לשירות של משימה זו; הוא יוסר בשינוי הבא."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "ענפים קיימים",
930
+ "mode": {
931
+ "reference": "הפניה",
932
+ "working": "עבודה"
933
+ },
934
+ "remove": "הסר את {branch}",
935
+ "searchPlaceholder": "הוסף ענף קיים…",
936
+ "connectFirst": "התחבר ל‑GitHub כדי להוסיף ענפים קיימים.",
937
+ "protectedWarning": "{branch} הוא ענף מוגן. דחיפות מההרצה עלולות להידחות.",
938
+ "multiRepoHint": "מצב עבודה אינו זמין כאשר משימה זו מערבת יותר משירות אחד.",
939
+ "frozenHint": "ענף העבודה נעול מכיוון שכבר קיימת בקשת משיכה למשימה זו.",
940
+ "hint": "מסרו למשימה זו ענפים קיימים של המאגר שלה. ענף הפניה הוא הקשר לקריאה בלבד שהסוכנים רשאים לבחון; בענף העבודה היחיד ההרצה ממשיכה לבנות במקום ליצור ענף חדש."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Reference repositories",
929
944
  "remove": "Remove {repo}",
@@ -1240,6 +1240,20 @@
1240
1240
  "involvedServicesEmpty": "Nessun servizio connesso. Connetti i servizi sul frame del servizio per selezionarli qui.",
1241
1241
  "involvedServiceStale": "Non piu' connesso al servizio di questa attivita'; verra' rimosso alla prossima modifica."
1242
1242
  },
1243
+ "aprioriBranches": {
1244
+ "title": "Branch esistenti",
1245
+ "mode": {
1246
+ "reference": "Riferimento",
1247
+ "working": "Lavoro"
1248
+ },
1249
+ "remove": "Rimuovi {branch}",
1250
+ "searchPlaceholder": "Aggiungi un branch esistente…",
1251
+ "connectFirst": "Connetti GitHub per aggiungere branch esistenti.",
1252
+ "protectedWarning": "{branch} e' un branch protetto. I push dell'esecuzione potrebbero essere rifiutati.",
1253
+ "multiRepoHint": "La modalita' di lavoro non e' disponibile finche' questa attivita' coinvolge piu' di un servizio.",
1254
+ "frozenHint": "Il branch di lavoro e' bloccato perche' esiste gia' una pull request per questa attivita'.",
1255
+ "hint": "Affida a questa attivita' branch gia' esistenti del suo repository. Un branch di riferimento e' contesto in sola lettura che gli agenti possono ispezionare; nell'unico branch di lavoro l'esecuzione continua a costruire invece di creare un nuovo branch."
1256
+ },
1243
1257
  "referenceRepos": {
1244
1258
  "title": "Repository di riferimento",
1245
1259
  "remove": "Rimuovi {repo}",
@@ -3640,6 +3654,7 @@
3640
3654
  "title": "Backend non configurato",
3641
3655
  "intro": "Il server è avviato ma non può funzionare finché non vengono forniti i parametri seguenti. Aggiungi i valori mancanti al tuo ambiente e ricarica.",
3642
3656
  "howToFix": "Come risolvere:",
3657
+ "viewDocs": "Vedi la documentazione",
3643
3658
  "reload": "Ricarica",
3644
3659
  "hint": "Qui vengono mostrati solo i nomi delle variabili e come impostarle, mai valori segreti."
3645
3660
  }
@@ -9,6 +9,7 @@
9
9
  "title": "バックエンドが設定されていません",
10
10
  "intro": "サーバーは起動しましたが、以下の設定が指定されるまで動作できません。不足している値を環境に追加してから再読み込みしてください。",
11
11
  "howToFix": "対処方法:",
12
+ "viewDocs": "ドキュメントを表示",
12
13
  "reload": "再読み込み",
13
14
  "hint": "ここに表示されるのは変数名と設定方法のみで、秘密の値は表示されません。"
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "接続済みのサービスはありません。ここで選択するには、サービスフレームでサービスを接続してください。",
925
926
  "involvedServiceStale": "このタスクのサービスとの接続が解除されています。次回の変更時に削除されます。"
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "既存のブランチ",
930
+ "mode": {
931
+ "reference": "参照",
932
+ "working": "作業"
933
+ },
934
+ "remove": "{branch} を削除",
935
+ "searchPlaceholder": "既存のブランチを追加…",
936
+ "connectFirst": "既存のブランチを追加するには GitHub を接続してください。",
937
+ "protectedWarning": "{branch} は保護されたブランチです。実行からのプッシュは拒否される場合があります。",
938
+ "multiRepoHint": "このタスクが複数のサービスにまたがる間は、作業モードを利用できません。",
939
+ "frozenHint": "このタスクには既にプルリクエストが存在するため、作業ブランチはロックされています。",
940
+ "hint": "このタスクにリポジトリの既存ブランチを渡します。参照ブランチはエージェントが閲覧できる読み取り専用のコンテキストです。唯一の作業ブランチでは、新しいブランチを作成せずに実行がそこで作業を続けます。"
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Reference repositories",
929
944
  "remove": "Remove {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "Backend nie jest skonfigurowany",
10
10
  "intro": "Serwer wystartował, ale nie zadziała, dopóki nie uzupełnisz poniższych ustawień. Dodaj brakujące wartości do swojego środowiska i odśwież.",
11
11
  "howToFix": "Jak naprawić:",
12
+ "viewDocs": "Zobacz dokumentację",
12
13
  "reload": "Odśwież",
13
14
  "hint": "Tutaj pokazujemy tylko nazwy zmiennych i sposób ich ustawienia, nigdy wartości sekretnych."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "Brak połączonych usług. Połącz usługi na ramce usługi, aby móc je tutaj wybrać.",
925
926
  "involvedServiceStale": "Nie jest już połączona z usługą tego zadania; zostanie usunięta przy następnej zmianie."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "Istniejące gałęzie",
930
+ "mode": {
931
+ "reference": "Referencyjna",
932
+ "working": "Robocza"
933
+ },
934
+ "remove": "Usuń {branch}",
935
+ "searchPlaceholder": "Dodaj istniejącą gałąź…",
936
+ "connectFirst": "Połącz GitHub, aby dodać istniejące gałęzie.",
937
+ "protectedWarning": "{branch} to chroniona gałąź. Wypchnięcia z uruchomienia mogą zostać odrzucone.",
938
+ "multiRepoHint": "Tryb roboczy jest niedostępny, gdy to zadanie obejmuje więcej niż jedną usługę.",
939
+ "frozenHint": "Gałąź robocza jest zablokowana, ponieważ dla tego zadania istnieje już pull request.",
940
+ "hint": "Przekaż temu zadaniu istniejące gałęzie jego repozytorium. Gałąź referencyjna to kontekst tylko do odczytu, który agenci mogą przeglądać; w jedynej gałęzi roboczej uruchomienie kontynuuje pracę zamiast tworzyć nową gałąź."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Reference repositories",
929
944
  "remove": "Remove {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "Arka uç yapılandırılmadı",
10
10
  "intro": "Sunucu başladı ancak aşağıdaki ayarlar sağlanana kadar çalışamaz. Eksik değerleri ortamınıza ekleyip yeniden yükleyin.",
11
11
  "howToFix": "Nasıl düzeltilir:",
12
+ "viewDocs": "Belgeleri görüntüle",
12
13
  "reload": "Yeniden yükle",
13
14
  "hint": "Burada yalnızca değişken adları ve nasıl ayarlanacakları gösterilir, asla gizli değerler değil."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "Bağlı servis yok. Burada seçebilmek için servis çerçevesinde servisleri bağlayın.",
925
926
  "involvedServiceStale": "Artık bu görevin servisine bağlı değil; bir sonraki değişiklikte kaldırılacak."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "Mevcut dallar",
930
+ "mode": {
931
+ "reference": "Referans",
932
+ "working": "Çalışma"
933
+ },
934
+ "remove": "{branch} öğesini kaldır",
935
+ "searchPlaceholder": "Mevcut bir dal ekle…",
936
+ "connectFirst": "Mevcut dalları eklemek için GitHub'ı bağlayın.",
937
+ "protectedWarning": "{branch} korumalı bir dal. Çalıştırmadan yapılan göndermeler reddedilebilir.",
938
+ "multiRepoHint": "Bu görev birden fazla servisi kapsadığı sürece çalışma modu kullanılamaz.",
939
+ "frozenHint": "Bu görev için zaten bir çekme isteği bulunduğundan çalışma dalı kilitli.",
940
+ "hint": "Bu göreve deposunun mevcut dallarını verin. Referans dalı, ajanların inceleyebileceği salt okunur bir bağlamdır; tek çalışma dalında çalıştırma, yeni bir dal oluşturmak yerine orada geliştirmeye devam eder."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Reference repositories",
929
944
  "remove": "Remove {repo}",
@@ -9,6 +9,7 @@
9
9
  "title": "Бекенд не налаштовано",
10
10
  "intro": "Сервер запустився, але не працюватиме, доки не буде задано наведені нижче параметри. Додайте відсутні значення до свого середовища та перезавантажте.",
11
11
  "howToFix": "Як виправити:",
12
+ "viewDocs": "Переглянути документацію",
12
13
  "reload": "Перезавантажити",
13
14
  "hint": "Тут показано лише назви змінних і як їх задати, ніколи не секретні значення."
14
15
  }
@@ -924,6 +925,20 @@
924
925
  "involvedServicesEmpty": "Немає з'єднаних сервісів. З'єднайте сервіси на рамці сервісу, щоб вибрати їх тут.",
925
926
  "involvedServiceStale": "Більше не з'єднаний із сервісом цього завдання; буде видалений під час наступної зміни."
926
927
  },
928
+ "aprioriBranches": {
929
+ "title": "Наявні гілки",
930
+ "mode": {
931
+ "reference": "Довідкова",
932
+ "working": "Робоча"
933
+ },
934
+ "remove": "Вилучити {branch}",
935
+ "searchPlaceholder": "Додати наявну гілку…",
936
+ "connectFirst": "Під'єднайте GitHub, щоб додавати наявні гілки.",
937
+ "protectedWarning": "{branch} — захищена гілка. Надсилання з виконання можуть бути відхилені.",
938
+ "multiRepoHint": "Робочий режим недоступний, доки це завдання охоплює більше ніж один сервіс.",
939
+ "frozenHint": "Робочу гілку заблоковано, оскільки для цього завдання вже існує pull request.",
940
+ "hint": "Передайте цьому завданню наявні гілки його репозиторію. Довідкова гілка — це контекст лише для читання, який агенти можуть переглядати; в єдиній робочій гілці виконання продовжує розробку замість створення нової гілки."
941
+ },
927
942
  "referenceRepos": {
928
943
  "title": "Reference repositories",
929
944
  "remove": "Remove {repo}",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cat-factory/app",
3
- "version": "0.112.0",
3
+ "version": "0.114.0",
4
4
  "description": "Reusable Nuxt layer for the Agent Architecture Board SPA (components, stores, composables, pages). Consume it from a thin deployment app via `extends: ['@cat-factory/app']` and point it at your backend with NUXT_PUBLIC_API_BASE. See deploy/frontend for an example.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -34,7 +34,7 @@
34
34
  "valibot": "^1.4.2",
35
35
  "vue": "3.5.39",
36
36
  "wretch": "^3.0.9",
37
- "@cat-factory/contracts": "0.125.0"
37
+ "@cat-factory/contracts": "0.126.0"
38
38
  },
39
39
  "devDependencies": {
40
40
  "@toad-contracts/testing": "0.3.2",