@cat-factory/app 0.239.0 → 0.241.1

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 (42) hide show
  1. package/README.md +11 -1
  2. package/app/components/documents/DocumentImportModal.vue +2 -0
  3. package/app/components/documents/DocumentSyncState.logic.spec.ts +33 -0
  4. package/app/components/documents/DocumentSyncState.logic.ts +38 -0
  5. package/app/components/documents/DocumentSyncState.vue +181 -0
  6. package/app/components/documents/TaskContextDocs.vue +21 -10
  7. package/app/components/layout/AccountAuditLog.logic.spec.ts +107 -0
  8. package/app/components/layout/AccountAuditLog.logic.ts +101 -0
  9. package/app/components/layout/AccountAuditLog.vue +148 -0
  10. package/app/components/layout/AccountTeamSettings.vue +39 -0
  11. package/app/components/panels/MergerResultView.vue +1 -0
  12. package/app/components/panels/StepToolServers.logic.spec.ts +41 -1
  13. package/app/components/panels/StepToolServers.logic.ts +38 -0
  14. package/app/components/panels/StepToolServers.vue +28 -8
  15. package/app/components/riskPolicy/RiskPolicyPicker.logic.ts +7 -1
  16. package/app/composables/api/accounts.ts +12 -0
  17. package/app/composables/api/documents.ts +9 -0
  18. package/app/composables/useDocumentFreshness.ts +111 -0
  19. package/app/stores/accounts.audit.spec.ts +74 -0
  20. package/app/stores/accounts.ts +75 -0
  21. package/app/stores/board/moveRefusal.spec.ts +40 -0
  22. package/app/stores/board/moveRefusal.ts +34 -0
  23. package/app/stores/board/placement.ts +6 -1
  24. package/app/stores/documents.spec.ts +156 -0
  25. package/app/stores/documents.ts +14 -0
  26. package/app/stores/notifications.ts +40 -7
  27. package/app/stores/workspace/commands.ts +1 -1
  28. package/app/stores/workspace/hydrate.ts +12 -7
  29. package/app/stores/workspace.spec.ts +91 -4
  30. package/app/stores/workspace.ts +18 -13
  31. package/app/types/documents.ts +4 -0
  32. package/i18n/locales/de.json +73 -3
  33. package/i18n/locales/en.json +73 -3
  34. package/i18n/locales/es.json +73 -3
  35. package/i18n/locales/fr.json +73 -3
  36. package/i18n/locales/he.json +73 -3
  37. package/i18n/locales/it.json +73 -3
  38. package/i18n/locales/ja.json +73 -3
  39. package/i18n/locales/pl.json +73 -3
  40. package/i18n/locales/tr.json +73 -3
  41. package/i18n/locales/uk.json +73 -3
  42. package/package.json +2 -2
@@ -9,6 +9,8 @@ import type {
9
9
  } from '~/types/domain'
10
10
  import { useAccountsStore } from '~/stores/accounts'
11
11
  import { useBoardStore } from '~/stores/board'
12
+ import { useNotificationsStore } from '~/stores/notifications'
13
+ import type { LiveWriteBaselines } from '~/stores/workspace/hydrate'
12
14
  import { applySnapshotToStores, resetPerBoardCaches } from '~/stores/workspace/hydrate'
13
15
  import { createWorkspaceCommands } from '~/stores/workspace/commands'
14
16
  import { createInfraSetupState } from '~/stores/workspace/infraSetup'
@@ -81,12 +83,12 @@ export const useWorkspaceStore = defineStore(
81
83
  )
82
84
 
83
85
  /**
84
- * Push a snapshot into the data stores. `boardSince` (captured BEFORE this snapshot's fetch)
85
- * lets the board store preserve any block live-`upsert`ed while the fetch was in flight, so a
86
- * slower refresh can't clobber a newer live status (see `useBoardStore().hydrate`). Omitted by
87
- * fresh loads (init/switch/create), where there is no in-flight-upsert race to guard.
86
+ * Push a snapshot into the data stores. `baselines` (captured BEFORE this snapshot's fetch)
87
+ * lets the replace-style stores preserve anything written live while the fetch was in flight,
88
+ * so a slower refresh can't clobber newer live state (see {@link LiveWriteBaselines}). Omitted
89
+ * by fresh loads (init/switch/create), where there is no in-flight race to guard.
88
90
  */
89
- function hydrate(snapshot: WorkspaceSnapshot, boardSince?: number) {
91
+ function hydrate(snapshot: WorkspaceSnapshot, baselines?: LiveWriteBaselines) {
90
92
  // A change of active board (or the first load) drops the per-block caches that are NOT
91
93
  // part of the snapshot; a same-board refresh keeps them (see `resetPerBoardCaches`).
92
94
  if (workspaceId.value !== snapshot.workspace.id) resetPerBoardCaches()
@@ -107,7 +109,7 @@ export const useWorkspaceStore = defineStore(
107
109
  workspaces.value.unshift(snapshot.workspace)
108
110
  }
109
111
  // Fan the rest of the snapshot out into the per-feature data stores.
110
- applySnapshotToStores(snapshot, boardSince)
112
+ applySnapshotToStores(snapshot, baselines)
111
113
  }
112
114
 
113
115
  /** Resolve accounts + boards, then open the right board for the active account. */
@@ -209,17 +211,20 @@ export const useWorkspaceStore = defineStore(
209
211
  const targetId = workspaceId.value
210
212
  if (!targetId) return
211
213
  const seq = ++refreshSeq
212
- // Capture the board's live-upsert baseline BEFORE the fetch: any block upserted by a live
213
- // event while this (potentially slow) snapshot is in flight is newer than the snapshot, so
214
- // `hydrate` must NOT clobber it back. The `refreshSeq` guard below only orders refreshes
215
- // against each OTHER — this guards a refresh against an interleaved live upsert (e.g. a
216
- // run's terminal status landing mid-fetch), the coherence hazard under CI latency.
217
- const boardSince = useBoardStore().hydrateBaseline()
214
+ // Capture the live-write baselines BEFORE the fetch: anything a live event writes while
215
+ // this (potentially slow) snapshot is in flight is newer than the snapshot, so `hydrate`
216
+ // must NOT clobber it back. The `refreshSeq` guard below only orders refreshes against each
217
+ // OTHER — this guards a refresh against an interleaved live write (a run's terminal status
218
+ // landing mid-fetch, or the inbox card it raises), the coherence hazard under CI latency.
219
+ const baselines: LiveWriteBaselines = {
220
+ board: useBoardStore().hydrateBaseline(),
221
+ notifications: useNotificationsStore().hydrateBaseline(),
222
+ }
218
223
  const snapshot = await api.getWorkspace(targetId)
219
224
  // A newer refresh was issued (or the active board switched) while this fetch was in flight —
220
225
  // discard this older/staler result so it can't clobber the newer hydrate.
221
226
  if (seq !== refreshSeq || workspaceId.value !== targetId) return
222
- hydrate(snapshot, boardSince)
227
+ hydrate(snapshot, baselines)
223
228
  }
224
229
 
225
230
  /** The active workspace id, or throw if the app isn't bootstrapped yet. */
@@ -15,6 +15,10 @@ export type {
15
15
  CredentialField,
16
16
  DocumentSourceDescriptor,
17
17
  DocumentConnection,
18
+ DocumentFreshness,
19
+ DocumentFreshnessChange,
20
+ DocumentFreshnessGap,
21
+ RefreshedDocumentView,
18
22
  SourceDocument,
19
23
  DocumentSearchResult,
20
24
  DocumentRefReason,
@@ -1832,6 +1832,7 @@
1832
1832
  "within_thresholds": "Jede Bewertung liegt innerhalb der {preset}-Schwellenwerte, daher wurde der PR automatisch gemergt.",
1833
1833
  "exceeded_thresholds": "{axes} überschritt die {preset}-Schwellenwerte, daher wartet der PR darauf, dass ein Mensch mergt.",
1834
1834
  "auto_merge_disabled": "Das {preset}-Preset sendet jeden PR an einen Menschen, daher wartet dieser auf Prüfung.",
1835
+ "no_policy_configured": "Für diesen Lauf galt keine Merge-Richtlinie, daher wird kein PR selbstständig gemergt. Diese Installation hat keine Merge-Preset-Bibliothek eingerichtet; das kann nur ein Betreiber ändern.",
1835
1836
  "no_rationale": "Der Merger hat den PR bewertet, aber keine Begründung gegeben, daher konnte dem Urteil zum automatischen Mergen nicht vertraut werden; der PR wartet darauf, dass ein Mensch mergt.",
1836
1837
  "no_assessment": "Der Merger hat keine parsbare Bewertung zurückgegeben, daher wartet der PR darauf, dass ein Mensch mergt.",
1837
1838
  "merge_failed": "Die Bewertungen lagen innerhalb der {preset}-Schwellenwerte, aber der automatische Merge konnte nicht abgeschlossen werden (zum Beispiel Branch-Schutz oder ein Konflikt), daher wartet der PR darauf, dass ein Mensch mergt.",
@@ -1997,6 +1998,15 @@
1997
1998
  "oauthTokenFailed": "war nicht verfügbar: die Verbindung liefert kein Zugriffstoken mehr.",
1998
1999
  "overBudget": "war nicht verfügbar: dieser Agent deklariert mehr Tool-Server, als ein Lauf mitführt.",
1999
2000
  "unknown": "war nicht verfügbar ({reason})."
2001
+ },
2002
+ "remedy": {
2003
+ "harnessUnsupported": "Führen Sie den Schritt auf einer Agenten-CLI mit MCP aus, oder erweitern Sie die Harness-Liste des Servers.",
2004
+ "transportUnsupported": "Deklarieren Sie dafür einen stdio-Server, oder führen Sie den Schritt auf einer Agenten-CLI aus, die HTTP-Server erreicht.",
2005
+ "missingSecret": "Hinterlegen Sie die genannte Zugangsinformation im Infrastruktur-Fenster unter den Capability-Zugangsdaten.",
2006
+ "reservedSecret": "Ändern Sie die Deklaration auf einen anderen Schlüssel; das Setzen dieser Variablen hilft gerade nicht.",
2007
+ "oauthNotConnected": "Verbinden Sie dieses Board im Infrastruktur-Fenster damit.",
2008
+ "oauthTokenFailed": "Verbinden Sie es im Infrastruktur-Fenster neu, oder warten Sie die Störung des Anbieters ab.",
2009
+ "overBudget": "Kürzen Sie, was der Agent deklariert, damit ein Lauf alles mitführen kann."
2000
2010
  }
2001
2011
  },
2002
2012
  "adherence": {
@@ -2204,7 +2214,9 @@
2204
2214
  },
2205
2215
  "members": {
2206
2216
  "title": "Mitglieder",
2207
- "empty": "Noch keine Mitglieder."
2217
+ "empty": "Noch keine Mitglieder.",
2218
+ "revokeSessions": "Auf allen Geräten abmelden",
2219
+ "sessionsRevoked": "Auf allen Geräten abgemeldet"
2208
2220
  },
2209
2221
  "invite": {
2210
2222
  "title": "Ein Teammitglied einladen",
@@ -2243,7 +2255,8 @@
2243
2255
  "sendInvite": "Einladung konnte nicht gesendet werden",
2244
2256
  "revokeInvite": "Einladung konnte nicht widerrufen werden",
2245
2257
  "connectEmail": "E-Mail-Absender konnte nicht verbunden werden",
2246
- "disconnectEmail": "E-Mail-Absender konnte nicht getrennt werden"
2258
+ "disconnectEmail": "E-Mail-Absender konnte nicht getrennt werden",
2259
+ "revokeSessions": "Mitglied konnte nicht abgemeldet werden"
2247
2260
  },
2248
2261
  "emailNoun": "E-Mail-Versand"
2249
2262
  },
@@ -2653,6 +2666,39 @@
2653
2666
  },
2654
2667
  "accountFoundational": {
2655
2668
  "intro": "Die gemeinsamen Fähigkeiten, die diese Organisation bereits betreibt - Dateiablage, Benachrichtigungen, Audit - samt ihren API-Verträgen. Jedes Board erbt sie, und einem Architekten wird gesagt, sie zu nutzen statt einen Neubau vorzuschlagen. Dienste, die dieses Deployment im Code registriert, werden hier ebenfalls geerbt und können per ID überschrieben oder unten abgewählt werden."
2669
+ },
2670
+ "auditLog": {
2671
+ "title": "Prüfprotokoll",
2672
+ "description": "Wer in diesem Konto was und wann geändert hat. Einträge werden nur angehängt und können weder bearbeitet noch gelöscht werden.",
2673
+ "empty": "Für dieses Konto wurde bisher nichts aufgezeichnet.",
2674
+ "loadMore": "Ältere Einträge laden",
2675
+ "refresh": "Aktualisieren",
2676
+ "retiredAction": "hat eine Aktion ausgeführt, die diese Version nicht mehr kennt ({action})",
2677
+ "actors": {
2678
+ "system": "Das System",
2679
+ "apiKey": "API-Schlüssel {id}"
2680
+ },
2681
+ "values": {
2682
+ "none": "keine"
2683
+ },
2684
+ "actions": {
2685
+ "accountMemberAdded": "hat {target} als {roles} zum Konto hinzugefügt",
2686
+ "accountMemberRolesChanged": "hat die Rollen von {target} von {previousRoles} zu {roles} geändert",
2687
+ "accountBudgetChanged": "hat das monatliche Ausgabenlimit auf {limit} gesetzt",
2688
+ "accountSettingsChanged": "hat den Standard-Cloud-Anbieter auf {defaultCloudProvider} gesetzt",
2689
+ "accountInvitationCreated": "hat {email} als {roles} eingeladen",
2690
+ "accountInvitationRevoked": "hat die Einladung für {email} zurückgezogen",
2691
+ "accountInvitationAccepted": "hat die Einladung für {email} als {roles} angenommen",
2692
+ "accountMemberSessionsRevoked": "hat {target} auf allen Geräten abgemeldet",
2693
+ "workspaceMemberAdded": "hat {target} als {role} zu einem Board hinzugefügt",
2694
+ "workspaceMemberRoleChanged": "hat die Board-Rolle von {target} von {previousRole} zu {role} geändert",
2695
+ "workspaceMemberRemoved": "hat {target} aus einem Board entfernt (war {role})",
2696
+ "workspaceAccessModeChanged": "hat den Board-Zugriff auf {accessMode} gesetzt"
2697
+ },
2698
+ "errors": {
2699
+ "load": "Das Prüfprotokoll konnte nicht geladen werden.",
2700
+ "loadMore": "Ältere Einträge konnten nicht geladen werden"
2701
+ }
2656
2702
  }
2657
2703
  },
2658
2704
  "board": {
@@ -2670,7 +2716,12 @@
2670
2716
  "archived": "Archiviert: „{name}“",
2671
2717
  "restored": "Wiederhergestellt: „{name}“",
2672
2718
  "archiveFailed": "Dienst konnte nicht archiviert werden",
2673
- "restoreFailed": "Dienst konnte nicht wiederhergestellt werden"
2719
+ "restoreFailed": "Dienst konnte nicht wiederhergestellt werden",
2720
+ "moveRefused": {
2721
+ "relaxes_role_sandbox": "Die Ausführungen dieser Aufgabe laufen an ihrem jetzigen Ort für deine Rolle isoliert, die Merge-Richtlinie am Zielort jedoch nicht. Bitte eine Workspace-Administration, sie zu verschieben.",
2722
+ "relaxes_role_submission_allowlist": "Die Merge-Richtlinie am Zielort würde dich Änderungsarten mergen lassen, die dir hier verwehrt sind. Bitte eine Workspace-Administration, sie zu verschieben.",
2723
+ "relaxes_role_class_rule": "Die Merge-Richtlinie am Zielort merged Änderungen automatisch, die du hier prüfen musst. Bitte eine Workspace-Administration, sie zu verschieben."
2724
+ }
2674
2725
  },
2675
2726
  "repoTypes": {
2676
2727
  "service": "Service",
@@ -3840,6 +3891,25 @@
3840
3891
  "imported": "\"{title}\" importiert",
3841
3892
  "importFailed": "Import fehlgeschlagen"
3842
3893
  },
3894
+ "freshness": {
3895
+ "updated": "Aktualisiert am {when}",
3896
+ "refresh": "Auf Änderungen prüfen",
3897
+ "change": {
3898
+ "unchanged": "Stimmt mit der Quelle überein",
3899
+ "reimported": "Neuere Fassung übernommen",
3900
+ "revision_only": "Die Quelle hat sich geändert, diese Kopie jedoch nicht"
3901
+ },
3902
+ "checkedAt": "Geprüft am {when}",
3903
+ "revision": "Revision {version}",
3904
+ "notApplicable": "Diese Installation hat keinen Leser für diese Quelle, es gibt also nichts zum Abgleichen.",
3905
+ "gap": {
3906
+ "not_connected": "Nicht geprüft: dieser Workspace ist nicht mehr mit der Quelle verbunden.",
3907
+ "credentials_unreadable": "Nicht geprüft: diese Installation kann die Zugangsdaten der Quelle nicht lesen.",
3908
+ "unversioned": "Nicht geprüft: die Quelle veröffentlicht keine Revision zum Vergleich.",
3909
+ "source_unreachable": "Nicht geprüft: die Quelle war nicht erreichbar."
3910
+ },
3911
+ "refreshFailed": "Prüfung auf Änderungen fehlgeschlagen"
3912
+ },
3843
3913
  "connect": {
3844
3914
  "title": "Quelle verbinden",
3845
3915
  "sourceFallback": "Quelle",
@@ -171,7 +171,12 @@
171
171
  "archived": "Archived \"{name}\"",
172
172
  "restored": "Restored \"{name}\"",
173
173
  "archiveFailed": "Couldn't archive the service",
174
- "restoreFailed": "Couldn't restore the service"
174
+ "restoreFailed": "Couldn't restore the service",
175
+ "moveRefused": {
176
+ "relaxes_role_sandbox": "This task’s runs are sandboxed for your role where it is now, and the merge policy governing it where you are moving it is not. Ask a workspace admin to move it.",
177
+ "relaxes_role_submission_allowlist": "The merge policy where you are moving this task would let you land kinds of change it holds you back from here. Ask a workspace admin to move it.",
178
+ "relaxes_role_class_rule": "The merge policy where you are moving this task auto-merges changes you are held to review on it here. Ask a workspace admin to move it."
179
+ }
175
180
  },
176
181
  "repoTypes": {
177
182
  "service": "Service",
@@ -1351,6 +1356,7 @@
1351
1356
  "within_thresholds": "Every score is within the {preset} thresholds, so the PR was merged automatically.",
1352
1357
  "exceeded_thresholds": "{axes} exceeded the {preset} thresholds, so the PR is waiting for a human to merge.",
1353
1358
  "auto_merge_disabled": "The {preset} preset sends every PR to a human, so this one is waiting for review.",
1359
+ "no_policy_configured": "No merge policy governed this run, so no PR merges on its own. This deployment has no merge preset library set up, which an operator has to fix.",
1354
1360
  "no_rationale": "The merger scored the PR but gave no rationale, so the verdict could not be trusted to auto-merge; the PR is waiting for a human to merge.",
1355
1361
  "no_assessment": "The merger did not return a parseable assessment, so the PR is waiting for a human to merge.",
1356
1362
  "merge_failed": "The scores were within the {preset} thresholds, but the automatic merge could not complete (for example branch protection or a conflict), so the PR is waiting for a human to merge.",
@@ -1519,6 +1525,15 @@
1519
1525
  "oauthTokenFailed": "was not available: the connection stopped producing an access token.",
1520
1526
  "overBudget": "was not available: this agent declares more tool servers than one run carries.",
1521
1527
  "unknown": "was not available ({reason})."
1528
+ },
1529
+ "remedy": {
1530
+ "harnessUnsupported": "Run the step on an agent CLI that speaks MCP, or widen the server's harness list.",
1531
+ "transportUnsupported": "Declare a stdio server for it, or run the step on an agent CLI that reaches HTTP servers.",
1532
+ "missingSecret": "Set the credential it names under capability credentials, in the Infrastructure window.",
1533
+ "reservedSecret": "Change the declaration to ask for another key; setting that variable is exactly what will not help.",
1534
+ "oauthNotConnected": "Connect this board to it from the Infrastructure window.",
1535
+ "oauthTokenFailed": "Reconnect it from the Infrastructure window, or wait out the vendor's outage.",
1536
+ "overBudget": "Trim what the agent declares, so one run can carry all of it."
1522
1537
  }
1523
1538
  },
1524
1539
  "adherence": {
@@ -2127,7 +2142,9 @@
2127
2142
  },
2128
2143
  "members": {
2129
2144
  "title": "Members",
2130
- "empty": "No members yet."
2145
+ "empty": "No members yet.",
2146
+ "revokeSessions": "Sign out of every device",
2147
+ "sessionsRevoked": "Signed out of every device"
2131
2148
  },
2132
2149
  "invite": {
2133
2150
  "title": "Invite a teammate",
@@ -2166,7 +2183,8 @@
2166
2183
  "sendInvite": "Could not send invitation",
2167
2184
  "revokeInvite": "Could not revoke invitation",
2168
2185
  "connectEmail": "Could not connect email sender",
2169
- "disconnectEmail": "Could not disconnect email sender"
2186
+ "disconnectEmail": "Could not disconnect email sender",
2187
+ "revokeSessions": "Could not sign the member out"
2170
2188
  },
2171
2189
  "emailNoun": "email sending"
2172
2190
  },
@@ -2576,6 +2594,39 @@
2576
2594
  },
2577
2595
  "accountFoundational": {
2578
2596
  "intro": "The shared capabilities this organisation already runs - file storage, notifications, audit - with their API contracts. Every board inherits them, and an architect is told to consume them instead of proposing a rebuild. Services this deployment registers in code are inherited here too, and can be overridden by id or opted out of below."
2597
+ },
2598
+ "auditLog": {
2599
+ "title": "Audit log",
2600
+ "description": "Who changed what in this account, and when. Records are append-only and cannot be edited or deleted.",
2601
+ "empty": "Nothing has been recorded for this account yet.",
2602
+ "loadMore": "Load older entries",
2603
+ "refresh": "Refresh",
2604
+ "retiredAction": "performed an action this version no longer recognises ({action})",
2605
+ "actors": {
2606
+ "system": "The system",
2607
+ "apiKey": "API key {id}"
2608
+ },
2609
+ "values": {
2610
+ "none": "none"
2611
+ },
2612
+ "actions": {
2613
+ "accountMemberAdded": "added {target} to the account as {roles}",
2614
+ "accountMemberRolesChanged": "changed the roles of {target} from {previousRoles} to {roles}",
2615
+ "accountBudgetChanged": "set the monthly spending limit to {limit}",
2616
+ "accountSettingsChanged": "set the default cloud provider to {defaultCloudProvider}",
2617
+ "accountInvitationCreated": "invited {email} as {roles}",
2618
+ "accountInvitationRevoked": "revoked the invitation for {email}",
2619
+ "accountInvitationAccepted": "accepted the invitation for {email} as {roles}",
2620
+ "accountMemberSessionsRevoked": "signed {target} out of every device",
2621
+ "workspaceMemberAdded": "added {target} to a board as {role}",
2622
+ "workspaceMemberRoleChanged": "changed the board role of {target} from {previousRole} to {role}",
2623
+ "workspaceMemberRemoved": "removed {target} from a board (they were {role})",
2624
+ "workspaceAccessModeChanged": "set board access to {accessMode}"
2625
+ },
2626
+ "errors": {
2627
+ "load": "The audit log could not be loaded.",
2628
+ "loadMore": "Could not load older entries"
2629
+ }
2579
2630
  }
2580
2631
  },
2581
2632
  "settings": {
@@ -4360,6 +4411,25 @@
4360
4411
  "imported": "Imported \"{title}\"",
4361
4412
  "importFailed": "Import failed"
4362
4413
  },
4414
+ "freshness": {
4415
+ "updated": "Updated {when}",
4416
+ "refresh": "Check for changes",
4417
+ "change": {
4418
+ "unchanged": "Matches the source",
4419
+ "reimported": "Pulled the newer version",
4420
+ "revision_only": "The source moved on, but this copy is unchanged"
4421
+ },
4422
+ "checkedAt": "Checked {when}",
4423
+ "revision": "Revision {version}",
4424
+ "notApplicable": "This deployment has no reader for that source, so there is nothing to check against.",
4425
+ "gap": {
4426
+ "not_connected": "Not checked: this workspace is no longer connected to the source.",
4427
+ "credentials_unreadable": "Not checked: this deployment cannot read the source credentials.",
4428
+ "unversioned": "Not checked: the source publishes no revision to compare against.",
4429
+ "source_unreachable": "Not checked: the source could not be reached."
4430
+ },
4431
+ "refreshFailed": "Could not check for changes"
4432
+ },
4363
4433
  "connect": {
4364
4434
  "title": "Connect source",
4365
4435
  "sourceFallback": "Source",
@@ -147,7 +147,12 @@
147
147
  "archived": "Archivado «{name}»",
148
148
  "restored": "Restaurado «{name}»",
149
149
  "archiveFailed": "No se pudo archivar el servicio",
150
- "restoreFailed": "No se pudo restaurar el servicio"
150
+ "restoreFailed": "No se pudo restaurar el servicio",
151
+ "moveRefused": {
152
+ "relaxes_role_sandbox": "Las ejecuciones de esta tarea están aisladas para tu rol donde está ahora, y la política de fusión que la regiría donde la mueves no lo está. Pide a una administración del espacio de trabajo que la mueva.",
153
+ "relaxes_role_submission_allowlist": "La política de fusión del destino te dejaría fusionar tipos de cambio que aquí tienes vedados. Pide a una administración del espacio de trabajo que la mueva.",
154
+ "relaxes_role_class_rule": "La política de fusión del destino fusiona automáticamente cambios que aquí debes revisar. Pide a una administración del espacio de trabajo que la mueva."
155
+ }
151
156
  },
152
157
  "repoTypes": {
153
158
  "service": "Servicio",
@@ -1263,6 +1268,7 @@
1263
1268
  "within_thresholds": "Todas las puntuaciones están dentro de los umbrales de {preset}, por lo que el PR se fusionó automáticamente.",
1264
1269
  "exceeded_thresholds": "{axes} superó los umbrales de {preset}, por lo que el PR espera a que una persona lo fusione.",
1265
1270
  "auto_merge_disabled": "El preajuste {preset} envía todos los PR a una persona, así que este espera revisión.",
1271
+ "no_policy_configured": "Ninguna política de fusión rigió esta ejecución, así que ningún PR se fusiona por sí solo. Esta implementación no tiene configurada una biblioteca de preajustes de fusión, algo que solo puede corregir un operador.",
1266
1272
  "no_rationale": "El fusionador puntuó el PR pero no dio ninguna justificación, así que no se pudo confiar en el veredicto para fusionar automáticamente; el PR espera a que una persona lo fusione.",
1267
1273
  "no_assessment": "El fusionador no devolvió una evaluación analizable, por lo que el PR espera a que una persona lo fusione.",
1268
1274
  "merge_failed": "Las puntuaciones estaban dentro de los umbrales de {preset}, pero la fusión automática no pudo completarse (por ejemplo, protección de rama o un conflicto), por lo que el PR espera a que una persona lo fusione.",
@@ -1428,6 +1434,15 @@
1428
1434
  "oauthTokenFailed": "no estuvo disponible: la conexión dejó de producir un token de acceso.",
1429
1435
  "overBudget": "no estuvo disponible: este agente declara más servidores de los que lleva una ejecución.",
1430
1436
  "unknown": "no estuvo disponible ({reason})."
1437
+ },
1438
+ "remedy": {
1439
+ "harnessUnsupported": "Ejecuta el paso en una CLI de agente que hable MCP, o amplía la lista de harnesses del servidor.",
1440
+ "transportUnsupported": "Declara un servidor stdio para él, o ejecuta el paso en una CLI de agente que alcance servidores HTTP.",
1441
+ "missingSecret": "Configura la credencial que nombra en las credenciales de capacidades, en la ventana de Infraestructura.",
1442
+ "reservedSecret": "Cambia la declaración para que pida otra clave; definir esa variable es justo lo que no ayudará.",
1443
+ "oauthNotConnected": "Conecta este tablero con él desde la ventana de Infraestructura.",
1444
+ "oauthTokenFailed": "Vuelve a conectarlo desde la ventana de Infraestructura, o espera a que pase la caída del proveedor.",
1445
+ "overBudget": "Recorta lo que declara el agente, para que una ejecución pueda llevarlo todo."
1431
1446
  }
1432
1447
  },
1433
1448
  "adherence": {
@@ -2020,7 +2035,9 @@
2020
2035
  },
2021
2036
  "members": {
2022
2037
  "title": "Miembros",
2023
- "empty": "Todavía no hay miembros."
2038
+ "empty": "Todavía no hay miembros.",
2039
+ "revokeSessions": "Cerrar sesión en todos los dispositivos",
2040
+ "sessionsRevoked": "Sesión cerrada en todos los dispositivos"
2024
2041
  },
2025
2042
  "invite": {
2026
2043
  "title": "Invitar a un compañero",
@@ -2059,7 +2076,8 @@
2059
2076
  "sendInvite": "No se pudo enviar la invitación",
2060
2077
  "revokeInvite": "No se pudo revocar la invitación",
2061
2078
  "connectEmail": "No se pudo conectar el remitente de correo",
2062
- "disconnectEmail": "No se pudo desconectar el remitente de correo"
2079
+ "disconnectEmail": "No se pudo desconectar el remitente de correo",
2080
+ "revokeSessions": "No se pudo cerrar la sesión del miembro"
2063
2081
  },
2064
2082
  "emailNoun": "el envío de correo"
2065
2083
  },
@@ -2469,6 +2487,39 @@
2469
2487
  },
2470
2488
  "accountFoundational": {
2471
2489
  "intro": "Las capacidades compartidas que esta organización ya opera - almacenamiento de archivos, notificaciones, auditoría - con sus contratos de API. Todos los tableros las heredan, y a un arquitecto se le indica que las consuma en lugar de proponer reconstruirlas. Los servicios que este despliegue registra en código también se heredan aquí, y se pueden sobrescribir por id o excluir abajo."
2490
+ },
2491
+ "auditLog": {
2492
+ "title": "Registro de auditoría",
2493
+ "description": "Quién cambió qué en esta cuenta, y cuándo. Los registros solo se añaden y no se pueden editar ni eliminar.",
2494
+ "empty": "Todavía no se ha registrado nada para esta cuenta.",
2495
+ "loadMore": "Cargar entradas anteriores",
2496
+ "refresh": "Actualizar",
2497
+ "retiredAction": "realizó una acción que esta versión ya no reconoce ({action})",
2498
+ "actors": {
2499
+ "system": "El sistema",
2500
+ "apiKey": "Clave de API {id}"
2501
+ },
2502
+ "values": {
2503
+ "none": "ninguno"
2504
+ },
2505
+ "actions": {
2506
+ "accountMemberAdded": "añadió a {target} a la cuenta como {roles}",
2507
+ "accountMemberRolesChanged": "cambió los roles de {target} de {previousRoles} a {roles}",
2508
+ "accountBudgetChanged": "estableció el límite de gasto mensual en {limit}",
2509
+ "accountSettingsChanged": "estableció el proveedor de nube predeterminado en {defaultCloudProvider}",
2510
+ "accountInvitationCreated": "invitó a {email} como {roles}",
2511
+ "accountInvitationRevoked": "revocó la invitación de {email}",
2512
+ "accountInvitationAccepted": "aceptó la invitación de {email} como {roles}",
2513
+ "accountMemberSessionsRevoked": "cerró la sesión de {target} en todos los dispositivos",
2514
+ "workspaceMemberAdded": "añadió a {target} a un tablero como {role}",
2515
+ "workspaceMemberRoleChanged": "cambió el rol de tablero de {target} de {previousRole} a {role}",
2516
+ "workspaceMemberRemoved": "eliminó a {target} de un tablero (era {role})",
2517
+ "workspaceAccessModeChanged": "estableció el acceso al tablero en {accessMode}"
2518
+ },
2519
+ "errors": {
2520
+ "load": "No se pudo cargar el registro de auditoría.",
2521
+ "loadMore": "No se pudieron cargar las entradas anteriores"
2522
+ }
2472
2523
  }
2473
2524
  },
2474
2525
  "settings": {
@@ -4223,6 +4274,25 @@
4223
4274
  "imported": "Se importó \"{title}\"",
4224
4275
  "importFailed": "Error al importar"
4225
4276
  },
4277
+ "freshness": {
4278
+ "updated": "Actualizado el {when}",
4279
+ "refresh": "Buscar cambios",
4280
+ "change": {
4281
+ "unchanged": "Coincide con la fuente",
4282
+ "reimported": "Se ha traído la versión más reciente",
4283
+ "revision_only": "La fuente ha cambiado, pero esta copia sigue igual"
4284
+ },
4285
+ "checkedAt": "Comprobado el {when}",
4286
+ "revision": "Revisión {version}",
4287
+ "notApplicable": "Esta instalación no tiene lector para esa fuente, así que no hay nada con lo que comparar.",
4288
+ "gap": {
4289
+ "not_connected": "Sin comprobar: este espacio de trabajo ya no está conectado a la fuente.",
4290
+ "credentials_unreadable": "Sin comprobar: esta instalación no puede leer las credenciales de la fuente.",
4291
+ "unversioned": "Sin comprobar: la fuente no publica ninguna revisión con la que comparar.",
4292
+ "source_unreachable": "Sin comprobar: no se ha podido contactar con la fuente."
4293
+ },
4294
+ "refreshFailed": "No se han podido buscar cambios"
4295
+ },
4226
4296
  "connect": {
4227
4297
  "title": "Conectar fuente",
4228
4298
  "sourceFallback": "Fuente",
@@ -147,7 +147,12 @@
147
147
  "archived": "Archivé « {name} »",
148
148
  "restored": "Restauré « {name} »",
149
149
  "archiveFailed": "Impossible d'archiver le service",
150
- "restoreFailed": "Impossible de restaurer le service"
150
+ "restoreFailed": "Impossible de restaurer le service",
151
+ "moveRefused": {
152
+ "relaxes_role_sandbox": "Les exécutions de cette tâche sont isolées pour votre rôle là où elle se trouve, et la politique de fusion qui la régirait à destination ne l’est pas. Demandez à une administration de l’espace de travail de la déplacer.",
153
+ "relaxes_role_submission_allowlist": "La politique de fusion à destination vous laisserait fusionner des types de changement dont vous êtes privé ici. Demandez à une administration de l’espace de travail de la déplacer.",
154
+ "relaxes_role_class_rule": "La politique de fusion à destination fusionne automatiquement des changements que vous devez relire ici. Demandez à une administration de l’espace de travail de la déplacer."
155
+ }
151
156
  },
152
157
  "repoTypes": {
153
158
  "service": "Service",
@@ -1263,6 +1268,7 @@
1263
1268
  "within_thresholds": "Tous les scores sont dans les seuils de {preset}, la PR a donc été fusionnée automatiquement.",
1264
1269
  "exceeded_thresholds": "{axes} a dépassé les seuils de {preset}, la PR attend donc une fusion par une personne.",
1265
1270
  "auto_merge_disabled": "Le préréglage {preset} envoie chaque PR à une personne ; celle-ci attend donc une revue.",
1271
+ "no_policy_configured": "Aucune politique de fusion n'a régi cette exécution, donc aucune PR ne fusionne d'elle-même. Ce déploiement n'a pas de bibliothèque de préréglages de fusion configurée, ce que seul un opérateur peut corriger.",
1266
1272
  "no_rationale": "Le fusionneur a évalué la PR mais n'a donné aucune justification, le verdict n'a donc pas pu être approuvé pour une fusion automatique ; la PR attend une fusion par une personne.",
1267
1273
  "no_assessment": "Le fusionneur n'a pas renvoyé d'évaluation exploitable, la PR attend donc une fusion par une personne.",
1268
1274
  "merge_failed": "Les scores étaient dans les seuils de {preset}, mais la fusion automatique n'a pas pu aboutir (par exemple protection de branche ou conflit), la PR attend donc une fusion par une personne.",
@@ -1428,6 +1434,15 @@
1428
1434
  "oauthTokenFailed": "n'était pas disponible : la connexion ne produit plus de jeton d'accès.",
1429
1435
  "overBudget": "n'était pas disponible : cet agent déclare plus de serveurs d'outils qu'une exécution n'en transporte.",
1430
1436
  "unknown": "n'était pas disponible ({reason})."
1437
+ },
1438
+ "remedy": {
1439
+ "harnessUnsupported": "Exécutez l’étape sur une CLI d’agent qui parle MCP, ou élargissez la liste de harnesses du serveur.",
1440
+ "transportUnsupported": "Déclarez un serveur stdio à sa place, ou exécutez l’étape sur une CLI d’agent qui atteint les serveurs HTTP.",
1441
+ "missingSecret": "Renseignez l’identifiant qu’il nomme dans les identifiants de capacités, depuis la fenêtre Infrastructure.",
1442
+ "reservedSecret": "Modifiez la déclaration pour demander une autre clé ; définir cette variable est précisément ce qui n’aidera pas.",
1443
+ "oauthNotConnected": "Connectez ce tableau à ce serveur depuis la fenêtre Infrastructure.",
1444
+ "oauthTokenFailed": "Reconnectez-le depuis la fenêtre Infrastructure, ou attendez la fin de la panne du fournisseur.",
1445
+ "overBudget": "Réduisez ce que l’agent déclare, pour qu’une exécution puisse tout transporter."
1431
1446
  }
1432
1447
  },
1433
1448
  "adherence": {
@@ -2020,7 +2035,9 @@
2020
2035
  },
2021
2036
  "members": {
2022
2037
  "title": "Membres",
2023
- "empty": "Aucun membre pour l'instant."
2038
+ "empty": "Aucun membre pour l'instant.",
2039
+ "revokeSessions": "Déconnecter de tous les appareils",
2040
+ "sessionsRevoked": "Déconnecté de tous les appareils"
2024
2041
  },
2025
2042
  "invite": {
2026
2043
  "title": "Inviter un coéquipier",
@@ -2059,7 +2076,8 @@
2059
2076
  "sendInvite": "Impossible d'envoyer l'invitation",
2060
2077
  "revokeInvite": "Impossible de révoquer l'invitation",
2061
2078
  "connectEmail": "Impossible de connecter l'expéditeur des e-mails",
2062
- "disconnectEmail": "Impossible de déconnecter l'expéditeur des e-mails"
2079
+ "disconnectEmail": "Impossible de déconnecter l'expéditeur des e-mails",
2080
+ "revokeSessions": "Impossible de déconnecter le membre"
2063
2081
  },
2064
2082
  "emailNoun": "l’envoi d’e-mails"
2065
2083
  },
@@ -2469,6 +2487,39 @@
2469
2487
  },
2470
2488
  "accountFoundational": {
2471
2489
  "intro": "Les capacités partagées que cette organisation exploite déjà - stockage de fichiers, notifications, audit - avec leurs contrats d'API. Chaque tableau en hérite, et il est demandé à un architecte de les consommer plutôt que de proposer de les reconstruire. Les services que ce déploiement enregistre dans le code sont également hérités ici : ils peuvent être remplacés par identifiant ou écartés ci-dessous."
2490
+ },
2491
+ "auditLog": {
2492
+ "title": "Journal d’audit",
2493
+ "description": "Qui a modifié quoi dans ce compte, et quand. Les entrées sont uniquement ajoutées et ne peuvent être ni modifiées ni supprimées.",
2494
+ "empty": "Rien n’a encore été enregistré pour ce compte.",
2495
+ "loadMore": "Charger les entrées plus anciennes",
2496
+ "refresh": "Actualiser",
2497
+ "retiredAction": "a effectué une action que cette version ne reconnaît plus ({action})",
2498
+ "actors": {
2499
+ "system": "Le système",
2500
+ "apiKey": "Clé d’API {id}"
2501
+ },
2502
+ "values": {
2503
+ "none": "aucun"
2504
+ },
2505
+ "actions": {
2506
+ "accountMemberAdded": "a ajouté {target} au compte en tant que {roles}",
2507
+ "accountMemberRolesChanged": "a changé les rôles de {target} de {previousRoles} à {roles}",
2508
+ "accountBudgetChanged": "a fixé la limite de dépenses mensuelle à {limit}",
2509
+ "accountSettingsChanged": "a défini le fournisseur cloud par défaut sur {defaultCloudProvider}",
2510
+ "accountInvitationCreated": "a invité {email} en tant que {roles}",
2511
+ "accountInvitationRevoked": "a révoqué l’invitation de {email}",
2512
+ "accountInvitationAccepted": "a accepté l’invitation de {email} en tant que {roles}",
2513
+ "accountMemberSessionsRevoked": "a déconnecté {target} de tous les appareils",
2514
+ "workspaceMemberAdded": "a ajouté {target} à un tableau en tant que {role}",
2515
+ "workspaceMemberRoleChanged": "a changé le rôle de tableau de {target} de {previousRole} à {role}",
2516
+ "workspaceMemberRemoved": "a retiré {target} d’un tableau (il ou elle était {role})",
2517
+ "workspaceAccessModeChanged": "a défini l’accès au tableau sur {accessMode}"
2518
+ },
2519
+ "errors": {
2520
+ "load": "Le journal d’audit n’a pas pu être chargé.",
2521
+ "loadMore": "Impossible de charger les entrées plus anciennes"
2522
+ }
2472
2523
  }
2473
2524
  },
2474
2525
  "settings": {
@@ -4223,6 +4274,25 @@
4223
4274
  "imported": "« {title} » importé",
4224
4275
  "importFailed": "Échec de l'importation"
4225
4276
  },
4277
+ "freshness": {
4278
+ "updated": "Mis à jour le {when}",
4279
+ "refresh": "Vérifier les changements",
4280
+ "change": {
4281
+ "unchanged": "Correspond à la source",
4282
+ "reimported": "Version plus récente récupérée",
4283
+ "revision_only": "La source a évolué, mais cette copie est inchangée"
4284
+ },
4285
+ "checkedAt": "Vérifié le {when}",
4286
+ "revision": "Révision {version}",
4287
+ "notApplicable": "Ce déploiement n'a pas de lecteur pour cette source, il n'y a donc rien à comparer.",
4288
+ "gap": {
4289
+ "not_connected": "Non vérifié : cet espace de travail n'est plus connecté à la source.",
4290
+ "credentials_unreadable": "Non vérifié : ce déploiement ne peut pas lire les identifiants de la source.",
4291
+ "unversioned": "Non vérifié : la source ne publie aucune révision à comparer.",
4292
+ "source_unreachable": "Non vérifié : la source est injoignable."
4293
+ },
4294
+ "refreshFailed": "Impossible de vérifier les changements"
4295
+ },
4226
4296
  "connect": {
4227
4297
  "title": "Connecter une source",
4228
4298
  "sourceFallback": "Source",