feat(agent): adopt AI SDK v7 — crash safety, context pruning, HITL approvals (#3362)

* docs(adr): propose agent AI SDK v7 adoption plan

* fix(ai): bind analyzeResume through aiService in service test

The test destructured analyzeResume as a named export that does not exist; main was red.

* test(agent): keep pure ai helpers real via spread-actual mock factory

* feat(agent): add run guards, patch version guard, run wall-clock timeout

* feat(agent): validate UI messages at the send boundary

* feat(agent): crash-safe draft-row persistence and server-side cancellation

* feat(agent): reap stale run claims at boot, on send, and on thread open

* feat(agent): fresh-document patch output and tiered context pruning

* feat(ai): shared agent tool contracts and message metadata schema

* feat(agent): add per-thread review-patches setting with update endpoint

* feat(agent): gate resume patches behind hmac-signed tool approval

* feat(agent): merge question answers and approval decisions before run claim

* feat(agent): approval ui with composed auto-send and fixture-driven tests

* feat(agent): usage metadata, tool activity cards, smoother streaming

* feat(agent): tool-call repair, input examples, structured step logging

* chore(i18n): translate new agent workspace strings across all locales

* fix(agent): gate stale-run draft cancellation on winning the claim clear

Snapshot streaming drafts before the conditional clear and skip the flip entirely when another reaper or a replacement run already cleared the claim. Also address review nits in eleven locale catalogs.

* fix(agent): flip reaped drafts only when their snapshotted state is unchanged

* fix(agent): address review findings across run lifecycle, context budget, and approval flow

- bind patches to the revision the model read via signed baseUpdatedAt
- claim the run before consuming a continuation; recorded-but-unexecuted approvals retry as pending continuations
- keep run ownership on stop() until cancellation persists; preserve the claim for the reaper when final persistence fails
- estimate tokens without serializing binary attachments (tokenx) and enforce the budget by dropping oldest whole turns
- mark crash-recovered patch results as snapshot boundaries; strip /data prefixes at execution time
- retry failed continuations without regenerate; mount a single AgentChat; disable response controls on read-only threads; freeze review toggle during runs (client+server)
- accumulate usage across continuations and match the SDK's nested usage shape; label-form token strings; reorderable source label; accessible note field; state-neutral web-search label

* chore(i18n): translate revised agent strings across all locales

* fix(agent): harden baseUpdatedAt validation and address review follow-ups

- bundle tokenx in the server runtime dependencies (e2e boot failure)
- strict ISO schema for baseUpdatedAt plus loud executor rejection of unparseable values
- it-IT source label consistency (Fonte)
- prove penultimate-turn retention in the context pruning test

* chore(deps): exempt tokenx from knip for the externalized server bundle
This commit is contained in:
Amruth Pillai
2026-08-20 08:06:53 +02:00
committed by GitHub
parent dbbab6fd76
commit c8081ac2fe
95 changed files with 14919 additions and 497 deletions
+103 -3
View File
@@ -543,6 +543,14 @@ msgstr "Candidature envoyée"
msgid "Applied on"
msgstr "Postulé le"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Approve"
msgstr "Approuver"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Approved — waiting for the agent…"
msgstr "Approuvé — en attente de l'agent…"
#: src/libs/locale.ts
msgid "Arabic"
msgstr "Arabe"
@@ -1462,6 +1470,14 @@ msgstr "Suppression de votre clé API..."
msgid "Deleting your resume..."
msgstr "Suppression de votre CV en cours..."
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Denied — waiting for the agent…"
msgstr "Refusé — en attente de l'agent…"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Deny"
msgstr "Refuser"
#: src/libs/resume/ats.ts
msgid "Describe what you did so the entry contributes keywords for matching."
msgstr "Décrivez ce que vous avez fait pour que l'entrée fournisse des mots-clés pour la correspondance."
@@ -1530,6 +1546,10 @@ msgstr "Faire un don"
msgid "Donate to Reactive Resume"
msgstr "Faire un don à Reactive Resume"
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Done"
msgstr "Terminé"
#. Action button to download two-factor backup codes as a text file
#. Primary action in the builder header to open resume download options
#: src/dialogs/auth/enable-two-factor.tsx
@@ -1642,6 +1662,10 @@ msgstr "Modifier le contenu en mode plein écran"
msgid "Edit date"
msgstr "Modifier la date"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Edit declined"
msgstr "Modification refusée"
#. Resume card context menu action to edit resume metadata
#. Resume card dropdown action to edit resume metadata
#: src/routes/builder/$resumeId/-components/header.tsx
@@ -1837,6 +1861,10 @@ msgstr "Exportez instantanément votre CV au format PDF, sans attente ni délai.
msgid "Exported pipeline-flow.png"
msgstr "pipeline-flow.png exporté"
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Failed"
msgstr "Échec"
#: src/routes/builder/$resumeId/-sidebar/right/sections/resume-analysis.tsx
msgid "Failed to analyze resume."
msgstr "Échec de l'analyse du curriculum vitae."
@@ -1967,6 +1995,10 @@ msgstr "Échec de la déconnexion du fournisseur. Veuillez réessayer."
msgid "Failed to update provider."
msgstr "Impossible de mettre à jour le fournisseur."
#: src/routes/agent/-components/agent-chat.tsx
msgid "Failed to update thread settings."
msgstr "Impossible de mettre à jour les paramètres du thread."
#. Fallback toast when changing account password fails
#: src/dialogs/auth/change-password.tsx
msgid "Failed to update your password. Please try again."
@@ -3153,6 +3185,14 @@ msgstr "OpenRouter"
msgid "opens in new tab"
msgstr "s'ouvre dans un nouvel onglet"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Optional note for the agent"
msgstr "Note facultative pour l'agent"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Optional note for the agent…"
msgstr "Note facultative pour l'agent…"
#: src/routes/builder/$resumeId/-sidebar/right/sections/sharing.tsx
msgid "Optionally, set a password so that only people with the password can view your resume through the link."
msgstr "Eventuellement, définissez un mot de passe pour que seules les personnes ayant le mot de passe puissent consulter votre CV par le biais du lien."
@@ -3499,6 +3539,10 @@ msgstr "Publications"
msgid "Publisher"
msgstr "Éditeur"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Raw JSON"
msgstr "JSON brut"
#: src/features/applications/components/application-ai-copilot.tsx
msgid "Re-score"
msgstr "Réévaluer"
@@ -3546,10 +3590,18 @@ msgstr "React Resume v<0>{__APP_VERSION__}</0>"
msgid "Reactive Resume v4 (JSON)"
msgstr "Reactive Resume v4 (JSON)"
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Read an attachment"
msgstr "Lecture d'une pièce jointe"
#: src/features/resume/stylesheet/editor.tsx
msgid "Read the Applying Custom Styles guide."
msgstr "Consultez le guide « Application des styles personnalisés »."
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Read the resume"
msgstr "Lecture du CV"
#: src/features/applications/components/application-form-sheet.tsx
msgid "Reading the posting…"
msgstr "Lecture de l'annonce…"
@@ -3700,8 +3752,8 @@ msgid "Restore"
msgstr "Restaurer"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Restore the resume to before this patch? This will roll back this patch and any patches applied after it."
msgstr "Restaurer la reprise à un état antérieur à ce correctif ? Cette action annulera ce correctif ainsi que tous les correctifs appliqués ultérieurement."
msgid "Restore the resume to before this patch?"
msgstr "Restaurer le CV tel qu'il était avant ce correctif ?"
#: src/routes/builder/$resumeId/-components/version-history.tsx
msgid "Restore this version?"
@@ -3726,6 +3778,10 @@ msgstr "L'analyse du curriculum vitae est terminée."
msgid "Resume content"
msgstr "Contenu du CV"
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Resume edit"
msgstr "Modification du CV"
#: src/features/applications/components/application-detail-sheet.tsx
msgid "Resume file"
msgstr "Fichier de CV"
@@ -3754,10 +3810,18 @@ msgstr "CVs"
msgid "Retry"
msgstr "Réessayer"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Review edits"
msgstr "Examiner les modifications"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Review the resume against a job description and ask me questions before changing uncertain sections."
msgstr "Veuillez vérifier votre CV en le comparant à la description du poste et posez-moi des questions avant de modifier les sections qui vous semblent incertaines."
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Review this edit"
msgstr "Examiner cette modification"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Rework the summary so it targets a senior engineering manager role without sounding generic."
msgstr "Remaniez le résumé pour qu'il cible un poste de responsable d'ingénierie senior sans paraître générique."
@@ -3798,6 +3862,10 @@ msgstr "Rotation"
msgid "Run your first analysis to get a scorecard, strengths, and prioritized suggestions."
msgstr "Effectuez votre première analyse pour obtenir un tableau de bord, des points forts et des suggestions classées par ordre de priorité."
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Running…"
msgstr "En cours d'exécution…"
#: src/libs/locale.ts
msgid "Russian"
msgstr "Russe"
@@ -4253,6 +4321,15 @@ msgstr "Origine"
msgid "Source Code"
msgstr "Code source"
#. placeholder {0}: operation.from
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "Source: {0}"
msgstr "Source : {0}"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Sources"
msgstr "Sources"
#: src/routes/builder/$resumeId/-sidebar/right/sections/page.tsx
msgid "Spacing (Horizontal)"
msgstr "Espacement (horizontal)"
@@ -4604,6 +4681,10 @@ msgstr "Impossible d'ouvrir cet assistant."
msgid "This date will not be read correctly."
msgstr "Cette date ne sera pas lue correctement."
#: src/routes/agent/-components/patch-approval-card.tsx
msgid "This edit request can no longer be answered."
msgstr "Il n'est plus possible de répondre à cette demande de modification."
#: src/libs/resume/ats.ts
msgid "This email address will not be recognized."
msgstr "Cette adresse email ne sera pas reconnue."
@@ -4712,6 +4793,10 @@ msgstr "Cela vous aidera à l'identifier plus tard, si vous prévoyez d'avoir pl
msgid "This will remove all items from this section."
msgstr "Cette opération permet de supprimer tous les éléments de cette section."
#: src/routes/agent/-components/agent-chat.tsx
msgid "This will roll back this patch and any patches applied after it."
msgstr "Cela annulera ce correctif ainsi que tous les correctifs appliqués après celui-ci."
#: src/routes/agent/-components/agent-chat.tsx
#: src/routes/agent/-components/thread-sidebar.tsx
msgid "Thread actions"
@@ -4794,6 +4879,18 @@ msgstr "Barre latérale droite"
msgid "Toggle threads"
msgstr "Basculer les fils"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Tokens: {threadTokenTotal}"
msgstr "Jetons : {threadTokenTotal}"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Tokens: {total}"
msgstr "Jetons : {total}"
#: src/routes/agent/-components/agent-chat.tsx
msgid "Tokens: {total} ({cached} cached)"
msgstr "Jetons : {total} ({cached} en cache)"
#: src/features/applications/components/application-form-sheet.tsx
msgid "Track a job you're applying to and link the resume you sent."
msgstr "Suivez une offre à laquelle vous postulez et liez le CV envoyé."
@@ -5213,6 +5310,10 @@ msgstr "Nous n'avons pas pu détecter le format automatiquement — veuillez le
msgid "We couldn't find that page"
msgstr "Nous n'avons pas trouvé cette page."
#: src/routes/agent/-components/tool-part-card.tsx
msgid "Web search"
msgstr "Recherche web"
#: src/dialogs/resume/sections/award.tsx
#: src/dialogs/resume/sections/certification.tsx
#: src/dialogs/resume/sections/education.tsx
@@ -5445,4 +5546,3 @@ msgstr "Zoom arrière"
#: src/libs/locale.ts
msgid "Zulu"
msgstr "Zoulou"