copilot-operator 0.1.0 → 0.1.2

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 (59) hide show
  1. package/README.md +13 -0
  2. package/dist/src/api/operator.controller.js +44 -0
  3. package/dist/src/api/operator.service.js +48 -13
  4. package/dist/src/config/layout.js +15 -4
  5. package/dist/src/config/schema.js +8 -2
  6. package/dist/src/orchestrator/taskRunner.js +26 -13
  7. package/dist/src/plan/importPlan.js +3 -2
  8. package/dist/src/plan/systemGuide.js +56 -0
  9. package/dist/src/session/compose.js +21 -2
  10. package/dist/src/session/store.js +51 -1
  11. package/dist/src/transport/chatSession.js +16 -4
  12. package/dist/src/vcs/taskVcs.js +5 -0
  13. package/dist/web/404.html +2 -2
  14. package/dist/web/_next/static/chunks/549-2086c05135bc9753.js +1 -0
  15. package/dist/web/_next/static/chunks/867-5b104743e24a4e2f.js +1 -0
  16. package/dist/web/_next/static/chunks/955-cf291b8a60315c58.js +1 -0
  17. package/dist/web/_next/static/chunks/app/defaults/page-559af121c43127a1.js +1 -0
  18. package/dist/web/_next/static/chunks/app/history/{page-bad4f3e89b485719.js → page-0df90ab9998815db.js} +1 -1
  19. package/dist/web/_next/static/chunks/app/import/page-8a4bdee8e38341a9.js +1 -0
  20. package/dist/web/_next/static/chunks/app/layout-92fa876afe619cf3.js +1 -0
  21. package/dist/web/_next/static/chunks/app/level1/page-697d4d6ba5bba41a.js +1 -0
  22. package/dist/web/_next/static/chunks/app/page-050cf6f71187e8af.js +1 -0
  23. package/dist/web/_next/static/chunks/app/presets/page-e2dcb924d9e2d758.js +1 -0
  24. package/dist/web/_next/static/chunks/app/sessions/view/page-4d31690c22c8b331.js +1 -0
  25. package/dist/web/_next/static/chunks/app/system/page-3aa2a0fef5454e69.js +1 -0
  26. package/dist/web/_next/static/css/{d77735cdc9020a86.css → 5a10c60adf9c5336.css} +1 -1
  27. package/dist/web/appearance.html +2 -2
  28. package/dist/web/appearance.txt +26 -25
  29. package/dist/web/defaults.html +2 -2
  30. package/dist/web/defaults.txt +26 -25
  31. package/dist/web/history.html +2 -2
  32. package/dist/web/history.txt +26 -25
  33. package/dist/web/import.html +2 -2
  34. package/dist/web/import.txt +26 -25
  35. package/dist/web/index.html +2 -2
  36. package/dist/web/index.txt +26 -25
  37. package/dist/web/level1.html +2 -2
  38. package/dist/web/level1.txt +26 -25
  39. package/dist/web/presets.html +2 -2
  40. package/dist/web/presets.txt +26 -25
  41. package/dist/web/sessions/view.html +2 -2
  42. package/dist/web/sessions/view.txt +26 -25
  43. package/dist/web/system.html +2 -2
  44. package/dist/web/system.txt +26 -25
  45. package/package.json +5 -3
  46. package/prompts/level1.md +17 -7
  47. package/dist/web/_next/static/chunks/643-34b9f66a6c317c4a.js +0 -1
  48. package/dist/web/_next/static/chunks/867-03b7cac8f79896c3.js +0 -1
  49. package/dist/web/_next/static/chunks/955-63de06e182d98949.js +0 -1
  50. package/dist/web/_next/static/chunks/app/defaults/page-ed858127cbdfb4ab.js +0 -1
  51. package/dist/web/_next/static/chunks/app/import/page-db1f5f1ab2f5cad1.js +0 -1
  52. package/dist/web/_next/static/chunks/app/layout-72251c52cc54f95e.js +0 -1
  53. package/dist/web/_next/static/chunks/app/level1/page-cf3e50cf64fecf4f.js +0 -1
  54. package/dist/web/_next/static/chunks/app/page-6fd16e5c8cf3b20f.js +0 -1
  55. package/dist/web/_next/static/chunks/app/presets/page-951e78b80e0e22e6.js +0 -1
  56. package/dist/web/_next/static/chunks/app/sessions/view/page-f2e63618097d7221.js +0 -1
  57. package/dist/web/_next/static/chunks/app/system/page-44e7954c0e48f4ba.js +0 -1
  58. /package/dist/web/_next/static/{u8rZNwh4d3n-HGJnfZ72Y → eWzbORCbQ1h_2IeLH_njb}/_buildManifest.js +0 -0
  59. /package/dist/web/_next/static/{u8rZNwh4d3n-HGJnfZ72Y → eWzbORCbQ1h_2IeLH_njb}/_ssgManifest.js +0 -0
@@ -1 +0,0 @@
1
- "use strict";(self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[867],{867:(e,t,s)=>{s.d(t,{LanguageProvider:()=>h,c5:()=>l,W3:()=>c,kj:()=>d});var o=s(3365),n=s(1521);let a={en:{"nav.label":"Main","nav.sessions":"Sessions","nav.live":"live","nav.liveTitle":"The bot is working right now: {n} session(s) running. Open the register to watch it.","nav.history":"Task register","nav.level1":"Level 1 prompt","nav.presets":"Level 2 presets","nav.appearance":"Appearance","nav.system":"System","dialog.confirmTitle":"Are you sure?","dialog.noticeTitle":"Notice","dialog.ok":"OK","dialog.cancel":"Cancel","batch.runName":"Name of this run","batch.runNamePlaceholder":"e.g. rules-engine, second attempt","batch.runNameWhy":"The register groups the tasks of a run under it and the exported files are named after it. Left empty, the plan the sessions came from gives its name; without one, the run goes by its id.","reg.runUnnamed":"Unnamed run","reg.runBy":"{name} \xb7 {t} task(s) in {s} session(s)","reg.runCounts":"{done} done \xb7 {failed} failed","reg.exportTitle":"Download as JSON","reg.exportPlan":"plan","reg.exportPlanWhy":"What was asked: the tasks in the plan format, as they are now, with the edits made in the UI. Imports again.","reg.exportDomain":"work","reg.exportDomainWhy":"What happened to the work: the task, what the chat tried, what was actually done, and why it did not end done.","reg.exportBot":"runner","reg.exportBotWhy":"What the runner did: environment, every event and step with its exit code, the transport, the reaper, the review machinery.","reg.exportRunTitle":"The whole run as JSON","reg.pick":"Choose tasks","reg.pickWhy":"Tick the tasks you want in one file, across runs and sessions. Nothing else changes.","reg.pickDone":"Done choosing","reg.pickAll":"All of them","reg.pickNone":"None","reg.pickedN":"{n} chosen","reg.pickedNone":"Nothing chosen yet — tick a task below.","reg.bundle":"Download plan, work and runner for the {n} chosen, as one file","reg.bundleWhy":"One JSON holding all three views of exactly the tasks you ticked: what was asked, what happened to it, and what the machine did. This is the file to hand to a chat model when you want it to work out why something went the way it did.","reg.bundleSaved":"Saved as {name}.","reg.fixPrompt":"Fix the prompt and queue it again","reg.fixPromptTitle":'The prompt of "{title}"',"reg.fixPromptHint":"Only the task text, as it will be sent. Level 2, the checks and the git names stay as they are; edit those on the task card. Saving queues the task again with this text; the attempt that ran keeps the text it ran with.","reg.fixPromptSave":"Save and queue again","reg.fixPromptSaved":'"{title}" is queued again with the new prompt. Start the session, or run it again from here.',"reg.fixPromptLoading":"reading the task…","reg.newTask":"New task","reg.newTaskIn":"in session","reg.newTaskNoSessions":"There is no session yet; create one first.","reg.newSession":"New session","reg.newTaskPick":"choose a session…","reg.retriedFreshDone":"blocked, then done in a fresh chat ({n}\xd7)","reg.retriedFreshStill":"still blocked after {n} fresh chat(s)","reg.retriedFreshWhy":"The runner ran this task again in a new conversation after it ended blocked. Done afterwards means the chat was the cause; blocked again means it was not: read the task text, the checks and the machine.","exec.title":"Execution","exec.intro":"How a run behaves when a task does not end done. Saved in data/settings.json; applies to runs started from now on.","exec.retryBlocked":"When a task ends blocked, run it again in a fresh conversation","exec.retryBlockedTimes":"times, then accept the verdict","exec.retryBlockedWhy":"The runner cannot tell why a task blocked: the prompt, the machine, or the chat itself — a long conversation whose early turns Copilot can no longer see. A fresh chat, with the contract sent again, cures a cause in the chat and nothing else. A task that comes back done was blocked by the chat; one that blocks again was not, and both attempts stay on its record. 0 turns this off.","exec.isolation":"Where the bot runs","exec.isolationNone":"Nowhere in particular — this account","exec.isolationNoneAccepted":"This account — I accept unattended runs without isolation","exec.isolationAccount":"A separate low-privilege Windows account","exec.isolationSandbox":"Windows Sandbox","exec.isolationVm":"A virtual machine","exec.isolationWhy":'Commands written by the model run as whoever this process is. Saying so here is what lets a run go unattended: with "nowhere in particular" chosen, a run without a person watching is refused, because nobody watching and nothing containing is the combination this will not be — unless you choose "I accept unattended runs without isolation", which allows it on your responsibility and is recorded with every run as exactly that. It is your statement, not a check — the runner records it, notes the account it actually holds, and says so when the two disagree.',"exec.save":"Save","exec.saved":"Saved. Applies to runs started from now on.","story.show":"What happened","story.hide":"Hide what happened","story.why":"The task as given, every message and reply, every command with its output, the review rounds, and how it ended — live while it runs.","story.loading":"reading the run folder…","story.showChat":"the conversation","story.showCommands":"the commands and their output","story.live":"live","story.showLive":"What is happening now","story.showLiveWhy":"The task is running as you read this: the messages, the commands and their output arrive here as they happen.","row.info":"What are these?","row.infoTitle":"What each of these gives you","row.infoOpenTask":"Opens this task on its session page: the text it was sent, its checks, the review verdict, and the buttons that edit or queue it again.","row.infoChat":"Opens the Microsoft 365 Copilot conversation itself, in a new tab. The bot drives that chat; this is the same thing a person sees.","row.infoExports":"Three JSON files, all about this one task. Hand one to a chat model when you want it to help; they answer different questions:","row.infoWhich":"Debugging a failure usually starts with **work**. **plan** is what you edit and import again. **runner** is for when the machine is the suspect — a missing tool, a held port, a crashed browser.","story.prompt":"The task, as given","story.bot":"bot → chat","story.chat":"chat → bot","story.review":"Review round {n}","story.step":"step {it}.{id}","story.running":"running","story.failedHere":"failed here","story.showOutput":"show output ({n} chars)","story.hideOutput":"hide output","story.showText":"show text ({n} chars)","story.hideText":"hide text","story.ended":"How it ended: done","story.endedBadly":"How it ended: {status}","story.notEnded":"Not ended yet.","sys.profileBot":"In use by the bot's own run right now ({n} Edge process(es)). That is expected while a session runs.","reg.continue":"Continue: run the {n} queued task(s) in {s} session(s)","reg.continueWhy":"Starts every session that still has something queued, in the order shown here, asking before each command.","reg.continueUnattended":"Continue without asking","reg.continueUnattendedWhy":"The same, running every command without stopping for approval.","reg.continueStarted":"Started: {n} session(s), one after another. Watch this page.","reg.continueRunning":"A session is running; it will take its queued tasks in turn.","reg.continuePanelTitle":"Before it continues","reg.continueChain":"These sessions are chains: a failed task stops the rest, and the tasks behind it were written assuming it worked. Each one goes back into the queue, in its place, as it is — or fix its prompt first:","reg.continueIndependent":"These sessions run independent tasks. Their failed ones are offered; untick any you would rather leave:","reg.continueSummary":"{q} queued task(s) plus {r} put back, in {s} session(s), in the order shown above.","reg.continueGo":"Continue, asking before each command","reg.continueNameWhy":"Suggested from the work this continues, and from how many goes at it there have been. The register groups under it and the downloaded files are named after it, so change it if it is wrong.","reg.continueWithFailed":"Continue: run {f} failed and {n} queued task(s) in {s} session(s)","reg.willRequeueFirst":"failed — goes back into the queue first","reg.willRequeueFirstWhy":'This session is a chain: the tasks behind this one were written assuming it worked. "Continue" puts it back in the queue in its place; fix its prompt first if it needs it.',"tree.load":"Show the folders","tree.reload":"Read the folders again","tree.hint":"Click a folder to include it with everything beneath; click again to take it out. The − on a row carves that folder out of an included parent. The lists above are what is saved.","tree.fold":"fold","tree.unfold":"unfold","tree.stateIn":"included, with everything beneath it — click to take it out","tree.stateInherited":"included through a folder above it — click to name it on its own","tree.stateOut":"carved out — press − again to put it back","tree.stateOutInherited":"carved out through a folder above it","tree.stateNone":"not included — click to include it with everything beneath","tree.insideIn":"{n} inside","tree.insideOut":"{n} carved out inside","tree.insideBoth":"{i} inside, {e} carved out","tree.insideWhy":"Folders named in the two lists that this one contains. Unfold it to see them.","tree.alsoOut":"Left out without being listed:","tree.alsoGitignore":"everything .gitignore lists, while that switch is on","tree.alsoEnv":".env files, while that switch is off","tree.alsoAlways":"node_modules, .git, dist and the rest of the build output, always","tree.exclude":"carve this folder out","tree.unexclude":"stop carving this folder out","proj.mirrorToDesktop":"Keep the projects on the Desktop","proj.mirrorToDesktopWhy":"On, every project listed here is copied to the Desktop — one folder per project under {root}, each file's name carrying the project's name — and refreshed before every run, which is how the copies reach OneDrive and the chat's file picker. Off, the project folders are removed from the Desktop. Each project has its own selection of folders below.","proj.mirrorOn":"Every project is on the Desktop under {root}.","proj.mirrorOff":"Nothing is kept on the Desktop.","proj.folders":"Folders that go to the Desktop","proj.foldersHint":"Which of this project's folders are copied. Empty means the whole project, minus what .gitignore lists.","proj.foldersSave":"Save the selection","proj.foldersSaved":"Selection saved.","proj.foldersEdit":"folders","lang.label":"Language","a11y.skip":"Skip to the content","theme.light":"Light","theme.dark":"Dark","theme.toLight":"Switch to the light theme","theme.toDark":"Switch to the dark theme","home.apiDown":"The API is not reachable.","home.noToken":"This browser does not have the key to the API yet.","home.noTokenHint":"Start the interface with {cmd}, which hands it the key; started any other way it has none.","home.apiHint":"Start it from the project folder with {cmd}. Expected at {url}.","home.new":"New session","home.newHint":"A session is one Copilot conversation. Tasks inside it run one after another in that same chat, so later tasks can build on earlier ones.","home.namePlaceholder":"Session name, e.g. payments-service","home.create":"Create","home.sessions":"Sessions","home.loading":"Loading…","home.none":"None yet.","home.col.name":"Name","home.col.tasks":"Tasks","home.col.state":"State","home.col.chat":"Chat","home.col.created":"Created","home.tasksDetail":"({done} done, {queued} queued)","home.notOpened":"not opened","home.col.remove":"Remove","home.delete":"Delete","home.deleteWhy":"Deleting a session removes it from this list and nothing else.","home.deleteConfirm":'Delete the session "{name}" and its {n} task(s)?\n\nWhat it already executed stays in its folders under runs/, and the conversation in Copilot is not touched. This cannot be undone.',"home.deleteRunning":"Stop the session before deleting it.","home.deleted":'"{name}" was deleted.',"home.selectAll":"Select every session","home.selected":"{n} selected","home.deleteSelected":"Delete the {n} selected","home.deleteSelectedConfirm":"Delete {n} session(s)?\n\n{names}\n\nWhat they already executed stays in their folders under runs/, and the conversations in Copilot are not touched. This cannot be undone.","home.deletedMany":"{n} session(s) deleted.","home.deleteSomeFailed":"{n} deleted; {m} could not be: {why}","home.tickForBoth":"The ticks choose what to run and what to delete. Only sessions with something queued can be run.","state.running":"running","state.idle":"idle","state.stopping":"stopping","state.completed":"completed","state.completedTitle":"Every task of this session ended done. Nothing is queued.","state.ended":"ended, with failures","state.endedTitle":"Every task ended, but not all of them done: {n} failed, blocked or stopped. Nothing is queued.","status.queued":"queued","status.running":"running","status.waiting-approval":"waiting for approval","status.done":"done","status.blocked":"not done","status.failed":"failed","status.aborted":"aborted","status.limit-reached":"limit reached","session.crumb":"Sessions","session.run":"Run {n} task(s)","session.runWhy":"Works through the queue on its own, without stopping to ask. This is the ordinary way to run: start it and come back when it has finished.","session.runStep":"Step by step","session.runStepWhy":"Shows you every command before it runs and waits for your decision. For when something has gone wrong, or a task is new and you want to watch what it actually does.","session.unattendedConfirm":"This runs on its own: the commands Copilot writes will be executed without asking you, until the queue is finished. The list of forbidden commands still applies. Start it?","session.stop":"Stop after current step","session.startedAuto":"started — it will work through the queue on its own","session.startedStep":"started — it will ask you before every command","session.notStarted":"not started: {reason}","session.modeUnattended":"not asking any more","session.askAgain":"Ask me again on every step","session.askingAgain":"every further step will be shown for approval","session.stopping":"stopping after the current step","session.willUseModel":"Model: {name}.","session.willUseFiles":"Project files: {root} ({dirs}).","session.noFiles":"Project files: none are attached to these tasks.","session.openChat":"open chat: {name}","session.noChat":"no conversation yet; the first run opens one","session.group":"Share a conversation","session.groupWhy":"Sessions with the same name here run in one Copilot chat: the first to run opens it, the rest join it and see its history. Leave it empty and this session gets a conversation of its own, which is the usual answer.","session.groupPlaceholder":"a name, the same in every session that should share","session.groupSaved":"saved","session.groupHasChat":"This session is already in a conversation, so it stays there. The group decides where a session goes the first time it runs.","approval.title":"Step {n} is waiting for you","approval.run":"Run","approval.runAll":"Run this and the rest without asking","approval.runAllWhy":"Answers this step with Run and stops asking for every step after it, for the rest of this run. Commands on the deny list are still refused, and a command that downloads from the internet still asks.","approval.runAllConfirm":"From here on, commands written by Copilot will run without asking, until this run ends. Commands on the deny list are still refused, and a command that downloads from the internet still asks. Continue?","approval.network":"This command downloads from the internet. The bot never does that on its own, even in a run that does not ask, because a later step could run what arrived. Run it only if you know what it fetches and why.","approval.skip":"Skip","approval.abort":"Abort task","model.title":"Copilot model","model.hint":"The list is read from the chat’s own model picker, so it is whatever your tenant offers today. Leave it on the chat default and nothing is touched; pick one and the conversation is switched to it at the start of each run.","model.default":"whatever the chat is set to (default)","model.refresh":"Read the list from Copilot","model.refreshConfirm":"This opens the bot’s Edge window, reads the model picker and closes it again. It cannot run while a session is running. Continue?","model.refreshing":"opening the chat and reading the picker…","model.refreshed":"read {n} model(s) from the chat","model.readAt":"Read {t}: {n} option(s).","model.chatWasOn":"The chat was on {name}.","model.neverRead":"The list has never been read on this machine. Press the button to read it from the chat.","model.none":"The chat did not offer a model picker.","model.saved":"runs will use {name}","model.savedDefault":"left on the chat default","model.lastUsed":"last run used {name}","model.notInList":"{name} (saved, not in the list that was read)","model.unavailable":"not available","model.defaultIs":"New sessions start on {name}.","model.defaultIsNone":"New sessions start on whatever the chat is set to.","model.makeDefault":"Start new sessions on {name}","model.clearDefault":"Stop setting a model on new sessions","model.defaultSaved":"new sessions will start on {name}","model.defaultCleared":"new sessions will be left on the chat default","model.showDetails":"show what the picker said","l1.title":"Level 1: the base prompt","l1.sent":"sent in this conversation","l1.notSent":"sent with the first task","l1.edit":"edit","l1.hint":"The prompt about how the bot works, sent once per conversation with priority over the level 2 instructions of every task below: the phases of a task, the JSON reply format, the stop word, how to verify before closing, when to declare a task blocked, a deviation or a disputed finding, and the rules level 2 cannot override.","l1.customised":"Using your customised copy.","l1.show":"show the prompt","vcs.title":"Version control","vcs.on":"on","vcs.off":"off","vcs.hint":"The runner does the git itself, before and after every task, and level 1 tells Copilot not to branch or commit. Two of you doing it would leave the repository in a state neither expects.","vcs.enable":"Work on branches and commit what was changed","vcs.enableWhy":"Recommended, and on by default. Without it a task edits your working tree with nothing to go back to. Pushing stays yours: nothing is ever pushed from here.","vcs.repo":"Repository","vcs.repoIs":"Working in {dir}.","vcs.repoNone":"No repository. Set one here, or set the project root under project files.","vcs.branches":"How branches are made","vcs.perTask":"A branch of its own for every task","vcs.perTaskWhy":"Every task branches from the same starting point, so it never sees what the task before it changed. Independent checks against one known state. A task that reads or checks earlier work will not find it here.","vcs.perSession":"One branch for the whole session","vcs.perSessionWhy":"Every task continues on the branch the one before it left, so a later task builds on the earlier work.","vcs.branchName":"Name of that one branch","vcs.branchNameWhy":"Without the prefix. Empty means it is built from the session name, the way it always was. It has no effect in the other mode, where each task names its own.","vcs.commit":"Commit when a task finishes","vcs.commitWhy":"One local commit per task, whatever the outcome, with the summary in the message. Off leaves the changes in the working tree.","vcs.notReady":"Version control is on, but it cannot work yet.","vcs.noRepo":"This folder cannot be used for version control","vcs.noRepoHow":'Version control needs a git repository: a folder with a .git in it. Make one there with "git init", or point this at a project that already is one. Until then the switch stays off, because a switch that is on and does nothing is worse than one that is off.',"vcs.pickFirst":"Choose the project folder first, then turn version control on.","vcs.repoOk":"This folder is a git repository.","vcs.repoField":"Project folder","vcs.ready":"Ready: {dir}, currently on {branch}.","vcs.completeOn":"The complete work of this session is on {branch}.","vcs.noSingleBranch":"There is no single branch with all of this session’s work: each of the {n} task(s) has its own, and HEAD is on whichever ran last.","vcs.pushIsYours":"Nothing is ever pushed. Review the branch and push it yourself.","vcs.saved":"saved","vcs.taskBranch":"branch {branch}","vcs.taskCommit":"commit {commit}","vcs.taskBase":"started from {commit}","vcs.taskProblem":"version control did not run: {problem}","vcs.taskFiles":"{n} file(s) changed","vcs.suspicious":"Committed although it looks like tool output or secrets ({n}) — pointed out once and left in place:","vcs.taskNoFiles":"nothing was committed — the task changed no files","vcs.taskBinary":"binary","mirror.title":"Project files for the chat","mirror.hint":"Selected directories are copied to one flat folder on the Desktop with the path in the file name ({example}), only changed files are rewritten, and the files are attached to the first message of each task. Attaching uploads a copy to your OneDrive.","mirror.enable":"attach project files","mirror.root":"Project root","mirror.listDirs":"List directories","mirror.noDirs":"no selectable directories","mirror.include":"Include (one per line; a directory includes everything beneath it)","mirror.exclude":"Exclude (one per line)","mirror.save":"Save","mirror.stateOn":"files are attached","mirror.stateOff":"no files attached","mirror.unsaved":"Not saved yet.","mirror.unsavedWhy":"These settings take effect only after Save. A run started now would use what was stored before.","mirror.saved":"saved","mirror.browse":"Browse…","mirror.browsing":"pick the folder in the window that opened","mirror.browseCancelled":"no folder picked","mirror.rootHint":"The folder the paths below are relative to.","mirror.rules":"What is copied from it","mirror.gitignore":"Leave out what .gitignore lists","mirror.gitignoreWhy":"On by default. Build output, local scratch files and anything else the project already ignores stay out of the chat. Never decides .env files.","mirror.env":"Copy .env files as well","mirror.envWhy":"Off by default. This switch alone decides the .env files: it does not matter whether the option above is ticked or what the .gitignore says about them.","mirror.envWarn":"The .env files of this project will be copied to the Desktop folder, uploaded to your OneDrive and attached to the chat. They usually hold passwords, keys and tokens. Turn this on?","mirror.envOn":"Secrets will be attached to every task of this session.","mirror.alwaysOut":"Always left out, whatever is ticked: {dirs}.","mirror.conflict":"The same directory cannot be both included and excluded.","mirror.conflictSame":'"{dir}" is in both lists.',"mirror.conflictParent":'"{exclude}" is excluded, but "{include}" is included and lies inside it.',"mirror.conflictFix":"Remove it from one of the two lists. Nothing is saved until you do.","mirror.needRoot":"Enter the project root first.","mirror.check":"Check what would be copied","mirror.checking":"checking…","mirror.checked":"{files} file(s), {size}.","mirror.checkedEnv":"{n} of them are .env files.","mirror.checkedSkipped":"{n} left out.","mirror.checkedNone":"Nothing would be copied with this selection.","mirror.showFiles":"show the list","mirror.showSkipped":"show what was left out","tasks.title":"Tasks","tasks.hint":"Run in this order, in the same conversation. When one finishes with a summary, the next queued one starts. A task that ends any other way stops the run and leaves the rest queued.","chain.title":"What happens when a task does not finish","chain.stop":"Stop the queue at the first failure","chain.stopWhy":"Treats the queue as one chain, which is what a suite usually is: a later task builds on what an earlier one did, so running it against a machine in an unplanned state is worse than not running it. The rest stay queued and can be run once the failure is dealt with.","chain.continue":"Carry on with the next task","chain.continueWhy":"Treats the tasks as independent checks that happen to share one conversation. One failing says nothing about the next, and the failures are read afterwards in the register.","chain.savedStop":"the queue will stop at the first failure","chain.savedContinue":"the queue will carry on past a failure","chain.locked":"This cannot be changed while the session is running.","tasks.none":"No tasks yet. Add one below.","task.iterations":"{n} iteration(s)","task.edit":"Edit","task.cancel":"Cancel","task.delete":"Delete","task.branch":"Branch for this task","task.branchWhy":"Without the prefix, which the runner adds. Empty means the name is built from the session and the task title, the way it always was.","task.branchIgnored":"This session works on one branch, so a name here is ignored. The branch is named in the version-control panel above.","task.commitMessage":"Commit message","task.commitWhy":"The first line is the subject. Copilot's summary and how the task ended are added underneath either way. Empty means the subject is the task title.","task.gitNames":'git: branch {branch} \xb7 commit "{subject}"',"task.gitBranchOnly":"git: branch {branch}","task.gitCommitOnly":'git: commit "{subject}"',"task.editAll":"Edit — title, instructions, prompt, branch and commit","checks.title":"Checks","run.unattended":"on its own, without stopping to ask","run.confirm":"step by step, asking before each command","restart.button":"Run again from here","restart.why":"Puts the code back to before this task, then queues this task and every one after it in the same run — including the ones that never got their turn — and starts them.","restart.checking":"working out what that would do…","restart.cannot":"Cannot start again from here: {problem}","restart.noRepo":" (no repository — version control is off for this work)","restart.alreadyQueued":" (already waiting, so it is left alone)","restart.repoLine":" {repo}\n back to {commit} on a new branch {branch}, and {n} later commit(s) stay on {kept}","restart.confirm":'Start again from "{title}"?\n\nThe code goes back first:\n{repos}\n\nNothing is deleted — the later commits stay on the branch they were made on, one checkout away.\n\nThen {tasks} task(s) in {sessions} session(s) are queued again and started {mode}:\n{list}\n\nAnything those tasks already produced is replaced by what they produce this time.',"restart.failed":"It did not start: {problem}","restart.started":"Started again: {requeued} task(s) queued, {repos} repository(ies) taken back.","review.title":"Independent review","review.hint":"When a task finishes and its checks pass, a second conversation is opened that had no part in the work. It is given the task and the files that changed — not the summary — and it decides by running the work, not by reading it. If it finds problems they go back to be fixed, and the task cannot close until it passes or the rounds run out.","review.on":"on","review.off":"off","review.enable":"Check every task with a second conversation","review.enableWhy":"Catches the class of defect neither the checks nor the task itself can: a claim nobody thought to test. Costs an extra conversation per task.","review.modelField":"Model for the review","review.modelWhy":"Leave empty to use this session’s own model. A different one is worth setting: a fresh conversation removes attachment to the work, but not the blind spots of the model that did it.","review.modelSame":"the same model as the work","review.save":"Save","review.saved":"Saved.","review.verdict.pass":"review passed","review.verdict.fail":"review found problems","review.verdict.error":"review did not run","review.verdict.skipped":"not reviewed","review.ran":"after running {n} command(s)","review.rounds":"{n} round(s)","review.onModel":"on {model}","review.findings":"what it found ({n})","review.evidence":"Evidence","review.problem":"The review could not be carried out: {problem}. The work was accepted unreviewed.","review.taskOff":"This task is not reviewed.","review.aboutTask":"about the task, not the work","review.repeated":"came back after a reported fix","task.deviations":"Not as the task said ({n})","task.deviationDid":"Did instead","task.deviationWhy":"Because","reg.deviations":"{n} deviation(s)","reg.deviationsWhy":"The model could not follow every instruction as written and said what it did instead. Open the task to read them.","task.disputes":"Review findings the model disputed ({n})","reg.disputes":"{n} dispute(s)","reg.disputesWhy":"The model said a review finding was wrong and gave evidence; the next reviewer was told. Open the task to read both sides.","task.readOnly":"read-only","reg.readOnlyWhy":"This task must not change files. The runner fails it if the working tree changed when it ended.","task.leftovers":"Left running and stopped by the runner ({n}):","task.leftoverPorts":"listening on {ports}","task.ranWith":"Ran with Node {node} \xb7 npm {npm} \xb7 git {git} \xb7 PowerShell {pwsh}","task.took":"took {d}","task.runningFor":"running for {d}","reg.runTook":"took {d}","reg.runRunning":"running for {d}","session.runClock":"This run: {n} task(s) \xb7 {d}","session.runClockLive":"This run: {n} task(s) \xb7 {d} so far","restore.button":"Restore","restore.why":"Put the repository back to the code as it was before this task started.","restore.checking":"checking…","restore.cannot":"Cannot restore: {problem}","restore.confirm":'Put {repo} back to the code as it was before "{title}"?\n\nA new branch {branch} is created at commit {commit} and checked out. Nothing is deleted and no history is rewritten.',"restore.confirmLosing":'Put {repo} back to the code as it was before "{title}"?\n\nA new branch {branch} is created at commit {commit} and checked out.\n\n{n} commit(s) made after that point will NOT be on it:\n{list}\n\nThey are not lost — they stay on {kept}, and you can switch back to it at any time. But the working tree will no longer contain that work, and anything built from it will need building again.',"restore.done":"The repository is on {branch} at {commit}. {n} later commit(s) stay on {kept}.","restore.doneNothing":"The repository is on {branch} at {commit}. There was nothing after it.","restore.failed":"The restore did not happen: {problem}","checks.why":"What has to be true before this task is allowed to end. The runner runs these itself after Copilot reports the task as done: if one fails, the failure goes back into the chat with its output and the task carries on until they pass or it runs out of attempts.","checks.none":"No checks. This task ends when Copilot says it has.","checks.noneWhy":"Add one for anything a command can settle: a compile, a test run, a file that must exist.","checks.add":"Add a check","checks.remove":"Remove","checks.name":"What it checks","checks.namePlaceholder":"the tests pass","checks.kind":"Must be","checks.run":"Command","checks.file":"File","checks.value":"Text","checks.valueRegex":"Pattern","checks.cwd":"In folder","checks.results":"Last time these ran","checks.passed":"passed","checks.failed":"failed","checks.n":"{n} check(s)","checks.fromReview":"From reviews ({n})","checks.fromReviewWhy":"Checks reviewers gave with their findings: the mechanical test that would have caught each one. They stay with the task for every later attempt, so what one review noticed is never again found by chance.","checks.state.suspended":"suspended — disputed, until the next review rules","checks.state.dropped":"dropped — the next review did not raise it again","checks.kind.exit-zero":"the command succeeds","checks.kind.exit-nonzero":"the command fails","checks.kind.output-contains":"its output contains","checks.kind.output-omits":"its output does not contain","checks.kind.output-matches":"its output matches","checks.kind.file-exists":"the file exists","checks.kind.file-missing":"the file does not exist","checks.kind.file-contains":"the file contains","task.rerun":"Run again","task.rerunWhy":"Puts this task back in the queue. What the earlier attempt did is kept and shown under the task.","task.rerunConfirm":'Queue "{title}" again? The earlier attempt is kept, with its own log.',"task.saveAndRerun":"Save and queue it again","task.editRanConfirm":'Save this edit to "{title}" and queue the task again? The attempt that already ran is kept, with the text it ran with.',"task.editRanWhy":"This task has already run, so saving an edit queues it again. The attempt that ran keeps its own text, its log and its summary.","task.attemptText":"the task as this attempt ran it","task.attempts":"earlier attempts ({n})","task.attemptN":"attempt {n}","task.deleteConfirm":'Delete queued task "{title}"?',"task.deleteConfirmRan":'Remove "{title}" from this session? It has already run; what it executed stays in its run folder under runs/.',"task.started":"started {t}","task.added":"added {t}","task.finished":"finished {t}","task.save":"Save","task.whatWasDone":"What was done","task.l2Show":"level 2 for this task ({n} line(s))","task.noL2":"no level 2 instructions for this task","task.promptAndL2":"task prompt and level 2","task.l2":"level 2","task.prompt":"task","task.firstMessage":"the exact first message that opened this task","task.files":"everything executed, and the files","task.log":"task-log.txt: the whole task as text","task.reports":"reports sent to Copilot:","task.artifacts":"downloaded files:","task.replies":"raw replies:","task.finalReply":"the last message Copilot sent","save.log":"save the log","save.attemptLog":"save this attempt's log","save.saving":"saving…","save.why":"Writes the file into a folder on the Desktop and opens Explorer with it already selected, so it can be dragged straight into the chat that orchestrates the work.","save.done":"Saved to {path} — Explorer is open on it, ready to drag.","save.savedOnly":"Saved to {path}. {note}","save.failed":"It could not be saved: {problem}","form.title":"Add a task","form.hint":"Goes to the end of the queue. If the session is running it will be picked up after the current tasks; if it is idle, press Run above. Level 2 is prefilled from the previous task so a series of tasks shares it.","form.titleLabel":"Title","form.titlePlaceholder":"short name, e.g. run the unit tests","form.taskLabel":"Task","form.taskPlaceholder":"What to do, what the result should be, what is out of bounds.","form.add":"Add to queue","form.queued":"queued","export.title":"Download the work","export.hint":"The conversation of the tasks you pick, as one text file. Nothing is sent anywhere: the file is built here and saved by your browser.","export.nothing":"Nothing has run in this session yet.","export.all":"Select all","export.none":"Clear the selection","export.selected":"{n} selected.","export.allOf":"Nothing ticked, so all {n} that have run.","export.outcome":"Expected and actual ({n})","export.full":"The whole conversation ({n})","export.outcomeWhy":"Expected and actual is the short one: for each task, the message that opened it and the answer that closed it. The whole conversation adds every report sent in between and every reply that came back.","l2.label":"Level 2: project, domain and team instructions for this task","l2.loadPreset":"load a preset…","l2.saveAs":"Save as preset","l2.saveAsPrompt":"Save these level 2 instructions as a preset named:","l2.savedAs":'saved as "{name}"',"l2.placeholder":"What the runner cannot know: the project, its layout, how tests run, the conventions, what never to touch.\nLeave empty if there is nothing to add. Level 1 always wins over anything here.","live.title":"Live","live.none":"Nothing yet. Events appear here while a run is in progress.","l1page.title":"Level 1: the base prompt","l1page.hint":'The prompt about how the bot works. It is sent once at the start of every conversation, before any project instructions, and a later task in the same conversation gets a short reminder of it. It tells the model the phases of a task (receive, plan a step, emit, read the results, repeat, verify, close), the JSON reply format the runner parses, the stop word, what a "done" needs (a verification it has run and read), when a task is "blocked" (at least two real approaches and something specific in the way), how to declare an instruction that cannot be followed as written and how to dispute a review finding, how the results file and refused steps come back, and the rules that level 2 cannot override. The independent review has its own prompt (prompts/review1.md). Edit it only if you know why: the parser expects exactly the format described here.',"l1page.custom":"Customised copy in data/level1.md","l1page.shipped":"Shipped version, prompts/level1.md","l1page.unsaved":"unsaved changes","l1page.save":"Save","l1page.saved":"Saved. Applies to sessions started from now on.","l1page.reset":"Reset to shipped","l1page.resetConfirm":"Discard your edits and go back to the base prompt shipped with the project?","l1page.resetDone":"Reset to the shipped base prompt.","presets.title":"Level 2 presets","presets.hint":"Level 2 is what you know and the runner does not: the project, the domain, the team's conventions, the tools in use. It is sent with every task and can be different for every task. Save the ones you reuse here and pick them when adding a task. Level 1 always has priority over anything written here.","presets.name":"Name","presets.namePlaceholder":"e.g. payments-service team","presets.content":"Instructions","presets.contentPlaceholder":"Project: ...\nRepository layout: ...\nHow we run tests: ...\nThings never to touch: ...","presets.save":"Save preset","presets.saved":'Saved "{name}".',"presets.list":"Saved","presets.none":"None yet.","presets.edit":"Edit","presets.delete":"Delete","presets.deleteConfirm":'Delete preset "{name}"?',"presets.show":"show","sys.machine":"This machine","sys.loading":"Loading…","sys.node":"Node","sys.edge":"Edge","sys.edgeMissing":"not found","sys.profile":"Bot profile","sys.profileMissing":"(not created yet: run cop login)","sys.profileInUse":"Profile in use","sys.profileHeld":"Edge is holding the profile (pids {pids}). A run would fail. Close that Edge window.","sys.profileUnknown":"could not check","sys.profileFree":"free","sys.desktop":"Desktop","sys.desktopSynced":"(backed up by OneDrive)","sys.desktopLocal":"(not backed up by OneDrive; mirror stays local)","sys.cwd":"Fallback folder for commands (a session runs in its own project folder)","sys.runs":"Runs folder","sys.data":"Data folder","sys.mode":"Default mode","sys.settings":"Settings","sys.settingsHint":"Read from {file} next to the project. It has the same shape as {example}; anything missing takes the default. Edit the file and restart the API.","sys.asSaved":"As saved","sys.resolved":"Resolved paths","sys.signin":"Sign-in","sys.signinHint":"Signing in is done once, from the terminal, so that the bot never handles credentials:","reg.title":"Task register","reg.hint":"Every task of every session in one place: what has been done, what is being done right now and what is still ahead. The order inside a session is the order it runs in.","reg.total":"tasks","reg.done":"done","reg.open":"ahead","reg.failedCount":"did not finish","reg.activeNow":"Running now","reg.upcoming":"What is next","reg.upcomingHint":"In the order they will run. A session runs its queue from the top; the first one of a session is the next one out.","reg.past":"What has been done","reg.pastHint":"Newest first. A task that did not end with a summary stopped its session and left the rest of the queue waiting.","reg.none":"No tasks yet.","reg.noUpcoming":"Nothing queued. Every task has run.","reg.noPast":"Nothing has run yet.","reg.noMatch":"Nothing matches the filter.","reg.next":"next in this session","reg.queuePos":"{n} in the queue","reg.waitingRun":"waiting for the session to be started","reg.willFollow":"runs after the {n} task(s) above it","reg.sessionRunning":"the session is running","reg.iterations":"{n} iteration(s)","reg.took":"took {d}","reg.filterSession":"Session","reg.filterStatus":"Status","reg.allSessions":"all sessions","reg.allStatuses":"all statuses","reg.search":"Search in the titles and the summaries","reg.searchPlaceholder":"a word from the task","reg.clear":"Clear the filters","reg.viewFlow":"Flow","reg.viewList":"List","reg.viewLabel":"View","reg.openTask":"task details","reg.openLog":"log","reg.runningCount":"running now","reg.attempts":"this is attempt {n} — see the {m} before it","reg.attemptsOne":"this is attempt {n} — see the one before it","reg.attemptN":"attempt {n}","reg.attemptLog":"log of this attempt","reg.blockedWhat":"The task ended without the work being done. What was tried and what is in the way is in the reason below.","reg.runGroup":"Started together","reg.runGroupHint":"One run is one press of a start button. Everything below was sent off together, in this order, through one browser window.","reg.runOf":"Run of {t} task(s) in {s} session(s)","reg.runAt":"started {when}","reg.runWith":"ran with {n} other task(s)","reg.runAlone":"ran on its own","reg.runTitle":"Run of {t} task(s) in {s} session(s), started {when}","reg.groupBy":"By run","reg.notInARun":"Not part of a run","reg.notInARunHint":"Tasks still waiting, and tasks that ran before this system began recording which of them were started together.","reg.col.task":"Task","reg.col.session":"Session","reg.col.status":"Status","reg.col.started":"Started","reg.col.took":"Took","reg.col.result":"Result","reg.stopped":"stopped: {reason}","reg.refresh":"Refresh","reg.updated":"updated {t}","ap.title":"Appearance","ap.hint":"Kept in this browser only. Nothing here is sent anywhere or shared with another machine.","ap.theme":"Theme","ap.themeWhy":"Warm light for a bright room, warm dark for a dim one.","ap.a11y":"Accessibility","ap.a11yHint":"Each of these can be turned on by itself; they are independent of the theme and of the language.","ap.size":"Text size","ap.sizeNormal":"Normal","ap.sizeLarge":"Large","ap.sizeHuge":"Largest","ap.sizeWhy":"Scales the whole interface, not only the body text.","ap.contrast":"Higher contrast","ap.contrastWhy":"Stronger borders and darker text. Drops some of the warmth in exchange for legibility.","ap.motion":"Less motion","ap.motionWhy":"No transitions, and the live log stops scrolling itself while a run is in progress.","ap.links":"Underline every link","ap.linksWhy":"Links stop relying on colour alone to be recognisable.","ap.focus":"Thick focus outline","ap.focusWhy":"Makes what the keyboard is on impossible to lose, when tabbing through a page.","ap.reset":"Back to the defaults","ap.example":"How it looks","ap.exampleText":"A task that ended with a summary, one waiting for approval, and a link.","ap.exampleLink":"a link in a sentence","nav.import":"Plan from JSON","nav.defaults":"Settings","def.title":"What every new session starts with","def.intro":"Three things are chosen here once instead of in every session: the folders being worked on, the model that does the work, and the model that reviews it. Sessions keep their own copies, so any of them can be changed afterwards without touching these.","def.autoSave":"Everything on this page saves itself as you change it. There is nothing to press.","def.savedAutomatically":"saved as you type","def.saveAnyway":"Save","def.saveAnywayWhy":"It is already saved. This button exists for the comfort of pressing one.","proj.nameField":"Name of the project","proj.namePlaceholder":"the folder's own name","proj.nameWhy":"What this project is called everywhere else: its folder on the Desktop, the name in front of every mirrored file, and the list Kerrigan is given. Empty means the folder's own name.","proj.nameSaved":"Name saved.","def.reviewTitle":"Model for the review","def.reviewIntro":"The model a new session's independent review starts on. A different model from the one doing the work is the cheapest way to make the second opinion genuinely second: a fresh conversation removes attachment to the work, not the model's blind spots.","def.reviewField":"Review model","def.reviewNone":"The session's own model","def.reviewSaved":"New sessions will be reviewed by {name}.","def.reviewCleared":"Cleared. New sessions are reviewed by their own model.","def.reviewSame":"This is the same model as the one doing the work. A different one would catch more.","def.reviewAffectsNew":"A new session starts with this review model, copied onto it when it is created. A plan that names none for a session gets it too.","def.reviewAffectsExisting":"Sessions that already exist keep theirs. Their review panel offers this one with a button.","def.reviewAffectsBatch":"A run of several sessions starts with this review model chosen, and says so before it writes it onto them.","def.reviewDefaultIs":"Default review model: {name}","def.reviewNoneShort":"No default review model is set.","def.modelTitle":"Model for new sessions","def.modelIntro":"The model a session starts on, by the exact name the chat's own picker shows. The list is whatever was read from the chat last; it belongs to Microsoft and differs per tenant, so it is never a list written into this project.","def.modelField":"Model","def.modelNone":"Leave the chat on whatever it is set to","def.modelSaved":"New sessions will start on {name}.","def.modelCleared":"Cleared. New sessions leave the chat on whatever it is set to.","def.modelAffectsNew":"A new session starts on this model, copied onto it at the moment it is created.","def.modelAffectsExisting":"Sessions that already exist keep the model they have. Their picker offers this one with a button.","def.modelAffectsBatch":"A run of several sessions starts with this model chosen, and says so before it writes it onto them.","def.modelDefaultIs":"Default model: {name}","def.modelNoneShort":"No default model is set.","def.modelUseIt":"use it here","proj.title":"The project you are working on","proj.intro":"Set the folder once here and every new session starts pointed at it, instead of it being typed in again each time. Sessions keep their own folders, so any of them can be pointed somewhere else afterwards.","proj.field":"Project folder","proj.save":"Save","proj.saved":"New sessions will start in {dir}.","proj.clear":"Clear","proj.cleared":"Cleared. New sessions start with no folder chosen.","proj.none":"No project folder is set, so every session starts with its folders empty.","proj.isRepo":"This folder is a git repository, so sessions pointed at it can branch and commit.","proj.notRepo":"This folder is not a git repository","proj.notRepoWhy":"It can still be the project: the files are there and tasks can work in it. What it cannot do is carry version control, so the switch for that stays off until the folder is a repository.","proj.affects":"What this changes, and what it does not","proj.affectsNew":"A new session starts with this folder in both its project-files field and its version-control field. Neither is switched on by being filled in.","proj.affectsExisting":"Sessions that already exist are untouched. Their folder fields offer this one with a button, and taking it is your decision.","proj.affectsPlan":"The brief for a chat model is offered this folder, so the model neither has to ask for it nor invent one.","proj.affectsNever":"Nothing here ever changes what a running session is doing.","proj.toSessions":"To the sessions","proj.toImport":"To the plan import","proj.defaultIs":"Default project: {dir}","proj.noneShort":"No default project is set.","proj.useIt":"use it here","proj.setIt":"set one","proj.change":"change it","proj.others":"Other projects","proj.isDefault":"the default","proj.isDefaultWhy":"New sessions start in this one, and the plan brief offers it first.","proj.entryName":"Name","proj.entryDir":"Folder","proj.addTitle":"Add another project","proj.listIntro":"Every project this machine works in. The first is the default: new sessions start there. The others are named so a plan can send work to them. All of them are described the same way, and all of them save as you type.","proj.othersIntro":"The rest of the folders you work in — a front end, a back end, the test suite — each with a short name. New sessions still start on the default above. These are offered with a button wherever a folder is chosen, and the plan brief lists them by path, so a plan across several repositories is written with the folders that exist instead of asking for each one.","proj.otherName":"Name","proj.otherDir":"Folder","proj.otherAdd":"Add","proj.otherRemove":"Remove","proj.othersNone":"No other projects yet.","proj.othersSaved":"Saved: {n} other project(s).","proj.otherRepo":"git repository","proj.otherNotRepo":"not a git repository","proj.otherUse":"use {name}","plan.title":"A plan written by a chat model","plan.intro":"Describe the work to any chat model you like, let it ask you the questions, and paste what it writes back here. This page creates the sessions and the tasks; it starts nothing.","plan.step1":"1. Take this to the chat","plan.step1Hint":"Copy the whole text into a new conversation with a model of your choice. It explains what this runner is, makes the model interview you about the work, and pins the exact format it must answer in.","plan.persona":"Kerrigan, the persona: two levels","plan.personaWhy":"What you copy is one text in two parts. The software part is this project's and does not change: what the bot is, the plan format, how to read the register's exports when a task fails, and how to check the finished run against the assignment. The organisation part is yours: where tickets come from, which company sources to search, how your machine is laid out, your team's conventions. While it is empty, the brief tells Kerrigan to interview you about all of that first, write the text, and ask you to paste it below and save; once saved it travels with every copy and the questions stop. Delete it and they come back.","plan.softwarePart":"Software level (fixed)","plan.orgPart":"How work is done here: the organisation and the projects","plan.orgHint":"What anybody doing a task here would need to know: where tickets come from, where to search, the conventions and templates, and for each project its path, what it does, what it needs before it builds, how it is built and tested, and what goes wrong there. Not what the organisation or the projects are called — a name helps with no task. Written once and read for months. Paste here the first of the documents Kerrigan hands back.","plan.personaPart":"How the tasks are carried out: the agent's persona","plan.personaHint":"How the agent that does the work goes about it: what it is responsible for and what it is not, its approach, the phases it works through, and what it hands back at the end. It has no name — it is a way of working, not a character — so you can swap it when different work needs a different approach. Written into every task when a plan is imported, so a session keeps the approach it was created with. Paste your own here, or the second of the documents Kerrigan hands back.","plan.workPart":"This work","plan.workHint":"What this group of tasks is about: the ticket, the goal, which projects it touches, what has already been decided or tried, what must not change meanwhile. Replaced whenever the work changes. Paste here the last of the documents Kerrigan hands back.","plan.ctxWritten":"written","plan.ctxEmpty":"empty — Kerrigan will ask","plan.ctxSaved":"saved; the next copy of the brief carries it","plan.ctxClear":"Empty this","plan.ctxCleared":"emptied; Kerrigan will ask about it again","plan.ctxClearConfirm":"Empty this text? Kerrigan will ask about it again the next time you copy the brief.","plan.copyBrief":"Copy the brief","plan.copied":"copied","plan.copyFailed":"The browser would not let the page copy. Select the text and copy it by hand.","plan.showBrief":"Show the text","plan.hideBrief":"Hide the text","plan.briefLang":"The brief is in the language this interface is in.","plan.briefAsks":"The brief does the asking","plan.briefAsksWhy":"Nothing is set here. The brief makes the model ask you whether the runner should do version control and which folder to work in, and the answers go into the JSON, per session. A plan that leaves them out is refused on import, with the exact wording to hand back to the chat.","plan.step2":"2. Bring the answer back","plan.step2Hint":"Paste it, drop the file on the box, or pick a file. Prose and code fences around the JSON are fine; they are stripped.","plan.placeholder":"Paste the JSON the chat model wrote…","plan.drop":"Drop a .json file here","plan.dropActive":"Let go to read the file","plan.browse":"Choose a file…","plan.clear":"Clear","plan.check":"Check it","plan.checking":"checking…","plan.import":"Create the sessions and tasks","plan.importing":"creating…","plan.fileError":"That file could not be read: {reason}","plan.fileTooBig":"That file is {size}, which is far larger than any plan. Nothing was read.","plan.valid":"This is a plan this system can read: {sessions} session(s), {tasks} task(s).","plan.invalid":"This is not a plan this system can read yet.","plan.issues":"What is wrong","plan.issuesHint":"Copy these back into the same conversation and ask for the whole corrected JSON. The paths say where in the document each problem is.","plan.copyIssues":"Copy the errors","plan.warnings":"Worth knowing","plan.duplicates":"This is already here","plan.duplicatesHint":"These sessions exist already, with exactly these tasks. Importing makes a second copy, which is allowed but is usually a mis-paste. Check that this is the corrected plan and not the old one.","plan.duplicateRow":"{name} — {tasks} identical task(s), imported {when}","plan.duplicateConfirm":"These sessions already exist with exactly these tasks:\n\n{names}\n\nImporting creates a second copy of them. Continue?","plan.cleared":"The box was emptied, so the same plan cannot be imported twice by accident.","plan.col.planFail":"If a session fails","plan.runThese":"Run these sessions","plan.preview":"What will be created","plan.notes":"Notes from the model","plan.col.session":"Session","plan.col.tasks":"Tasks","plan.col.chain":"On a failed task","plan.col.repo":"Repository","plan.noRepo":"none","plan.step3":"3. Check it, then start it yourself","plan.step3Hint":"Nothing runs on its own. Read what was created, change anything you want to change, and start it from the sessions list.","plan.imported":"Created {sessions} session(s) with {tasks} task(s). Nothing has started.","plan.toSessions":"To the sessions list","batch.title":"Run several sessions","batch.hint":"Tick the sessions to run, and they run one after another, in the order they are listed here. Two conversations cannot run at the same time: the browser profile belongs to one at a time.","batch.selected":"{n} selected, {tasks} queued task(s)","batch.notRunnable":"{n} of them have nothing queued and are left out of the run.","batch.pickFirst":"Choose which sessions to run","batch.pickFirstWhy":"Tick them in the list below and the two buttons come alive. They run in the order shown here, one after another.","batch.nothingRunnable":"None of the ticked sessions has anything queued","batch.nothingRunnableWhy":"Only tasks still waiting in a queue are run. Add a task to one of them, or tick a session that has some.","batch.oneRunning":"A session is already running on its own","batch.oneRunningWhy":"Two conversations cannot run at the same time, so a run of several has to wait. Let it finish, or stop it from its own page.","batch.selectQueued":"Select every session with something queued","batch.selectNone":"Select none","batch.onFailure":"If a session fails","batch.model":"Model for this run","batch.waiting":"{n} step(s) waiting for you","approval.waitingHere":"A step is waiting for your decision","approval.waitingHereWhy":"A run started from this page asks its questions here, so it does not look stuck while a session page nobody has open waits for an answer.","batch.reviewModel":"Model that reviews the work","batch.reviewModelKeep":"Each session keeps its own","batch.reviewModelWhy":"The independent review runs in its own conversation after each task. Putting it on a different model from the one doing the work is the cheapest way to make the second opinion genuinely second: a fresh conversation removes attachment to the work, but not the blind spots of the model that produced it.","batch.reviewSame":"This is the same model that does the work. A different one would catch more.","batch.reviewOffIn":"The review is switched off in {n} of the selected session(s); a model here does not turn it on.","batch.modelKeep":"Each session keeps its own","batch.modelWhy":"Choosing one here writes it onto every selected session before the run starts, so what a session says it uses and what it used stay the same thing afterwards.","batch.modelOverrides":"{n} of the selected session(s) are on a different model and will be changed to this one.","batch.modelNone":"No models have been read from the chat yet.","batch.modelRunning":"On {name}.","batch.vcsProblem":"Version control cannot run in these sessions","batch.vcsProblemWhy":"They will still run, but no branch will be made and nothing will be committed, so the work is left loose in the working tree. The commonest cause is an earlier run that was interrupted before the runner could commit.","batch.vcsProblemRow":"{name}: {problem}","batch.hiddenWhileRunning":"Choosing sessions, the model and what a failure means are hidden while a run is in progress, because none of them can change what is already running. They come back when it ends.","batch.fromPlan":"Selected from the plan you just imported, in its order.","batch.chain":"Stop, and leave the rest as they are","batch.chainWhy":"The sessions are one piece of work in order. A later session usually assumes the earlier ones worked, so running it after a failure tests nothing.","batch.independent":"Carry on with the next session","batch.independentWhy":"The sessions are separate pieces of work that happen to have been started together. One failing says nothing about the next.","batch.run":"Run {n} session(s)","batch.runWhy":"Works through the selected sessions one after another, on its own, without stopping to ask. This is the ordinary way to run.","batch.runStep":"Step by step","batch.runStepWhy":"Stops before every command in every session and waits for you. For chasing a problem down, or when a plan is new.","batch.unattendedConfirm":"This runs on its own, across {n} session(s): the commands Copilot writes will be executed without asking you, until every one of them is finished. The list of forbidden commands still applies. Start them?","batch.stop":"Stop after the current step","batch.pause":"Pause after this task","batch.pauseWhy":"Lets the task that is running finish properly — its checks, its review, its commit — and then holds. Everything still queued stays queued, and Continue picks it up where it left off.","batch.pausing":"pausing: the task that is running will finish first, and the rest of the queue is kept","batch.resume":"Take the hold off","batch.resumeWhy":"Carries on with the queue, as though the pause had not been pressed. Only works while the paused task is still running.","batch.stopWhy":'Cuts in after the current step. The task it interrupts ends "aborted", part-done. Use Pause instead if you only want to think.',"batch.notStarted":"not started: {reason}","batch.notStartedTitle":"The run did not start","batch.notStartedIsolation":'Settings → "Where the bot runs": choose where the bot runs, or accept unattended runs without isolation',"batch.nothingQueued":"nothing queued","batch.progress":"Running {name} — {done} of {total} done.","batch.finished":"Finished: {done} done, {failed} failed, {skipped} not run.","batch.stopping":"stopping after the current step; the sessions after this one stay as they are","batch.col.session":"Session","batch.debug":"Download everything as JSON","batch.debugWhy":"One file with what ran and what happened across these sessions: every step and its exit code, every summary, every check, and what each task committed. For handing to someone — or something — that has to work out why a run went the way it did.","batch.debugSelected":"for the {n} selected session(s)","batch.debugLast":"for the sessions of the last run","batch.col.state":"State","batch.col.ran":"Tasks","batch.col.why":"Why","batch.state.waiting":"waiting","batch.state.running":"running","batch.state.done":"done","batch.state.failed":"failed","batch.state.stopped":"stopped","batch.state.skipped":"not run","batch.ranOf":"{ran} ran, {failed} failed"},bg:{"nav.label":"Основно","nav.sessions":"Сесии","nav.live":"live","nav.liveTitle":"Ботът работи в момента: {n} сесия(и). Отворете регистъра, за да гледате.","nav.history":"Регистър на задачите","nav.level1":"Основен prompt","nav.presets":"Шаблони ниво 2","nav.appearance":"Изглед","nav.system":"Система","dialog.confirmTitle":"Сигурни ли сте?","dialog.noticeTitle":"Съобщение","dialog.ok":"Добре","dialog.cancel":"Отказ","batch.runName":"Име на това пускане","batch.runNamePlaceholder":"напр. rules-engine, втори опит","batch.runNameWhy":"Регистърът групира задачите на едно пускане под него, а изтеглените файлове носят името му. Оставено празно, името идва от плана, от който са сесиите; без такъв пускането се води по своето id.","reg.runUnnamed":"Пускане без име","reg.runBy":"{name} \xb7 {t} задачи в {s} сесии","reg.runCounts":"{done} готови \xb7 {failed} провалени","reg.exportTitle":"Изтегли като JSON","reg.exportPlan":"план","reg.exportPlanWhy":"Какво е поискано: задачите във формата на плана, както са сега, с редакциите от интерфейса. Внася се отново.","reg.exportDomain":"работа","reg.exportDomainWhy":"Какво се случи с работата: задачата, какво пробва чатът, какво реално е направено и защо не е завършила готова.","reg.exportBot":"runner","reg.exportBotWhy":"Какво направи runner-ът: среда, всяко събитие и стъпка с кода ѝ на изход, транспортът, спирането на процеси, механиката на рецензията.","reg.exportRunTitle":"Цялото пускане като JSON","reg.pick":"Избери задачи","reg.pickWhy":"Отметни задачите, които искаш в един файл, през пускания и сесии. Нищо друго не се променя.","reg.pickDone":"Готово с избора","reg.pickAll":"Всички","reg.pickNone":"Нито една","reg.pickedN":"избрани: {n}","reg.pickedNone":"Още нищо не е избрано — отметни задача по-долу.","reg.bundle":"Изтегли план, работа и runner за избраните {n}, в един файл","reg.bundleWhy":"Един JSON с трите изгледа на точно отметнатите задачи: какво е поискано, какво се е случило с него и какво е направила машината. Това е файлът, който се подава на чат модел, когато искаш да проумее защо нещо е тръгнало така.","reg.bundleSaved":"Запазен като {name}.","reg.fixPrompt":"Поправи prompt-а и върни в опашката","reg.fixPromptTitle":'Prompt-ът на „{title}"',"reg.fixPromptHint":"Само текстът на задачата, както ще бъде изпратен. Ниво 2, проверките и имената за git остават каквито са; тях ги редактирате от картата на задачата. Запазването връща задачата в опашката с този текст; опитът, който е минал, пази текста, с който е минал.","reg.fixPromptSave":"Запази и върни в опашката","reg.fixPromptSaved":'„{title}" е върната в опашката с новия prompt. Пуснете сесията или „Пусни отново оттук".',"reg.fixPromptLoading":"чета задачата…","reg.newTask":"Нова задача","reg.newTaskIn":"в сесия","reg.newTaskNoSessions":"Още няма сесия; първо създайте една.","reg.newSession":"Нова сесия","reg.newTaskPick":"изберете сесия…","reg.retriedFreshDone":"блокира, после готова в нов чат ({n}\xd7)","reg.retriedFreshStill":"още блокирана след {n} нови чата","reg.retriedFreshWhy":"Runner-ът пусна тази задача отново в нов разговор, след като завърши блокирана. Готова след това означава, че причината е била чатът; блокирана отново означава, че не е: четете текста на задачата, проверките и машината.","exec.title":"Изпълнение","exec.intro":"Как се държи едно пускане, когато задача не завърши готова. Пази се в data/settings.json; важи за пускания, започнати от сега нататък.","exec.retryBlocked":"Когато задача завърши блокирана, пусни я отново в нов разговор","exec.retryBlockedTimes":"пъти, после приеми присъдата","exec.retryBlockedWhy":"Runner-ът не може да отсъди защо задача е блокирала: prompt-ът, машината или самият чат — дълъг разговор, чиито ранни ходове Copilot вече не вижда. Нов чат, с изпратен наново договор, лекува причина в чата и нищо друго. Задача, която след това е готова, е била блокирана от чата; задача, която блокира пак, не е, и двата опита остават в записа ѝ. 0 го изключва.","exec.isolation":"Къде върви ботът","exec.isolationNone":"Никъде специално — в този акаунт","exec.isolationNoneAccepted":"В този акаунт — приемам пускане без надзор без изолация","exec.isolationAccount":"Отделен Windows акаунт с малки права","exec.isolationSandbox":"Windows Sandbox","exec.isolationVm":"Виртуална машина","exec.isolationWhy":"Командите, написани от модела, вървят като този процес. Да го кажете тук е това, което позволява пускане без надзор: при избрано „никъде специално“ пускане без човек се отказва, защото никой да не гледа и нищо да не огражда е комбинацията, която това няма да бъде — освен ако не изберете „приемам пускане без надзор без изолация“, което го позволява на ваша отговорност и се записва с всяко пускане точно като това. Това е ваше твърдение, не проверка — runner-ът го записва, отбелязва акаунта, който всъщност държи, и казва, когато двете не съвпадат.","exec.save":"Запази","exec.saved":"Запазено. Важи за пускания, започнати от сега нататък.","story.show":"Какво се случи","story.hide":"Скрий какво се случи","story.why":"Заданието както е дадено, всяко съобщение и отговор, всяка команда с изхода ѝ, кръговете на рецензията и как е завършило — на живо, докато върви.","story.loading":"чета папката на изпълнението…","story.showChat":"разговорът","story.showCommands":"командите и изходът им","story.live":"на живо","story.showLive":"Какво се случва в момента","story.showLiveWhy":"Задачата се изпълнява, докато четете това: съобщенията, командите и изходът им пристигат тук, докато се случват.","row.info":"Какво са тези?","row.infoTitle":"Какво дава всяко от тях","row.infoOpenTask":"Отваря задачата на страницата на сесията ѝ: текста, който ѝ е изпратен, проверките ѝ, присъдата на рецензията и бутоните, с които се редактира или се връща в опашката.","row.infoChat":"Отваря самия разговор в Microsoft 365 Copilot, в нов таб. Ботът кара този чат; това е същото, което вижда и човек.","row.infoExports":"Три JSON файла, всички за тази една задача. Подайте някой от тях на чат модел, когато искате помощ; те отговарят на различни въпроси:","row.infoWhich":"Дебъгването на провал обикновено започва с **работа**. **план** е това, което редактирате и внасяте отново. **runner** е за когато заподозреният е машината — липсващ инструмент, зает порт, паднал браузър.","story.prompt":"Заданието, както е дадено","story.bot":"бот → чат","story.chat":"чат → бот","story.review":"Рецензия, кръг {n}","story.step":"стъпка {it}.{id}","story.running":"работи","story.failedHere":"провали се тук","story.showOutput":"покажи изхода ({n} знака)","story.hideOutput":"скрий изхода","story.showText":"покажи текста ({n} знака)","story.hideText":"скрий текста","story.ended":"Как завърши: готова","story.endedBadly":"Как завърши: {status}","story.notEnded":"Още не е завършила.","sys.profileBot":"В момента се ползва от собственото изпълнение на бота ({n} процеса на Edge). Това е очаквано, докато сесия работи.","reg.continue":"Продължи: пусни {n} чакащи задачи в {s} сесии","reg.continueWhy":"Пуска всяка сесия, в която още има нещо в опашката, в показания тук ред, с питане преди всяка команда.","reg.continueUnattended":"Продължи без да пита","reg.continueUnattendedWhy":"Същото, но всяка команда се изпълнява без спиране за одобрение.","reg.continueStarted":"Пуснато: {n} сесии, една след друга. Гледайте тази страница.","reg.continueRunning":"Сесия работи; тя ще вземе чакащите си задачи поред.","reg.continuePanelTitle":"Преди да продължи","reg.continueChain":"Тези сесии са вериги: провалена задача спира останалите, а задачите след нея са писани с презумпцията, че е минала. Всяка се връща в опашката, на мястото си, както е — или първо ѝ поправете prompt-а:","reg.continueIndependent":"Тези сесии пускат независими задачи. Провалените им се предлагат; махнете отметката на тези, които предпочитате да оставите:","reg.continueSummary":"{q} чакащи задачи плюс {r} върнати, в {s} сесии, в показания по-горе ред.","reg.continueGo":"Продължи, с питане преди всяка команда","reg.continueNameWhy":"Предложено от работата, която продължава, и от това кой пореден опит е. Регистърът групира под него, а изтеглените файлове го носят — така че го променете, ако не е вярно.","reg.continueWithFailed":"Продължи: пусни {f} провалили се и {n} чакащи задачи в {s} сесии","reg.willRequeueFirst":"провалена — връща се в опашката първа","reg.willRequeueFirstWhy":'Тази сесия е верига: задачите след тази са писани с презумпцията, че е минала. „Продължи" я връща в опашката на мястото ѝ; ако трябва, първо ѝ поправете prompt-а.',"tree.load":"Покажи папките","tree.reload":"Прочети папките отново","tree.hint":"Кликнете папка, за да я включите с всичко под нея; кликнете пак, за да я махнете. Знакът − на реда изрязва тази папка от включена родителска. Списъците горе са това, което се запазва.","tree.fold":"сгъни","tree.unfold":"разгъни","tree.stateIn":"включена, с всичко под нея — кликнете, за да я махнете","tree.stateInherited":"включена през папка над нея — кликнете, за да я именувате отделно","tree.stateOut":"изрязана — натиснете − пак, за да я върнете","tree.stateOutInherited":"изрязана през папка над нея","tree.stateNone":"не е включена — кликнете, за да я включите с всичко под нея","tree.insideIn":"{n} вътре","tree.insideOut":"{n} изрязани вътре","tree.insideBoth":"{i} вътре, {e} изрязани","tree.insideWhy":"Папки от двата списъка, които се намират в тази. Разгънете я, за да ги видите.","tree.alsoOut":"Остава навън, без да е изброено:","tree.alsoGitignore":"всичко, което .gitignore изброява, докато този превключвател е включен","tree.alsoEnv":".env файловете, докато този превключвател е изключен","tree.alsoAlways":"node_modules, .git, dist и останалият build изход, винаги","tree.exclude":"изрежи тази папка","tree.unexclude":"спри да изрязваш тази папка","proj.mirrorToDesktop":"Дръж проектите на Desktop-а","proj.mirrorToDesktopWhy":"Включено, всеки проект от списъка се копира на Desktop-а — по една папка на проект под {root}, като името на всеки файл носи името на проекта — и се обновява преди всяко пускане; така копията стигат до OneDrive и до избора на файлове в чата. Изключено, папките на проектите се махат от Desktop-а. Всеки проект има собствен избор на папки по-долу.","proj.mirrorOn":"Всички проекти са на Desktop-а под {root}.","proj.mirrorOff":"Нищо не се държи на Desktop-а.","proj.folders":"Папки, които отиват на Desktop-а","proj.foldersHint":"Кои папки от този проект се копират. Празно означава целият проект, без това, което .gitignore изброява.","proj.foldersSave":"Запази избора","proj.foldersSaved":"Изборът е запазен.","proj.foldersEdit":"папки","lang.label":"Език","a11y.skip":"Към съдържанието","theme.light":"Светла","theme.dark":"Тъмна","theme.toLight":"Превключи към светлата тема","theme.toDark":"Превключи към тъмната тема","home.apiDown":"API-то не отговаря.","home.noToken":"Този браузър още няма ключа за API-то.","home.noTokenHint":"Пуснете интерфейса с {cmd}, който му дава ключа; пуснат по друг начин, той няма такъв.","home.apiHint":"Пуснете го от папката на проекта с {cmd}. Очаква се на {url}.","home.new":"Нова сесия","home.newHint":"Сесията е един разговор с Copilot. Задачите в нея се изпълняват една след друга в същия чат, така че следващите могат да стъпват на предишните.","home.namePlaceholder":"Име на сесията, напр. payments-service","home.create":"Създай","home.sessions":"Сесии","home.loading":"Зареждане…","home.none":"Още няма.","home.col.name":"Име","home.col.tasks":"Задачи","home.col.state":"Състояние","home.col.chat":"Чат","home.col.created":"Създадена","home.tasksDetail":"({done} готови, {queued} чакащи)","home.notOpened":"не е отворен","home.col.remove":"Махане","home.delete":"Изтрий","home.deleteWhy":"Изтриването на сесия я маха от този списък и нищо повече.","home.deleteConfirm":"Да изтрия ли сесията „{name}“ и нейните {n} задача(и)?\n\nВече изпълненото остава в папките ѝ под runs/, а разговорът в Copilot не се пипа. Това не може да се върне.","home.deleteRunning":"Спрете сесията, преди да я изтриете.","home.deleted":"„{name}“ беше изтрита.","home.selectAll":"Избери всички сесии","home.selected":"{n} избрани","home.deleteSelected":"Изтрий избраните {n}","home.deleteSelectedConfirm":"Да изтрия ли {n} сесия(и)?\n\n{names}\n\nВече изпълненото остава в папките им под runs/, а разговорите в Copilot не се пипат. Това не може да се върне.","home.deletedMany":"Изтрити са {n} сесия(и).","home.deleteSomeFailed":"{n} изтрити; {m} не можаха: {why}","home.tickForBoth":"Отметките избират какво да се пусне и какво да се изтрие. Пускат се само сесии с нещо в опашката.","state.running":"работи","state.idle":"свободна","state.stopping":"спира","state.completed":"завършена","state.completedTitle":"Всички задачи на тази сесия са приключили готови. Нищо не чака в опашката.","state.ended":"приключила, с провали","state.endedTitle":"Всички задачи са приключили, но не всички готови: {n} провалени, блокирани или спрени. Нищо не чака в опашката.","status.queued":"чака","status.running":"работи","status.waiting-approval":"чака одобрение","status.done":"готова","status.blocked":"неизпълнена","status.failed":"провалена","status.aborted":"прекратена","status.limit-reached":"достигнат лимит","session.crumb":"Сесии","session.run":"Пусни {n} задача(и)","session.runWhy":"Минава през опашката сама, без да спира да пита. Това е обичайният начин: пускате и се връщате, когато приключи.","session.runStep":"Стъпка по стъпка","session.runStepWhy":"Показва ви всяка команда, преди да я изпълни, и чака решението ви. За когато нещо се е объркало или задачата е нова и искате да видите какво прави в действителност.","session.unattendedConfirm":"Това се изпълнява само: командите, които Copilot напише, ще се пускат, без да ви питат, докато опашката не свърши. Списъкът със забранени команди продължава да важи. Да я пуснем ли?","session.stop":"Спри след текущата стъпка","session.startedAuto":"стартира — ще мине през опашката сама","session.startedStep":"стартира — ще пита преди всяка команда","session.notStarted":"не е стартирано: {reason}","session.modeUnattended":"вече не пита","session.askAgain":"Питай ме пак на всяка стъпка","session.askingAgain":"всяка следваща стъпка ще чака одобрение","session.stopping":"спира след текущата стъпка","session.willUseModel":"Модел: {name}.","session.willUseFiles":"Файлове на проекта: {root} ({dirs}).","session.noFiles":"Файлове на проекта: не се прикачат към тези задачи.","session.openChat":"отвори чата: {name}","session.noChat":"още няма разговор; първото изпълнение го отваря","session.group":"Споделяне на разговор","session.groupWhy":"Сесиите с едно и също име тук се изпълняват в един чат на Copilot: първата, която тръгне, го отваря, а останалите се присъединяват към него и виждат историята му. Оставено празно, сесията получава собствен разговор — което е обичайният отговор.","session.groupPlaceholder":"име, едно и също във всички сесии, които да споделят","session.groupSaved":"запазено","session.groupHasChat":"Тази сесия вече е в разговор и остава в него. Групата решава къде отива сесията при първото ѝ пускане.","approval.title":"Стъпка {n} чака вашето решение","approval.run":"Изпълни","approval.runAll":"Изпълни без да питаш повече","approval.runAllWhy":"Отговаря на тази стъпка с Изпълни и престава да пита за следващите до края на това изпълнение. Забранените команди пак се отказват, а команда, която тегли от интернет, пак пита.","approval.runAllConfirm":"Оттук нататък командите, написани от Copilot, ще се изпълняват без да питат, докато това изпълнение приключи. Забранените команди пак се отказват, а команда, която тегли от интернет, пак пита. Продължавате ли?","approval.network":"Тази команда тегли от интернет. Ботът никога не го прави сам, дори при пускане без питане, защото следваща стъпка може да пусне изтегленото. Изпълнете я само ако знаете какво тегли и защо.","approval.skip":"Пропусни","approval.abort":"Прекрати задачата","model.title":"Модел на Copilot","model.hint":"Списъкът се чете от самия избор на модел в чата, така че съдържа това, което вашият тенант предлага днес. Ако оставите по подразбиране, нищо не се пипа; ако изберете модел, разговорът се превключва на него в началото на всяко изпълнение.","model.default":"каквото е настроено в чата (по подразбиране)","model.refresh":"Прочети списъка от Copilot","model.refreshConfirm":"Това отваря прозореца на Edge на бота, прочита избора на модел и го затваря. Не може да се изпълни, докато тече сесия. Продължавате ли?","model.refreshing":"отварям чата и чета избора…","model.refreshed":"прочетени са {n} модела от чата","model.readAt":"Прочетено на {t}: {n} опции.","model.chatWasOn":"Чатът беше на {name}.","model.neverRead":"Списъкът никога не е четен на тази машина. Натиснете бутона, за да го прочетете от чата.","model.none":"Чатът не показва избор на модел.","model.saved":"изпълненията ще ползват {name}","model.savedDefault":"оставено по подразбиране на чата","model.lastUsed":"последното изпълнение ползва {name}","model.notInList":"{name} (запазен, но го няма в прочетения списък)","model.unavailable":"не е наличен","model.defaultIs":"Новите сесии тръгват с {name}.","model.defaultIsNone":"Новите сесии тръгват с това, което е настроено в чата.","model.makeDefault":"Новите сесии да тръгват с {name}","model.clearDefault":"Да не се задава модел на новите сесии","model.defaultSaved":"новите сесии ще тръгват с {name}","model.defaultCleared":"новите сесии ще остават на настроеното в чата","model.showDetails":"покажи какво каза изборът","l1.title":"Ниво 1: основен prompt","l1.sent":"изпратен в този разговор","l1.notSent":"изпраща се с първата задача","l1.edit":"редактирай","l1.hint":"Prompt-ът за начина, по който работи ботът, изпращан веднъж на разговор с приоритет над инструкциите от ниво 2 на всяка задача по-долу: фазите на една задача, JSON форматът на отговора, стоп думата, как се проверява преди затваряне, кога задача е блокирана, отклонение или оспорена находка, и правилата, които ниво 2 не може да промени.","l1.customised":"Използва се вашето редактирано копие.","l1.show":"покажи prompt-а","vcs.title":"Контрол на версиите","vcs.on":"включен","vcs.off":"изключен","vcs.hint":"Изпълнителят сам прави git преди и след всяка задача, а ниво 1 казва на Copilot да не прави клонове и комити. Ако и двамата го правите, хранилището остава в състояние, което никой от двамата не очаква.","vcs.enable":"Работи по клонове и комитвай промененото","vcs.enableWhy":"Препоръчва се и е включено по подразбиране. Без него задачата променя работното ви дърво без път назад. Push-ването остава ваше: оттук никога не се push-ва.","vcs.repo":"Хранилище","vcs.repoIs":"Работи се в {dir}.","vcs.repoNone":"Няма хранилище. Задайте го тук или задайте корен на проекта при файловете.","vcs.branches":"Как се правят клоновете","vcs.perTask":"Отделен клон за всяка задача","vcs.perTaskWhy":"Всяка задача тръгва от една и съща точка и никога не вижда промените на предишната. Независими проверки срещу едно известно състояние. Задача, която чете или проверява по-ранна работа, няма да я намери тук.","vcs.perSession":"Един клон за цялата сесия","vcs.perSessionWhy":"Всяка задача продължава оттам, където е спряла предишната, така че по-късната стъпва върху предишната работа.","vcs.branchName":"Име на този един клон","vcs.branchNameWhy":"Без представката. Празно значи, че се сглобява от името на сесията, както винаги е било. В другия режим няма ефект — там всяка задача си именува своя.","vcs.commit":"Комит при приключване на задача","vcs.commitWhy":"По един локален комит на задача, независимо от изхода, с обяснението в съобщението. Изключено оставя промените в работното дърво.","vcs.notReady":"Контролът на версиите е включен, но още не може да работи.","vcs.noRepo":"Тази папка не може да се ползва за контрол на версиите","vcs.noRepoHow":"Контролът на версиите иска git хранилище — папка, в която има .git. Направете такова с „git init“ там или посочете проект, който вече е хранилище. Дотогава превключвателят остава изключен, защото включен превключвател, който не прави нищо, е по-лош от изключен.","vcs.pickFirst":"Първо изберете папката на проекта, после включете контрола на версиите.","vcs.repoOk":"Тази папка е git хранилище.","vcs.repoField":"Папка на проекта","vcs.ready":"Готово: {dir}, в момента на {branch}.","vcs.completeOn":"Цялата работа на тази сесия е на {branch}.","vcs.noSingleBranch":"Няма един клон с цялата работа на сесията: всяка от {n} задачи има свой, а HEAD е на последно изпълнената.","vcs.pushIsYours":"Нищо не се push-ва. Прегледайте клона и го качете сами.","vcs.saved":"запазено","vcs.taskBranch":"клон {branch}","vcs.taskCommit":"комит {commit}","vcs.taskBase":"тръгнала от {commit}","vcs.taskProblem":"контролът на версиите не се изпълни: {problem}","vcs.taskFiles":"{n} променени файла","vcs.suspicious":"Комитнато, макар да прилича на изход на инструмент или на тайни ({n}) — посочено веднъж и оставено:","vcs.taskNoFiles":"нищо не беше комитнато — задачата не промени файлове","vcs.taskBinary":"двоичен","mirror.title":"Файлове на проекта за чата","mirror.hint":"Избраните директории се копират в една плоска папка на Desktop с пътя в името на файла ({example}), презаписват се само променените файлове, и файловете се прикачат към първото съобщение на всяка задача. Прикачването качва копие в OneDrive.","mirror.enable":"прикачай файловете на проекта","mirror.root":"Корен на проекта","mirror.listDirs":"Покажи директориите","mirror.noDirs":"няма подходящи директории","mirror.include":"Включи (по една на ред; директория включва всичко под нея)","mirror.exclude":"Изключи (по една на ред)","mirror.save":"Запази","mirror.stateOn":"файловете се прикачат","mirror.stateOff":"не се прикачат файлове","mirror.unsaved":"Още не е запазено.","mirror.unsavedWhy":"Тези настройки влизат в сила едва след Запази. Изпълнение, започнато сега, ще ползва записаното преди това.","mirror.saved":"запазено","mirror.browse":"Избери папка…","mirror.browsing":"изберете папката в отворилия се прозорец","mirror.browseCancelled":"не е избрана папка","mirror.rootHint":"Папката, спрямо която са пътищата по-долу.","mirror.rules":"Какво се копира от него","mirror.gitignore":"Не добавяй това, което е в .gitignore","mirror.gitignoreWhy":"Включено по подразбиране. Компилираното, локалните временни файлове и всичко останало, което проектът вече игнорира, не влиза в чата. Няма отношение към .env файловете.","mirror.env":"Копирай и .env файловете","mirror.envWhy":"Изключено по подразбиране. Само тази отметка решава за .env файловете: няма значение дали опцията отгоре е маркирана, нито какво пише за тях в .gitignore.","mirror.envWarn":"Ще копирам .env файловете на този проект в папката на Desktop, ще се качат в OneDrive и ще се прикачат към чата. В тях обикновено има пароли, ключове и токени. Да включа ли това?","mirror.envOn":"Тайните ще се прикачат към всяка задача на тази сесия.","mirror.alwaysOut":"Винаги остават навън, независимо от отметките: {dirs}.","mirror.conflict":"Една и съща директория не може да е едновременно включена и изключена.","mirror.conflictSame":"„{dir}“ е и в двата списъка.","mirror.conflictParent":"„{exclude}“ е изключена, а „{include}“ е включена и се намира в нея.","mirror.conflictFix":"Махнете я от единия списък. Дотогава нищо не се запазва.","mirror.needRoot":"Първо въведете корена на проекта.","mirror.check":"Провери какво ще се копира","mirror.checking":"проверявам…","mirror.checked":"{files} файла, {size}.","mirror.checkedEnv":"От тях {n} са .env файлове.","mirror.checkedSkipped":"{n} остават навън.","mirror.checkedNone":"С този избор нищо няма да се копира.","mirror.showFiles":"покажи списъка","mirror.showSkipped":"покажи какво остава навън","tasks.title":"Задачи","tasks.hint":"Изпълняват се в този ред, в същия разговор. Когато една приключи с обяснение, започва следващата чакаща. Задача, която приключи по друг начин, спира изпълнението и останалите остават да чакат.","chain.title":"Какво става, когато задача не приключи успешно","chain.stop":"Спри опашката при първата провалена","chain.stopWhy":"Третира опашката като една верига, каквото обикновено е един suite: следващата задача стъпва върху направеното от предишната, затова да се изпълнява върху машина в непланирано състояние е по-злото. Останалите остават да чакат и могат да се пуснат, след като провалът е отстранен.","chain.continue":"Продължи със следващата задача","chain.continueWhy":"Третира задачите като независими проверки, които просто споделят един разговор. Провалът на една не казва нищо за следващата, а провалите се четат после в регистъра.","chain.savedStop":"опашката ще спира при първата провалена","chain.savedContinue":"опашката ще продължава след провал","chain.locked":"Това не може да се променя, докато сесията работи.","tasks.none":"Още няма задачи. Добавете по-долу.","task.iterations":"{n} итерация(и)","task.edit":"Редактирай","task.cancel":"Отказ","task.delete":"Изтрий","task.branch":"Клон за тази задача","task.branchWhy":"Без представката — нея я слага runner-ът. Празно значи, че името се сглобява от сесията и заглавието на задачата, както винаги е било.","task.branchIgnored":"Тази сесия работи по един клон, така че име тук се игнорира. Клонът се именува в панела за контрол на версиите по-горе.","task.commitMessage":"Текст на комита","task.commitWhy":"Първият ред е заглавният. Резюмето на Copilot и как е приключила задачата се добавят отдолу така или иначе. Празно значи, че заглавният ред е заглавието на задачата.","task.gitNames":"git: клон {branch} \xb7 комит „{subject}“","task.gitBranchOnly":"git: клон {branch}","task.gitCommitOnly":"git: комит „{subject}“","task.editAll":"Промени — заглавие, инструкции, текст, клон и комит","checks.title":"Проверки","run.unattended":"самостоятелно, без да спира да пита","run.confirm":"стъпка по стъпка, с питане преди всяка команда","restart.button":"Пусни отново оттук","restart.why":"Връща кода отпреди тази задача, след което пуска нея и всички след нея от същото изпълнение — включително онези, които изобщо не са стигнали до ред.","restart.checking":"изчислява се какво би станало…","restart.cannot":"Не може да се пусне отново оттук: {problem}","restart.noRepo":" (няма хранилище — контролът на версиите е изключен за тази работа)","restart.alreadyQueued":" (вече чака, затова се оставя както си е)","restart.repoLine":" {repo}\n назад до {commit} на нов клон {branch}, а {n} по-късни комита остават на {kept}","restart.confirm":"Да пусна ли отново от „{title}“?\n\nПърво кодът се връща:\n{repos}\n\nНищо не се трие — по-късните комити остават на клона, на който са направени, на един checkout разстояние.\n\nСлед това {tasks} задача(и) в {sessions} сесия(и) се нареждат отново и тръгват {mode}:\n{list}\n\nВсичко, което тези задачи вече са произвели, се заменя с това, което произведат сега.","restart.failed":"Не тръгна: {problem}","restart.started":"Пуснато отново: {requeued} задача(и) в опашката, {repos} хранилище(а) върнати назад.","review.title":"Независима рецензия","review.hint":"Когато задачата приключи и проверките ѝ минат, се отваря втори разговор, който не е участвал в работата. Получава задачата и променените файлове — не и резюмето — и решава, като изпълни работата, а не като я прочете. Ако намери проблеми, те се връщат за поправка, и задачата не може да приключи, докато не мине или не свършат рундовете.","review.on":"включена","review.off":"изключена","review.enable":"Проверявай всяка задача с втори разговор","review.enableWhy":"Хваща класа дефекти, който нито проверките, нито самата задача могат: твърдение, за което никой не се е сетил да провери. Струва по един допълнителен разговор на задача.","review.modelField":"Модел за рецензията","review.modelWhy":"Остави празно, за да ползва модела на сесията. Друг модел си струва: свежият разговор маха привързаността към работата, но не и слепите петна на модела, който я е свършил.","review.modelSame":"същият модел като на работата","review.save":"Запази","review.saved":"Запазено.","review.verdict.pass":"рецензията мина","review.verdict.fail":"рецензията намери проблеми","review.verdict.error":"рецензията не се проведе","review.verdict.skipped":"без рецензия","review.ran":"след {n} изпълнени команди","review.rounds":"{n} рунд(а)","review.onModel":"на {model}","review.findings":"какво намери ({n})","review.evidence":"Доказателство","review.problem":"Рецензията не можа да се проведе: {problem}. Работата е приета без рецензия.","review.taskOff":"Тази задача не се рецензира.","review.aboutTask":"за задачата, не за работата","review.repeated":"върна се след докладвана поправка","task.deviations":"Не както задачата казва ({n})","task.deviationDid":"Направено вместо това","task.deviationWhy":"Защото","reg.deviations":"{n} отклонение(я)","reg.deviationsWhy":"Моделът не е могъл да следва всяка инструкция буквално и е казал какво е направил вместо това. Отвори задачата, за да ги прочетеш.","task.disputes":"Оспорени находки на рецензията ({n})","reg.disputes":"{n} оспорване(ия)","reg.disputesWhy":"Моделът е казал, че находка на рецензията е грешна, с доказателство; следващият рецензент е уведомен. Отвори задачата за двете страни.","task.readOnly":"само за четене","reg.readOnlyWhy":"Тази задача не бива да променя файлове. Runner-ът я проваля, ако работното дърво е променено в края ѝ.","task.leftovers":"Оставени работещи и спрени от runner-а ({n}):","task.leftoverPorts":"слуша на {ports}","task.ranWith":"Изпълнено с Node {node} \xb7 npm {npm} \xb7 git {git} \xb7 PowerShell {pwsh}","task.took":"отне {d}","task.runningFor":"работи от {d}","reg.runTook":"отне {d}","reg.runRunning":"работи от {d}","session.runClock":"Това пускане: {n} задачи \xb7 {d}","session.runClockLive":"Това пускане: {n} задачи \xb7 {d} досега","restore.button":"Върни","restore.why":"Връща хранилището към кода, какъвто е бил преди тази задача да започне.","restore.checking":"проверява се…","restore.cannot":"Не може да се върне: {problem}","restore.confirm":"Да върна ли {repo} към кода отпреди „{title}“?\n\nСъздава се нов клон {branch} на комита {commit} и се превключва на него. Нищо не се изтрива и никаква история не се пренаписва.","restore.confirmLosing":"Да върна ли {repo} към кода отпреди „{title}“?\n\nСъздава се нов клон {branch} на комита {commit} и се превключва на него.\n\n{n} комита, направени след този момент, НЯМА да са в него:\n{list}\n\nТе не са изгубени — остават на {kept} и можете да се върнете на него по всяко време. Но работното дърво вече няма да съдържа тази работа, и всичко построено от нея ще трябва да се построи наново.","restore.done":"Хранилището е на {branch}, на комит {commit}. {n} по-късни комита остават на {kept}.","restore.doneNothing":"Хранилището е на {branch}, на комит {commit}. След него нямаше нищо.","restore.failed":"Връщането не се случи: {problem}","checks.why":"Какво трябва да е вярно, преди задачата да има право да приключи. Runner-ът ги изпълнява сам, след като Copilot докладва задачата за готова: ако някоя не мине, провалът се връща в чата заедно с изхода си и задачата продължава, докато не минат или не ѝ свършат опитите.","checks.none":"Няма проверки. Тази задача приключва, когато Copilot каже, че е приключила.","checks.noneWhy":"Добавете за всичко, което една команда може да реши: компилация, пускане на тестове, файл, който трябва да съществува.","checks.add":"Добави проверка","checks.remove":"Махни","checks.name":"Какво проверява","checks.namePlaceholder":"тестовете минават","checks.kind":"Трябва","checks.run":"Команда","checks.file":"Файл","checks.value":"Текст","checks.valueRegex":"Израз","checks.cwd":"В папка","checks.results":"Последното им изпълнение","checks.passed":"мина","checks.failed":"не мина","checks.n":"{n} проверки","checks.fromReview":"От рецензии ({n})","checks.fromReviewWhy":"Проверки, дадени от рецензентите заедно с находките им: механичният тест, който би хванал всяка. Остават със задачата за всеки следващ опит, така че забелязаното веднъж не се намира повече по случайност.","checks.state.suspended":"спряна — оспорена, до присъдата на следващата рецензия","checks.state.dropped":"отпаднала — следващата рецензия не повдигна находката отново","checks.kind.exit-zero":"командата да успее","checks.kind.exit-nonzero":"командата да се провали","checks.kind.output-contains":"изходът ѝ да съдържа","checks.kind.output-omits":"изходът ѝ да не съдържа","checks.kind.output-matches":"изходът ѝ да съвпада с","checks.kind.file-exists":"файлът да съществува","checks.kind.file-missing":"файлът да не съществува","checks.kind.file-contains":"файлът да съдържа","task.rerun":"Пусни отново","task.rerunWhy":"Връща задачата в опашката. Направеното от предишния опит се запазва и се показва под задачата.","task.rerunConfirm":"Да върна ли „{title}“ в опашката? Предишният опит се запазва, със собствен дневник.","task.saveAndRerun":"Запази и върни в опашката","task.editRanConfirm":"Да запазя ли промяната в „{title}“ и да върна задачата в опашката? Вече изпълненият опит се запазва с текста, с който е изпълнен.","task.editRanWhy":"Тази задача вече е изпълнявана, затова записът на промяна я връща в опашката. Изпълненият опит си остава със собствен текст, дневник и обяснение.","task.attemptText":"задачата, както е изпълнена в този опит","task.attempts":"предишни опити ({n})","task.attemptN":"опит {n}","task.deleteConfirm":"Да изтрия ли чакащата задача „{title}“?","task.deleteConfirmRan":"Да махна ли „{title}“ от сесията? Тя вече е изпълнена; изпълненото остава в папката ѝ под runs/.","task.started":"започната {t}","task.added":"добавена {t}","task.finished":"приключила {t}","task.save":"Запази","task.whatWasDone":"Какво е направено","task.l2Show":"ниво 2 за тази задача ({n} реда)","task.noL2":"тази задача няма инструкции от ниво 2","task.promptAndL2":"задачата и ниво 2","task.l2":"ниво 2","task.prompt":"задача","task.firstMessage":"точното първо съобщение, с което започна задачата","task.files":"всичко изпълнено и файловете","task.log":"task-log.txt: цялата задача като текст","task.reports":"отчети, пратени на Copilot:","task.artifacts":"свалени файлове:","task.replies":"сурови отговори:","task.finalReply":"последното съобщение от Copilot","save.log":"запази log-а","save.attemptLog":"запази log-а на този опит","save.saving":"запазва се…","save.why":"Записва файла в папка на десктопа и отваря Explorer с вече избран файл, за да може да се влачи направо в чата, който води работата.","save.done":"Запазен в {path} — Explorer е отворен върху него, готов за влачене.","save.savedOnly":"Запазен в {path}. {note}","save.failed":"Не можа да бъде запазен: {problem}","form.title":"Добави задача","form.hint":"Отива в края на опашката. Ако сесията работи, ще бъде поета след текущите задачи; ако е свободна, натиснете Изпълни горе. Ниво 2 се попълва от предишната задача, така че серия от задачи го споделя.","form.titleLabel":"Заглавие","form.titlePlaceholder":"кратко име, напр. пусни unit тестовете","form.taskLabel":"Задача","form.taskPlaceholder":"Какво да се направи, какъв трябва да е резултатът, какво е извън обхвата.","form.add":"Добави в опашката","form.queued":"добавена","export.title":"Изтегли свършената работа","export.hint":"Разговорът на избраните задачи, като един текстов файл. Нищо не се изпраща навън: файлът се съставя тук и се записва от браузъра ви.","export.nothing":"В тази сесия още нищо не е изпълнявано.","export.all":"Избери всички","export.none":"Изчисти избора","export.selected":"избрани: {n}.","export.allOf":"Няма отметнати, затова всички {n} изпълнени.","export.outcome":"Очаквано и получено ({n})","export.full":"Целият разговор ({n})","export.outcomeWhy":"„Очаквано и получено“ е краткият вариант: за всяка задача първото съобщение и отговорът, с който тя приключва. Целият разговор добавя и всички отчети помежду и всички отговори.","l2.label":"Ниво 2: инструкции за проекта, домейна и екипа за тази задача","l2.loadPreset":"зареди шаблон…","l2.saveAs":"Запази като шаблон","l2.saveAsPrompt":"Запази тези инструкции от ниво 2 като шаблон с име:","l2.savedAs":"запазено като „{name}“","l2.placeholder":"Това, което изпълнителят не може да знае: проектът, структурата му, как се пускат тестовете, конвенциите, какво никога да не се пипа.\nОставете празно, ако няма какво да добавите. Ниво 1 винаги има предимство пред написаното тук.","live.title":"На живо","live.none":"Още нищо. Събитията се появяват тук, докато тече изпълнение.","l1page.title":"Ниво 1: основен prompt","l1page.hint":'Prompt-ът за начина, по който работи ботът. Изпраща се веднъж в началото на всеки разговор, преди инструкциите за проекта, а следваща задача в същия разговор получава кратко напомняне за него. Казва на модела фазите на една задача (получи, планирай стъпка, изпрати, прочети резултата, повтори, провери, затвори), JSON формата на отговора, който runner-ът парсва, стоп думата, какво изисква „done" (проверка, която сам е пуснал и прочел), кога задача е „blocked" (поне два реални подхода и нещо конкретно на пътя), как се обявява инструкция, която не може да се изпълни както е написана, и как се оспорва находка от рецензия, как се връщат файлът с резултатите и отказаните стъпки, и правилата, които ниво 2 не може да промени. Независимата рецензия има собствен prompt (prompts/review1.md). Редактирайте го само ако знаете защо: парсърът очаква точно описания тук формат.',"l1page.custom":"Редактирано копие в data/level1.md","l1page.shipped":"Оригиналът от проекта, prompts/level1.md","l1page.unsaved":"незапазени промени","l1page.save":"Запази","l1page.saved":"Запазено. Важи за сесии, започнати от сега нататък.","l1page.reset":"Върни оригинала","l1page.resetConfirm":"Да отхвърля ли редакциите ви и да върна основния prompt, доставен с проекта?","l1page.resetDone":"Върнат е оригиналният основен prompt.","presets.title":"Шаблони за ниво 2","presets.hint":"Ниво 2 е това, което вие знаете, а изпълнителят не: проектът, домейнът, конвенциите на екипа, използваните инструменти. Изпраща се с всяка задача и може да е различно за всяка. Запазете тук тези, които преизползвате, и ги избирайте при добавяне на задача. Ниво 1 винаги има предимство пред написаното тук.","presets.name":"Име","presets.namePlaceholder":"напр. екип payments-service","presets.content":"Инструкции","presets.contentPlaceholder":"Проект: ...\nСтруктура на репото: ...\nКак пускаме тестове: ...\nКакво никога да не се пипа: ...","presets.save":"Запази шаблона","presets.saved":"Запазено „{name}“.","presets.list":"Запазени","presets.none":"Още няма.","presets.edit":"Редактирай","presets.delete":"Изтрий","presets.deleteConfirm":"Да изтрия ли шаблона „{name}“?","presets.show":"покажи","sys.machine":"Тази машина","sys.loading":"Зареждане…","sys.node":"Node","sys.edge":"Edge","sys.edgeMissing":"не е намерен","sys.profile":"Профил на бота","sys.profileMissing":"(още не е създаден: пуснете cop login)","sys.profileInUse":"Профилът се ползва от","sys.profileHeld":"Edge държи профила (pid {pids}). Изпълнение би се провалило. Затворете този прозорец на Edge.","sys.profileUnknown":"не можа да се провери","sys.profileFree":"свободен","sys.desktop":"Desktop","sys.desktopSynced":"(архивира се в OneDrive)","sys.desktopLocal":"(не се архивира в OneDrive; огледалото остава локално)","sys.cwd":"Резервна папка за командите (сесията работи в собствената си папка на проекта)","sys.runs":"Папка с изпълненията","sys.data":"Папка с данните","sys.mode":"Режим по подразбиране","sys.settings":"Настройки","sys.settingsHint":"Четат се от {file} до проекта. Има същата форма като {example}; липсващото взема стойността по подразбиране. Редактирайте файла и рестартирайте API-то.","sys.asSaved":"Както е записано","sys.resolved":"Изчислени пътища","sys.signin":"Вписване","sys.signinHint":"Вписването става веднъж, от терминала, за да не работи ботът никога с пароли:","reg.title":"Регистър на задачите","reg.hint":"Всички задачи от всички сесии на едно място: какво е направено, какво се изпълнява в момента и какво предстои. Редът в една сесия е редът на изпълнение.","reg.total":"задачи","reg.done":"готови","reg.open":"предстоят","reg.failedCount":"не са приключили","reg.activeNow":"В момента","reg.upcoming":"Какво следва","reg.upcomingHint":"В реда, в който ще се изпълнят. Сесията върви по опашката си отгоре надолу; първата в една сесия е следващата на ход.","reg.past":"Какво е направено","reg.pastHint":"Най-новите отгоре. Задача, която не е приключила с обяснение, е спряла сесията си и е оставила останалите да чакат.","reg.none":"Още няма задачи.","reg.noUpcoming":"Няма чакащи. Всички задачи са минали.","reg.noPast":"Още нищо не е изпълнявано.","reg.noMatch":"Нищо не отговаря на филтъра.","reg.next":"следваща в тази сесия","reg.queuePos":"{n}-а в опашката","reg.waitingRun":"чака сесията да бъде стартирана","reg.willFollow":"тръгва след {n} задача(и) преди нея","reg.sessionRunning":"сесията работи","reg.iterations":"{n} итерация(и)","reg.took":"отне {d}","reg.filterSession":"Сесия","reg.filterStatus":"Състояние","reg.allSessions":"всички сесии","reg.allStatuses":"всички състояния","reg.search":"Търсене в заглавията и обясненията","reg.searchPlaceholder":"дума от задачата","reg.clear":"Изчисти филтрите","reg.viewFlow":"Поток","reg.viewList":"Списък","reg.viewLabel":"Изглед","reg.openTask":"детайли на задачата","reg.openLog":"log","reg.runningCount":"в момента","reg.attempts":"това е опит {n} — виж {m}-те преди него","reg.attemptsOne":"това е опит {n} — виж този преди него","reg.attemptN":"опит {n}","reg.attemptLog":"log на този опит","reg.blockedWhat":"Задачата приключи, без работата да е свършена. Какво е опитано и какво пречи, пише в причината отдолу.","reg.runGroup":"Пуснати заедно","reg.runGroupHint":"Едно изпълнение е едно натискане на бутона за старт. Всичко отдолу е тръгнало наведнъж, в този ред, през един прозорец на браузъра.","reg.runOf":"Изпълнение на {t} задача(и) в {s} сесия(и)","reg.runAt":"пуснато {when}","reg.runWith":"заедно с още {n} задача(и)","reg.runAlone":"пусната сама","reg.runTitle":"Изпълнение на {t} задача(и) в {s} сесия(и), пуснато {when}","reg.groupBy":"По изпълнение","reg.notInARun":"Извън изпълнение","reg.notInARunHint":"Задачи, които още чакат, и задачи, изпълнени преди системата да започне да записва кои от тях са пуснати заедно.","reg.col.task":"Задача","reg.col.session":"Сесия","reg.col.status":"Състояние","reg.col.started":"Започната","reg.col.took":"Времетраене","reg.col.result":"Резултат","reg.stopped":"спряна: {reason}","reg.refresh":"Обнови","reg.updated":"обновено в {t}","ap.title":"Изглед","ap.hint":"Пази се само в този браузър. Нищо оттук не се изпраща никъде и не се споделя с друга машина.","ap.theme":"Тема","ap.themeWhy":"Топла светла за светла стая, топла тъмна за тъмна.","ap.a11y":"Достъпност","ap.a11yHint":"Всяка от тези настройки работи сама за себе си; не зависят нито от темата, нито от езика.","ap.size":"Размер на текста","ap.sizeNormal":"Нормален","ap.sizeLarge":"Голям","ap.sizeHuge":"Най-голям","ap.sizeWhy":"Уголемява целия интерфейс, не само основния текст.","ap.contrast":"По-висок контраст","ap.contrastWhy":"По-плътни рамки и по-тъмен текст. Жертва част от топлината в името на четимостта.","ap.motion":"По-малко движение","ap.motionWhy":"Без плавни преходи; дневникът на живо спира сам да се превърта, докато тече изпълнение.","ap.links":"Подчертавай всички връзки","ap.linksWhy":"Връзките престават да се разпознават само по цвят.","ap.focus":"Дебел фокусен контур","ap.focusWhy":"Прави невъзможно да изгубите къде е клавиатурата, докато обхождате страницата с Tab.","ap.reset":"Върни настройките по подразбиране","ap.example":"Как изглежда","ap.exampleText":"Задача, приключила с обяснение, друга, която чака одобрение, и една връзка.","ap.exampleLink":"връзка в изречение","nav.import":"План от JSON","nav.defaults":"Настройки","def.title":"С какво тръгва всяка нова сесия","def.intro":"Тук се избират веднъж три неща, вместо във всяка сесия: папките, по които се работи, моделът, който върши работата, и моделът, който я проверява. Сесиите си пазят собствени копия, така че всяка от тях може да бъде променена после, без това да пипа зададеното тук.","def.autoSave":"Всичко на тази страница се запазва само, докато го променяте. Няма какво да натискате.","def.savedAutomatically":"запазва се, докато пишете","def.saveAnyway":"Запази","def.saveAnywayWhy":"Вече е запазено. Този бутон съществува заради удоволствието да натиснеш бутон.","proj.nameField":"Име на проекта","proj.namePlaceholder":"името на самата папка","proj.nameWhy":"Как се казва този проект навсякъде другаде: папката му на Desktop-а, името пред всеки копиран файл и списъкът, който получава Kerrigan. Празно означава името на самата папка.","proj.nameSaved":"Името е запазено.","def.reviewTitle":"Модел за рецензията","def.reviewIntro":"Моделът, с който тръгва независимата рецензия на новата сесия. Модел, различен от този, който върши работата, е най-евтиният начин второто мнение наистина да е второ: новият разговор маха привързаността към работата, но не и слепите петна на модела.","def.reviewField":"Модел за рецензията","def.reviewNone":"Собственият модел на сесията","def.reviewSaved":"Новите сесии ще бъдат проверявани от {name}.","def.reviewCleared":"Изчистено. Новите сесии се проверяват от собствения си модел.","def.reviewSame":"Това е същият модел, който върши работата. Друг би хванал повече.","def.reviewAffectsNew":"Новата сесия тръгва с този модел за рецензията, записан върху нея при създаването ѝ. План, който не назовава такъв за сесия, също го получава.","def.reviewAffectsExisting":"Вече съществуващите сесии си пазят своя. Панелът им за рецензия предлага този с бутон.","def.reviewAffectsBatch":"Изпълнението на няколко сесии тръгва с този модел за рецензията избран и го казва, преди да го запише върху тях.","def.reviewDefaultIs":"Модел за рецензията по подразбиране: {name}","def.reviewNoneShort":"Няма зададен модел за рецензията по подразбиране.","def.modelTitle":"Модел за новите сесии","def.modelIntro":"Моделът, с който тръгва една сесия, с точното име от менюто на самия чат. Списъкът е този, който е прочетен от чата последно; той принадлежи на Microsoft и е различен за всеки клиент, затова никога не е списък, записан в този проект.","def.modelField":"Модел","def.modelNone":"Остави чата на каквото е настроен","def.modelSaved":"Новите сесии ще тръгват на {name}.","def.modelCleared":"Изчистено. Новите сесии оставят чата на каквото е настроен.","def.modelAffectsNew":"Новата сесия тръгва на този модел, записан върху нея в момента на създаването ѝ.","def.modelAffectsExisting":"Вече съществуващите сесии си пазят модела. Тяхното меню ви предлага този с бутон.","def.modelAffectsBatch":"Изпълнението на няколко сесии тръгва с този модел избран и го казва, преди да го запише върху тях.","def.modelDefaultIs":"Модел по подразбиране: {name}","def.modelNoneShort":"Няма зададен модел по подразбиране.","def.modelUseIt":"ползвай го тук","proj.title":"Проектът, по който се работи","proj.intro":"Задайте папката веднъж тук и всяка нова сесия тръгва насочена към нея, вместо да я въвеждате наново всеки път. Сесиите пазят собствените си папки, така че всяка от тях може да бъде насочена другаде после.","proj.field":"Папка на проекта","proj.save":"Запази","proj.saved":"Новите сесии ще тръгват в {dir}.","proj.clear":"Изчисти","proj.cleared":"Изчистено. Новите сесии тръгват без избрана папка.","proj.none":"Няма зададена папка на проекта, така че всяка сесия тръгва с празни полета.","proj.isRepo":"Тази папка е git хранилище, така че сесиите, насочени към нея, могат да правят клонове и комити.","proj.notRepo":"Тази папка не е git хранилище","proj.notRepoWhy":"Пак може да е проектът: файловете са там и задачите могат да работят в нея. Това, което не може, е да носи контрол на версиите — превключвателят за него остава изключен, докато папката не стане хранилище.","proj.affects":"Какво променя това и какво не","proj.affectsNew":"Новата сесия тръгва с тази папка и в полето за файлове на проекта, и в полето за контрол на версиите. Нито едното не се включва само защото е попълнено.","proj.affectsExisting":"Вече съществуващите сесии не се пипат. Техните полета ви предлагат тази папка с бутон, а дали да я вземете е ваше решение.","proj.affectsPlan":"Заданието за чат модела получава тази папка, така че моделът нито трябва да пита за нея, нито да си я измисля.","proj.affectsNever":"Нищо тук никога не променя това, което една работеща сесия прави в момента.","proj.toSessions":"Към сесиите","proj.toImport":"Към внасянето на план","proj.defaultIs":"Проект по подразбиране: {dir}","proj.noneShort":"Няма зададен проект по подразбиране.","proj.useIt":"ползвай го тук","proj.setIt":"задайте такъв","proj.change":"смени","proj.others":"Други проекти","proj.isDefault":"по подразбиране","proj.isDefaultWhy":"Новите сесии тръгват в този, а заданието за плана го предлага пръв.","proj.entryName":"Име","proj.entryDir":"Папка","proj.addTitle":"Добави още един проект","proj.listIntro":"Всички проекти, в които тази машина работи. Първият е по подразбиране: новите сесии тръгват там. Останалите са именувани, за да може план да прати работа към тях. Всички се описват по един и същи начин и всички се запазват, докато пишете.","proj.othersIntro":"Останалите папки, по които работите — front end, back end, тестовете — всяка с кратко име. Новите сесии пак тръгват от папката по подразбиране горе. Тези се предлагат с бутон навсякъде, където се избира папка, а заданието за план ги изброява с пътищата им, така че план през няколко хранилища се пише с папките, които съществуват, вместо да пита за всяка.","proj.otherName":"Име","proj.otherDir":"Папка","proj.otherAdd":"Добави","proj.otherRemove":"Махни","proj.othersNone":"Още няма други проекти.","proj.othersSaved":"Запазено: {n} други проекта.","proj.otherRepo":"git хранилище","proj.otherNotRepo":"не е git хранилище","proj.otherUse":"ползвай {name}","plan.title":"План, написан от чат модел","plan.intro":"Опишете работата на кой да е чат модел, оставете го да ви зададе въпросите и поставете тук това, което ви е написал. Тази страница създава сесиите и задачите; не стартира нищо.","plan.step1":"1. Занесете това в чата","plan.step1Hint":"Копирайте целия текст в нов разговор с модел по ваш избор. Той обяснява какво представлява този runner, кара модела да ви разпита за работата и фиксира точния формат, в който трябва да отговори.","plan.persona":"Kerrigan, персоната: две нива","plan.personaWhy":"Това, което копирате, е един текст от три части. Софтуерната част е на този проект и не се променя: какво е ботът, форматът на плана, как се четат файловете от регистъра, когато задача се провали, и как се проверява готовото пускане спрямо заданието. Другите две са ваши и са разделени, защото се менят с различна скорост: организацията и проектите се пишат веднъж и се четат с месеци, а описанието на работата се сменя, когато се смени работата. Докато някое от двете е празно, заданието казва на Kerrigan първо да ви разпита и да върне и двете като JSON, с указание къде да ги поставите; веднъж запазени, те пътуват с всяко копие и въпросите спират.","plan.softwarePart":"Софтуерно ниво (фиксирано)","plan.orgPart":"Как се работи тук: организацията и проектите","plan.orgHint":"Каквото би трябвало да знае всеки, който върши задача тук: откъде идват ticket-ите, къде да се търси, правилата и шаблоните, а за всеки проект — пътят му, какво прави, какво му трябва, преди да се строи, как се строи и тества, и какво се чупи там. Не как се казват организацията или проектите — името не помага на никоя задача. Пише се веднъж и се чете с месеци. Тук поставете първия от документите, които Kerrigan връща.","plan.personaPart":"Как се изпълняват задачите: персоната на агента","plan.personaHint":"Как агентът, който върши работата, подхожда към нея: за какво отговаря и за какво не, подходът му, фазите, през които минава, и какво предава накрая. Няма име — това е начин на работа, не герой — затова може да го смените, когато друга работа иска друг подход. Вписва се във всяка задача при импорт на план, така че сесията пази подхода, с който е създадена. Поставете тук своя собствена или втория от документите, които Kerrigan връща.","plan.workPart":"Тази работа","plan.workHint":"За какво е тази група задачи: ticket-ът, целта, кои проекти засяга, какво вече е решено или пробвано, какво не бива да се променя междувременно. Сменя се, когато се смени работата. Тук поставете последния от документите, които Kerrigan връща.","plan.ctxWritten":"написано","plan.ctxEmpty":"празно — Kerrigan ще пита","plan.ctxSaved":"запазено; следващото копиране на заданието го носи","plan.ctxClear":"Изпразни","plan.ctxCleared":"изпразнено; Kerrigan пак ще пита за него","plan.ctxClearConfirm":"Да изпразня ли този текст? Kerrigan ще пита за него отново при следващото копиране на заданието.","plan.copyBrief":"Копирай заданието","plan.copied":"копирано","plan.copyFailed":"Браузърът не позволи копиране от страницата. Маркирайте текста и го копирайте ръчно.","plan.showBrief":"Покажи текста","plan.hideBrief":"Скрий текста","plan.briefLang":"Заданието е на езика, на който е този интерфейс.","plan.briefAsks":"Заданието пита вместо вас","plan.briefAsksWhy":"Тук не се настройва нищо. Заданието кара модела да ви попита дали runner-ът да прави контрол на версиите и в коя папка се работи, а отговорите влизат в самия JSON, за всяка сесия. План, който ги пропусне, се отказва при внасяне, с готов текст, който да върнете в чата.","plan.step2":"2. Върнете отговора тук","plan.step2Hint":"Поставете го, пуснете файла върху полето или изберете файл. Текст и ограждащи блокове около JSON-а не пречат; премахват се.","plan.placeholder":"Поставете JSON-а, който чат моделът е написал…","plan.drop":"Пуснете .json файл тук","plan.dropActive":"Пуснете, за да се прочете файлът","plan.browse":"Изберете файл…","plan.clear":"Изчисти","plan.check":"Провери","plan.checking":"проверява се…","plan.import":"Създай сесиите и задачите","plan.importing":"създава се…","plan.fileError":"Файлът не можа да бъде прочетен: {reason}","plan.fileTooBig":"Този файл е {size} — многократно повече от какъвто и да е план. Нищо не беше прочетено.","plan.valid":"Това е план, който системата разбира: {sessions} сесия(и), {tasks} задача(и).","plan.invalid":"Това още не е план, който системата може да прочете.","plan.issues":"Какво не е наред","plan.issuesHint":"Копирайте това обратно в същия разговор и поискайте целия поправен JSON. Пътищата казват къде в документа е всеки проблем.","plan.copyIssues":"Копирай грешките","plan.warnings":"Добре е да знаете","plan.duplicates":"Това вече го има","plan.duplicatesHint":"Тези сесии вече съществуват, с точно тези задачи. Импортът прави второ копие — позволено е, но обикновено значи, че е поставен грешният текст. Проверете дали това е поправеният план, а не старият.","plan.duplicateRow":"{name} — {tasks} еднакви задачи, внесени {when}","plan.duplicateConfirm":"Тези сесии вече съществуват с точно тези задачи:\n\n{names}\n\nИмпортът ще направи второ тяхно копие. Да продължим ли?","plan.cleared":"Полето беше изчистено, за да не се внесе същият план втори път по невнимание.","plan.col.planFail":"При провалена сесия","plan.runThese":"Пусни тези сесии","plan.preview":"Какво ще бъде създадено","plan.notes":"Бележки от модела","plan.col.session":"Сесия","plan.col.tasks":"Задачи","plan.col.chain":"При провалена задача","plan.col.repo":"Хранилище","plan.noRepo":"няма","plan.step3":"3. Прегледайте и стартирайте сами","plan.step3Hint":"Нищо не тръгва само. Прочетете какво е създадено, променете каквото искате да промените, и го пуснете от списъка със сесии.","plan.imported":"Създадени са {sessions} сесия(и) с {tasks} задача(и). Нищо не е стартирано.","plan.toSessions":"Към списъка със сесии","batch.title":"Пускане на няколко сесии","batch.hint":"Отбележете кои сесии да се изпълнят и те тръгват една след друга, в реда, в който са изброени тук. Два разговора не могат да вървят едновременно: профилът на браузъра е на един по едно и също време.","batch.selected":"{n} избрани, {tasks} задача(и) в опашката","batch.notRunnable":"{n} от тях нямат нищо в опашката и не влизат в изпълнението.","batch.pickFirst":"Изберете кои сесии да се изпълнят","batch.pickFirstWhy":"Отметнете ги в списъка по-долу и двата бутона се отключват. Изпълняват се в реда, показан тук, една след друга.","batch.nothingRunnable":"Нито една от отметнатите сесии няма нещо в опашката","batch.nothingRunnableWhy":"Изпълняват се само задачи, които още чакат в опашка. Добавете задача в някоя от тях или отметнете сесия, която има.","batch.oneRunning":"Една сесия вече върви сама","batch.oneRunningWhy":"Два разговора не могат да вървят едновременно, затова изпълнението на няколко трябва да изчака. Оставете я да приключи или я спрете от нейната страница.","batch.selectQueued":"Избери всички сесии с нещо в опашката","batch.selectNone":"Изчисти избора","batch.onFailure":"Ако сесия се провали","batch.model":"Модел за това изпълнение","batch.waiting":"{n} стъпка(и) чакат вас","approval.waitingHere":"Стъпка чака вашето решение","approval.waitingHereWhy":"Изпълнение, стартирано от тази страница, задава въпросите си тук, за да не изглежда забило, докато страница на сесия, която никой не е отворил, чака отговор.","batch.reviewModel":"Модел, който проверява работата","batch.reviewModelKeep":"Всяка сесия си остава със своя","batch.reviewModelWhy":"Независимата рецензия върви в собствен разговор след всяка задача. Да я сложите на модел, различен от този, който върши работата, е най-евтиният начин второто мнение да е наистина второ: свежият разговор маха привързаността към работата, но не и слепите петна на модела, който я е произвел.","batch.reviewSame":"Това е същият модел, който върши работата. Друг би хванал повече.","batch.reviewOffIn":"Рецензията е изключена в {n} от избраните сесии; моделът тук не я включва.","batch.modelKeep":"Всяка сесия със своя","batch.modelWhy":"Ако изберете един тук, той се записва върху всяка избрана сесия преди старта, така че после това, което сесията казва, че ползва, и това, което е ползвала, остават едно и също.","batch.modelOverrides":"{n} от избраните сесии са на друг модел и ще бъдат сменени на този.","batch.modelNone":"Още не са прочетени модели от чата.","batch.modelRunning":"Върви на {name}.","batch.vcsProblem":"Контролът на версиите не може да работи в тези сесии","batch.vcsProblemWhy":"Те пак ще се изпълнят, но няма да се направи клон и нищо няма да се комитне, тоест работата остава разхвърляна в работното дърво. Най-честата причина е предишно изпълнение, прекъснато преди runner-ът да успее да комитне.","batch.vcsProblemRow":"{name}: {problem}","batch.hiddenWhileRunning":"Изборът на сесии, на модел и на поведение при провал се скриват, докато тече изпълнение, защото нито едно от тях не може да промени вече започналото. Връщат се, щом то приключи.","batch.fromPlan":"Избрани от плана, който току-що внесохте, в неговия ред.","batch.chain":"Спри и остави останалите както са","batch.chainWhy":"Сесиите са една работа, подредена по ред. По-късната обикновено разчита, че по-ранните са минали, така че пускането ѝ след провал не проверява нищо.","batch.independent":"Продължи със следващата сесия","batch.independentWhy":"Сесиите са отделни парчета работа, които просто са стартирани заедно. Провалът на едната не казва нищо за следващата.","batch.run":"Пусни {n} сесия(и)","batch.runWhy":"Минава през избраните сесии една след друга, сама, без да спира да пита. Това е обичайният начин.","batch.runStep":"Стъпка по стъпка","batch.runStepWhy":"Спира преди всяка команда във всяка сесия и чака вас. За проследяване на проблем или когато планът е нов.","batch.unattendedConfirm":"Това се изпълнява само, през {n} сесия(и): командите, които Copilot напише, ще се пускат, без да ви питат, докато всички не приключат. Списъкът със забранени команди продължава да важи. Да ги пуснем ли?","batch.stop":"Спри след текущата стъпка","batch.pause":"Пауза след тази задача","batch.pauseWhy":"Оставя задачата, която върви, да приключи както трябва — проверките ѝ, рецензията ѝ, комита ѝ — и чак тогава спира. Всичко останало в опашката си остава там, а „Продължи“ го подхваща оттам, докъдето е стигнало.","batch.pausing":"пауза: задачата, която върви, първо ще приключи, а останалата опашка се запазва","batch.resume":"Махни паузата","batch.resumeWhy":"Продължава с опашката, все едно паузата не е натискана. Работи само докато паузираната задача още върви.","batch.stopWhy":"Прекъсва след текущата стъпка. Задачата, която прекъсва, завършва „прекратена“, наполовина свършена. Ако само искате да помислите, ползвайте паузата.","batch.notStarted":"не стартира: {reason}","batch.notStartedTitle":"Пускането не тръгна","batch.notStartedIsolation":"Настройки → „Къде върви ботът“: изберете къде върви ботът или приемете пускане без надзор без изолация","batch.nothingQueued":"няма нищо в опашката","batch.progress":"Изпълнява се {name} — {done} от {total} приключили.","batch.finished":"Приключи: {done} успешни, {failed} провалени, {skipped} неизпълнени.","batch.stopping":"спира след текущата стъпка; сесиите след тази остават както са","batch.col.session":"Сесия","batch.debug":"Изтегли всичко като JSON","batch.debugWhy":"Един файл с това какво се е изпълнило и какво е станало в тези сесии: всяка стъпка и кодът ѝ на изход, всяко резюме, всяка проверка и какво е комитнала всяка задача. За подаване на някого — или нещо — което трябва да разбере защо изпълнението е минало така.","batch.debugSelected":"за {n}-те избрани сесии","batch.debugLast":"за сесиите от последното изпълнение","batch.col.state":"Състояние","batch.col.ran":"Задачи","batch.col.why":"Защо","batch.state.waiting":"чака","batch.state.running":"изпълнява се","batch.state.done":"готова","batch.state.failed":"провалена","batch.state.stopped":"спряна","batch.state.skipped":"неизпълнена","batch.ranOf":"{ran} изпълнени, {failed} провалени"}},r="cop.locale",i=(0,n.createContext)({locale:"en",setLocale:()=>void 0});function h(e){let{children:t}=e,[s,a]=(0,n.useState)("en");return(0,n.useEffect)(()=>{let e="en";try{let t=window.localStorage.getItem(r);"en"===t||"bg"===t?e=t:navigator.language.toLowerCase().startsWith("bg")&&(e="bg")}catch(e){}a(e),document.documentElement.lang=e},[]),(0,o.jsx)(i.Provider,{value:{locale:s,setLocale:e=>{a(e);try{window.localStorage.setItem(r,e)}catch(e){}document.documentElement.lang=e}},children:t})}function d(){let{locale:e}=(0,n.useContext)(i);return{t:function(t){var s,o;let n=arguments.length>1&&void 0!==arguments[1]?arguments[1]:{},r=null!=(o=null!=(s=a[e][t])?s:a.en[t])?o:t;for(let[e,t]of Object.entries(n))r=r.split("{".concat(e,"}")).join(String(t));return r},locale:e}}function l(){let{locale:e,setLocale:t}=(0,n.useContext)(i),{t:s}=d();return(0,o.jsxs)("select",{"aria-label":s("lang.label"),value:e,onChange:e=>t(e.target.value),style:{width:"auto"},children:[(0,o.jsx)("option",{value:"en",children:"English"}),(0,o.jsx)("option",{value:"bg",children:"Български"})]})}function c(){let{locale:e}=(0,n.useContext)(i);return t=>t?new Date(t).toLocaleString("bg"===e?"bg-BG":void 0,{hour12:!1}):""}}}]);
@@ -1 +0,0 @@
1
- "use strict";(self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[955],{1910:(e,t,s)=>{s.d(t,{u:()=>l});var n=s(3365),a=s(1521),r=s(867);function l(e){let{label:t,save:s}=e,{t:l}=(0,r.kj)(),[i,o]=(0,a.useState)(!1),[c,d]=(0,a.useState)(""),[u,h]=(0,a.useState)(!1),m=async()=>{o(!0),d("");try{var e;let t=await s();h(!1),d(t.revealed?l("save.done",{path:t.path}):l("save.savedOnly",{path:t.path,note:null!=(e=t.note)?e:""}))}catch(e){h(!0),d(l("save.failed",{problem:e.message}))}finally{o(!1)}};return(0,n.jsxs)(n.Fragment,{children:[(0,n.jsx)("button",{type:"button",className:"linkish",disabled:i,title:l("save.why"),onClick:()=>void m(),children:i?l("save.saving"):t}),c&&(0,n.jsx)("span",{className:u?"err small":"muted small",children:c})]})}},3041:(e,t,s)=>{s.d(t,{e:()=>i});var n=s(1521),a=s(5549),r=s(1035),l=s(867);function i(e){let{t}=(0,l.kj)(),[s,i]=(0,n.useState)(""),[o,c]=(0,n.useState)("");return{busy:s,message:o,clearMessage:()=>c(""),restore:(0,n.useCallback)(async s=>{i("restore"),c("");try{var n,l,o,d,u,h,m,p,f,x,j,y,N,g;let i=await a.FH.restorePreview(s.sessionId,s.taskId);if(!i.ok)return void c(t("restore.cannot",{problem:null!=(o=i.problem)?o:""}));let k={repo:i.repoDir,title:s.title,branch:null!=(d=i.branchName)?d:"",commit:(null!=(u=i.baseCommit)?u:"").slice(0,8)},v=i.leftBehind.length>0?t("restore.confirmLosing",{...k,n:i.leftBehind.length,kept:null!=(h=i.keptOn)?h:"",list:i.leftBehind.slice(0,10).join("\n")}):t("restore.confirm",k);if(!await (0,r.Z)(v))return;let b=await a.FH.restore(s.sessionId,s.taskId);if(!b.ok)return void c(t("restore.failed",{problem:null!=(m=b.problem)?m:""}));c((null!=(p=null==(n=b.leftBehind)?void 0:n.length)?p:0)>0?t("restore.done",{branch:null!=(f=b.branch)?f:"",commit:(null!=(x=b.commit)?x:"").slice(0,8),n:null!=(j=null==(l=b.leftBehind)?void 0:l.length)?j:0,kept:null!=(y=b.keptOn)?y:""}):t("restore.doneNothing",{branch:null!=(N=b.branch)?N:"",commit:(null!=(g=b.commit)?g:"").slice(0,8)})),e()}catch(e){c(e.message)}finally{i("")}},[t,e]),restartFrom:(0,n.useCallback)(async s=>{i("restart"),c("");try{var n,l;let i=await a.FH.restartPlan(s.sessionId,s.taskId);if(!i.ok)return void c(t("restart.cannot",{problem:null!=(n=i.problem)?n:""}));let o=i.restores.filter(e=>!e.ok);if(o.length>0)return void c(t("restart.cannot",{problem:o.map(e=>{var t;return"".concat(e.repoDir,": ").concat(null!=(t=e.problem)?t:"")}).join(" | ")}));let d=i.restores.map(e=>{var s,n,a;return t("restart.repoLine",{repo:e.repoDir,commit:(null!=(s=e.baseCommit)?s:"").slice(0,8),branch:null!=(n=e.branchName)?n:"",n:e.leftBehind.length,kept:null!=(a=e.keptOn)?a:""})}).join("\n"),u=i.tasks.map(e=>" ".concat(e.sessionName," / ").concat(e.title).concat(e.alreadyQueued?t("restart.alreadyQueued"):"")).join("\n"),h=t("restart.confirm",{title:i.from.title,tasks:i.tasks.length,sessions:i.sessions.length,list:u,repos:d||t("restart.noRepo"),mode:t("unattended"===i.mode?"run.unattended":"run.confirm")});if(!await (0,r.Z)(h))return;let m=await a.FH.restartFrom(s.sessionId,s.taskId);if(!m.started){c(t("restart.failed",{problem:null!=(l=m.reason)?l:""})),e();return}c(t("restart.started",{requeued:m.requeued,repos:m.restored.length})),e()}catch(e){c(e.message)}finally{i("")}},[t,e])}}},3374:(e,t,s)=>{s.d(t,{c:()=>a});var n=s(1521);function a(e){let t=arguments.length>1&&void 0!==arguments[1]?arguments[1]:1e3,[s,a]=(0,n.useState)(()=>Date.now());return(0,n.useEffect)(()=>{if(!e)return;a(Date.now());let s=window.setInterval(()=>a(Date.now()),t);return()=>window.clearInterval(s)},[e,t]),s}},3523:(e,t,s)=>{function n(e,t){let s=arguments.length>2&&void 0!==arguments[2]?arguments[2]:Date.now();if(!e)return;let n=Date.parse(e);if(Number.isNaN(n))return;let a=t?Date.parse(t):s;return Number.isNaN(a)?void 0:Math.max(0,a-n)}function a(e){return!!e.startedAt&&!e.finishedAt&&"queued"!==e.status}function r(e,t){let s=arguments.length>2&&void 0!==arguments[2]?arguments[2]:Date.now(),n=t.some(e=>a(e)),r=t.map(e=>e.finishedAt?Date.parse(e.finishedAt):NaN).filter(e=>!Number.isNaN(e)),l=Date.parse(e.startedAt),i=n||0===r.length?s:Math.max(...r);return{ms:Number.isNaN(l)?0:Math.max(0,i-l),live:n,tasks:t.length}}function l(e){var t,s;let n=new Map;for(let s of e){if(!s.runGroup)continue;let e=null!=(t=n.get(s.runGroup.id))?t:{run:s.runGroup,tasks:[]};e.tasks.push(s),n.set(s.runGroup.id,e)}return null!=(s=[...n.values()].sort((e,t)=>Date.parse(t.run.startedAt)-Date.parse(e.run.startedAt))[0])?s:null}s.d(t,{DG:()=>a,d5:()=>n,eZ:()=>r,hH:()=>l})},5132:(e,t,s)=>{s.d(t,{s:()=>i});var n=s(3365),a=s(1521);function r(e,t){let s,a=[],r=/(`[^`\n]+`)|(\*\*[^*\n]+\*\*)|(\*[^*\n]+\*)/g,l=0,i=0;for(;null!==(s=r.exec(e));){s.index>l&&a.push(e.slice(l,s.index));let r=s[0],o="".concat(t,"-i").concat(i+=1);r.startsWith("`")?a.push((0,n.jsx)("code",{children:r.slice(1,-1)},o)):r.startsWith("**")?a.push((0,n.jsx)("strong",{children:r.slice(2,-2)},o)):a.push((0,n.jsx)("em",{children:r.slice(1,-1)},o)),l=s.index+r.length}return l<e.length&&a.push(e.slice(l)),a}function l(e){let t=/^\s*[-*•]\s+(.*)$/.exec(e);if(t)return t[1];let s=/^\s*\d+[.)]\s+(.*)$/.exec(e);return s?s[1]:null}function i(e){let{text:t,className:s}=e,i=[],o=t.replace(/\r\n/g,"\n").split("\n"),c=0,d=0;for(;c<o.length;){let e=o[c];if(e.trim().startsWith("```")){let e=[];for(c+=1;c<o.length&&!o[c].trim().startsWith("```");)e.push(o[c++]);c+=1,e.length>0&&i.push((0,n.jsx)("pre",{children:e.join("\n")},"b".concat(d+=1)));continue}if(null!==l(e)){let e=[];for(;c<o.length&&null!==l(o[c]);)e.push(l(o[c++]));i.push((0,n.jsx)("ul",{children:e.map((e,t)=>(0,n.jsx)("li",{children:r(e,"b".concat(d,"-").concat(t))},t))},"b".concat(d+=1)));continue}if(""===e.trim()){c+=1;continue}let t=[];for(;c<o.length&&""!==o[c].trim()&&null===l(o[c])&&!o[c].trim().startsWith("```");)t.push(o[c++]);let s=d+=1;i.push((0,n.jsx)("p",{children:t.map((e,t)=>(0,n.jsxs)(a.Fragment,{children:[t>0&&(0,n.jsx)("br",{}),r(e,"b".concat(s,"-").concat(t))]},t))},"b".concat(s)))}return(0,n.jsx)("div",{className:"rich ".concat(null!=s?s:""),children:i})}},7619:(e,t,s)=>{s.d(t,{P:()=>o});var n=s(3365),a=s(1521),r=s(5549),l=s(867),i=s(5132);function o(e){let{sessionId:t,taskId:s,runId:o,live:c}=e,{t:d}=(0,l.kj)(),[u,h]=(0,a.useState)(null),[m,p]=(0,a.useState)(""),[f,x]=(0,a.useState)(!0),[j,y]=(0,a.useState)(!0),[N,g]=(0,a.useState)(new Set);if((0,a.useEffect)(()=>{let e,n=!0,a=async()=>{try{let l=await r.FH.taskStory(t,s,o);if(!n)return;h(l),p(""),l.live&&(e=setTimeout(a,4e3))}catch(t){if(!n)return;p(t.message),c&&(e=setTimeout(a,4e3))}};return a(),()=>{n=!1,e&&clearTimeout(e)}},[t,s,o,c]),m&&!u)return(0,n.jsx)("div",{className:"err small",children:m});if(!u)return(0,n.jsx)("div",{className:"muted small",children:d("story.loading")});let k=e=>g(t=>{let s=new Set(t);return s.has(e)?s.delete(e):s.add(e),s}),v=(e,t)=>{if(!("review"===e.kind?f||j:"step"===e.kind?j:f))return null;if("review"===e.kind)return(0,n.jsxs)("li",{className:"story-review",children:[(0,n.jsx)("div",{className:"story-head",children:(0,n.jsx)("span",{className:"chip",children:d("story.review",{n:e.round})})}),(0,n.jsx)("ol",{className:"story",children:e.entries.map((e,s)=>v(e,"".concat(t,"-").concat(s)))})]},t);if("step"===e.kind){let s=N.has(t);return(0,n.jsxs)("li",{className:"story-step".concat(e.failed?" failed":""),children:[(0,n.jsxs)("div",{className:"story-head",children:[(0,n.jsx)("span",{className:"chip",children:d("story.step",{it:e.iteration,id:e.id})}),e.outcome&&(0,n.jsxs)("span",{className:"badge ".concat(e.failed?"failed":"done"),children:[e.outcome,void 0!==e.exitCode?" \xb7 exit ".concat(e.exitCode):"",void 0!==e.durationMs?" \xb7 ".concat((0,r.c5)(e.durationMs)):""]}),!e.outcome&&(0,n.jsx)("span",{className:"badge running",children:d("story.running")}),e.failed&&(0,n.jsx)("span",{className:"badge failed",children:d("story.failedHere")})]}),(0,n.jsx)("pre",{className:"story-cmd",children:e.command}),e.output&&(0,n.jsxs)(n.Fragment,{children:[(0,n.jsx)("button",{type:"button",className:"linkish small",onClick:()=>k(t),children:s?d("story.hideOutput"):d("story.showOutput",{n:e.output.length})}),s&&(0,n.jsx)("pre",{className:"story-out",children:e.output})]})]},t)}let s=N.has(t),a="sent"===e.kind?d("story.bot"):d("story.chat"),l="reply"===e.kind&&("blocked"===e.status||"failed"===e.status);return(0,n.jsxs)("li",{className:"story-msg ".concat(e.kind).concat(l?" failed":""),children:[(0,n.jsxs)("div",{className:"story-head",children:[(0,n.jsx)("strong",{children:a}),(0,n.jsx)("span",{className:"muted small",children:e.label}),"reply"===e.kind&&e.status&&(0,n.jsx)("span",{className:"badge ".concat(l?"failed":"done"===e.status?"done":""),children:e.status})]}),"reply"===e.kind&&e.notes&&(0,n.jsx)("p",{className:"story-notes",children:e.notes}),(0,n.jsx)("button",{type:"button",className:"linkish small",onClick:()=>k(t),children:s?d("story.hideText"):d("story.showText",{n:e.text.length})}),s&&(0,n.jsx)("pre",{className:"story-out",children:e.text})]},t)},b=u.close,w=b&&"done"!==b.status;return(0,n.jsxs)("div",{className:"story-box",children:[(0,n.jsxs)("div",{className:"row small",style:{marginBottom:6},children:[(0,n.jsxs)("label",{className:"option-inline",children:[(0,n.jsx)("input",{type:"checkbox",checked:f,onChange:e=>x(e.target.checked)})," ",d("story.showChat")]}),(0,n.jsxs)("label",{className:"option-inline",children:[(0,n.jsx)("input",{type:"checkbox",checked:j,onChange:e=>y(e.target.checked)})," ",d("story.showCommands")]}),u.live&&(0,n.jsxs)("span",{className:"live",children:[(0,n.jsx)("span",{className:"dot","aria-hidden":"true"})," ",d("story.live")]}),m&&(0,n.jsx)("span",{className:"err",children:m})]}),(0,n.jsxs)("div",{className:"story-fixed",children:[(0,n.jsx)("strong",{children:d("story.prompt")}),(0,n.jsx)("pre",{className:"story-out always",children:u.prompt})]}),(0,n.jsx)("ol",{className:"story",children:u.entries.map((e,t)=>v(e,"e".concat(t)))}),b?(0,n.jsxs)("div",{className:"story-fixed close".concat(w?" failed":""),children:[(0,n.jsx)("strong",{children:w?d("story.endedBadly",{status:b.status}):d("story.ended")}),b.reason&&(0,n.jsx)("p",{className:"err small",children:b.reason}),b.summary&&(0,n.jsx)(i.s,{text:b.summary,className:"what"}),b.checks&&b.checks.length>0&&(0,n.jsx)("ul",{className:"small",style:{margin:"6px 0 0",paddingLeft:18},children:b.checks.map((e,t)=>(0,n.jsxs)("li",{className:e.passed?"":"err",children:[e.passed?"✓":"✗"," ",e.name,!e.passed&&e.detail?" — ".concat(e.detail):""]},t))})]}):(0,n.jsx)("div",{className:"story-fixed muted small",children:d("story.notEnded")})]})}}}]);
@@ -1 +0,0 @@
1
- (self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[189],{1896:(e,l,t)=>{Promise.resolve().then(t.bind(t,3197))},2244:(e,l,t)=>{"use strict";t.d(l,{k:()=>c});var r=t(3365),s=t(1521),a=t(5549),n=t(867);function i(e){return e.trim().replace(/\\/g,"/").replace(/^\.\//,"").replace(/\/+$/,"")}function o(e,l){return"."===l||""===l||e===l||e.startsWith("".concat(l,"/"))}function d(e,l,t){return t.includes(e)?"out":t.some(l=>l!==e&&o(e,l))?"out-inherited":l.includes(e)?"in":l.some(l=>l!==e&&o(e,l))?"inherited":"none"}function c(e){let{rootDir:l,respectGitignore:t,includeEnvFiles:c,include:u,exclude:m,onChange:h}=e,{t:p}=(0,n.kj)(),[j,x]=(0,s.useState)(null),[v,f]=(0,s.useState)(""),[g,y]=(0,s.useState)(new Set),[N,b]=(0,s.useState)(""),w=async()=>{if(l.trim()){f("");try{let e=await a.FH.dirs(l,t);x(e),b("".concat(l,"|").concat(t)),y(new Set(e.filter(e=>!e.includes("/"))))}catch(e){f(e.message)}}};(0,s.useEffect)(()=>{x(null),b("")},[l,t]);let k=(0,s.useMemo)(()=>(function(e){let l=[],t=new Map;for(let s of[...e].sort()){var r;let e={path:s,name:null!=(r=s.split("/").pop())?r:s,children:[]};t.set(s,e);let a=s.includes("/")?t.get(s.slice(0,s.lastIndexOf("/"))):void 0;(a?a.children:l).push(e)}return l})(null!=j?j:[]),[j]),S=u.map(i).filter(Boolean),D=m.map(i).filter(Boolean),C=e=>(0,r.jsx)("ul",{className:"dir-tree",children:e.map(e=>{let l=d(e.path,S,D),t=g.has(e.path),s=function(e,l,t){let r=l=>l.filter(l=>l!==e&&o(l,e)).length;return{included:r(l),excluded:r(t)}}(e.path,S,D),a=!t&&e.children.length>0&&(s.included>0||s.excluded>0);return(0,r.jsxs)("li",{className:"dir ".concat(l),children:[(0,r.jsxs)("div",{className:"dir-row",children:[e.children.length>0?(0,r.jsx)("button",{type:"button",className:"dir-flip",onClick:()=>{let l;return l=e.path,y(e=>{let t=new Set(e);return t.has(l)?t.delete(l):t.add(l),t})},"aria-label":t?p("tree.fold"):p("tree.unfold"),"aria-expanded":t,children:t?"▾":"▸"}):(0,r.jsx)("span",{className:"dir-flip","aria-hidden":"true"}),(0,r.jsxs)("button",{type:"button",className:"dir-name",onClick:()=>(e=>{if("in"===d(e,S,D))return void h(S.filter(l=>l!==e),D);h([...S.filter(l=>!o(l,e)),e],D.filter(l=>!o(l,e)))})(e.path),title:"in"===l?p("tree.stateIn"):"inherited"===l?p("tree.stateInherited"):"out"===l?p("tree.stateOut"):"out-inherited"===l?p("tree.stateOutInherited"):p("tree.stateNone"),"aria-pressed":"in"===l||"inherited"===l,children:[(0,r.jsx)("span",{className:"dir-mark","aria-hidden":"true",children:"in"===l?"✓":"inherited"===l?"\xb7":"out"===l||"out-inherited"===l?"\xd7":""}),e.name]}),(0,r.jsx)("button",{type:"button",className:"dir-out".concat("out"===l?" on":""),onClick:()=>(e=>{if(D.includes(e))return void h(S,D.filter(l=>l!==e));h(S.filter(l=>l!==e&&!o(l,e)),[...D.filter(l=>!o(l,e)),e])})(e.path),title:"out"===l?p("tree.unexclude"):p("tree.exclude"),children:"−"}),a&&(0,r.jsx)("span",{className:"chip inside".concat(s.excluded>0?" out":""),title:p("tree.insideWhy"),children:s.excluded>0&&s.included>0?p("tree.insideBoth",{i:s.included,e:s.excluded}):s.excluded>0?p("tree.insideOut",{n:s.excluded}):p("tree.insideIn",{n:s.included})})]}),t&&e.children.length>0&&C(e.children)]},e.path)})}),F=N!=="".concat(l,"|").concat(t);return(0,r.jsxs)("div",{className:"dir-tree-box",children:[(0,r.jsxs)("div",{className:"row",children:[(0,r.jsx)("button",{type:"button",onClick:()=>void w(),disabled:!l.trim(),children:null===j||F?p("tree.load"):p("tree.reload")}),(0,r.jsx)("span",{className:"muted small",children:p("tree.hint")})]}),v&&(0,r.jsx)("div",{className:"err small",children:v}),(0,r.jsxs)("p",{className:"muted small",style:{marginTop:6},children:[p("tree.alsoOut")," ",[t?p("tree.alsoGitignore"):null,!1===c?p("tree.alsoEnv"):null,p("tree.alsoAlways")].filter(Boolean).join(" \xb7 ")]}),null!==j&&!F&&(0===j.length?(0,r.jsx)("p",{className:"muted small",children:p("mirror.noDirs")}):C(k))]})}},3197:(e,l,t)=>{"use strict";t.r(l),t.d(l,{default:()=>m});var r=t(3365),s=t(1521),a=t(8197),n=t.n(a),i=t(5549),o=t(867),d=t(1035),c=t(4784),u=t(2244);function m(){let{t:e}=(0,o.kj)(),[l,t]=(0,s.useState)(null),[a,n]=(0,s.useState)(!1),[c,u]=(0,s.useState)("");(0,s.useEffect)(()=>{i.FH.models().then(t).catch(()=>void 0)},[]);let m=async()=>{if(await (0,d.Z)(e("model.refreshConfirm"))){n(!0),u(e("model.refreshing"));try{var l;let r=await i.FH.models().then(()=>i.FH.refreshModels());t(r),u(0===r.options.length?null!=(l=r.note)?l:e("model.none"):e("model.refreshed",{n:r.options.length}))}catch(e){u(e.message)}finally{n(!1)}}},h={catalogue:l,setCatalogue:t,refreshModels:m,refreshing:a,refreshMsg:c};return(0,r.jsxs)(r.Fragment,{children:[(0,r.jsxs)("div",{className:"panel",children:[(0,r.jsx)("h2",{children:e("def.title")}),(0,r.jsx)("p",{className:"muted small",children:e("def.intro")}),(0,r.jsx)("p",{className:"why",children:e("def.autoSave")})]}),(0,r.jsx)(j,{}),(0,r.jsx)(g,{...h}),(0,r.jsx)(y,{...h}),(0,r.jsx)(f,{})]})}function h(e){let l=arguments.length>1&&void 0!==arguments[1]?arguments[1]:900,t=(0,s.useRef)(null),r=(0,s.useRef)(e);return r.current=e,(0,s.useEffect)(()=>()=>{t.current&&clearTimeout(t.current)},[]),e=>{t.current&&clearTimeout(t.current),t.current=setTimeout(()=>void r.current(e),l)}}function p(e){let{msg:l,onSave:t}=e,{t:s}=(0,o.kj)();return(0,r.jsxs)("div",{className:"row",style:{marginTop:6},children:[t&&(0,r.jsx)("button",{className:"quiet",onClick:t,title:s("def.saveAnywayWhy"),children:s("def.saveAnyway")}),(0,r.jsx)("span",{className:"muted small",role:"status",children:l||s("def.savedAutomatically")})]})}function j(){var e;let{t:l}=(0,o.kj)(),[t,a]=(0,s.useState)(null),[n,d]=(0,s.useState)(""),[c,u]=(0,s.useState)(""),[m,j]=(0,s.useState)(""),[v,f]=(0,s.useState)(""),[g,y]=(0,s.useState)(!1),[N,b]=(0,s.useState)(""),[w,k]=(0,s.useState)(""),S=(0,s.useCallback)(async()=>{try{let e=await i.FH.project();a(e),d(e.rootDir),u(e.name),f("")}catch(e){f(e.message)}},[]);(0,s.useEffect)(()=>{S()},[S]);let D=async(e,l)=>{y(!0),j("");try{let t=await i.FH.setProject(e);return a(t),d(t.rootDir),j(l(t)),f(""),!0}catch(e){return f(e.message),!1}finally{y(!1)}},C=e=>D({rootDir:e},e=>e.rootDir?l("proj.saved",{dir:e.rootDir}):l("proj.cleared")),F=e=>D({name:e},()=>l("proj.nameSaved")),T=h(C),B=h(F),M=async(e,l)=>{y(!0);try{var t;let r=await i.FH.browseFolder(l.trim()||void 0);r.ok?e(r.path):r.cancelled||f(null!=(t=r.reason)?t:"")}finally{y(!1)}},R=null!=(e=null==t?void 0:t.others)?e:[],A=e=>e.map(e=>({name:e.name,rootDir:e.rootDir,...e.mirror?{mirror:e.mirror}:{}})),E=async()=>{await D({others:[...A(R),{name:N.trim(),rootDir:w.trim()}]},e=>l("proj.othersSaved",{n:e.others.length}))&&(b(""),k(""))};return(0,r.jsxs)("div",{className:"panel",id:"project",children:[(0,r.jsx)("h2",{children:l("proj.title")}),(0,r.jsx)("p",{className:"muted small",children:l("proj.intro")}),v&&(0,r.jsx)("div",{className:"err",children:v}),t&&(0,r.jsxs)("div",{className:"option".concat(t.mirrorToDesktop?" warned":""),style:{marginBottom:12},children:[(0,r.jsxs)("label",{children:[(0,r.jsx)("input",{type:"checkbox",checked:t.mirrorToDesktop,onChange:e=>{D({mirrorToDesktop:e.target.checked},e=>e.mirrorToDesktop?l("proj.mirrorOn",{root:e.contextRoot}):l("proj.mirrorOff"))},disabled:g}),(0,r.jsx)("span",{children:l("proj.mirrorToDesktop")})]}),(0,r.jsx)("p",{className:"why",children:l("proj.mirrorToDesktopWhy",{root:t.contextRoot})})]}),(0,r.jsx)("p",{className:"muted small",children:l("proj.listIntro")}),(0,r.jsx)(x,{name:c,dir:n,repoOk:!!(null==t?void 0:t.repoOk),repoProblem:null==t?void 0:t.repoProblem,mirror:null==t?void 0:t.mirror,isDefault:!0,busy:g,onName:e=>{u(e),B(e)},onNameBlur:()=>void F(c),onDir:e=>{d(e),T(e)},onDirBlur:()=>void C(n),onBrowse:()=>void M(e=>void C(e),n),onRemove:(null==t?void 0:t.rootDir)?()=>void C(""):void 0,removeLabel:l("proj.clear"),onFolders:e=>D({mirror:e},()=>l("proj.foldersSaved"))}),(0,r.jsx)(p,{msg:m}),t&&!t.rootDir&&(0,r.jsx)("p",{className:"muted small",style:{marginTop:8},children:l("proj.none")}),R.map(e=>(0,r.jsx)(x,{name:e.name,dir:e.rootDir,repoOk:e.repoOk,repoProblem:e.repoProblem,mirror:e.mirror,busy:g,onName:t=>void D({others:A(R.map(l=>l.name===e.name?{...l,name:t}:l))},()=>l("proj.nameSaved")),onDir:t=>void D({others:A(R.map(l=>l.name===e.name?{...l,rootDir:t}:l))},()=>l("proj.othersSaved",{n:R.length})),onBrowse:()=>void M(t=>void D({others:A(R.map(l=>l.name===e.name?{...l,rootDir:t}:l))},()=>l("proj.othersSaved",{n:R.length})),e.rootDir),onRemove:()=>{let t;t=e.name,D({others:A(R.filter(e=>e.name!==t))},e=>l("proj.othersSaved",{n:e.others.length}))},removeLabel:l("proj.otherRemove"),onFolders:t=>{let r;return r=e.name,D({others:A(R.map(e=>e.name===r?{...e,mirror:t}:e))},()=>l("proj.foldersSaved"))}},e.name)),(0,r.jsx)("h3",{id:"others",children:l("proj.addTitle")}),(0,r.jsx)("p",{className:"muted small",children:l("proj.othersIntro")}),(0,r.jsxs)("div",{className:"row",style:{marginTop:8},children:[(0,r.jsx)("input",{type:"text","aria-label":l("proj.entryName"),value:N,onChange:e=>b(e.target.value),placeholder:l("proj.entryName"),disabled:g,style:{width:160}}),(0,r.jsx)("input",{type:"text",className:"grow","aria-label":l("proj.entryDir"),value:w,onChange:e=>k(e.target.value),placeholder:"C:\\Projects\\my-app-tests",disabled:g}),(0,r.jsx)("button",{onClick:()=>void M(e=>k(e),w),disabled:g,children:l("mirror.browse")}),(0,r.jsx)("button",{className:"primary",onClick:()=>void E(),disabled:g||!N.trim()||!w.trim(),children:l("proj.otherAdd")})]}),(0,r.jsx)("h3",{children:l("proj.affects")}),(0,r.jsxs)("ul",{className:"muted small",style:{margin:0,paddingLeft:20},children:[(0,r.jsx)("li",{children:l("proj.affectsNew")}),(0,r.jsx)("li",{children:l("proj.affectsExisting")}),(0,r.jsx)("li",{children:l("proj.affectsPlan")}),(0,r.jsx)("li",{children:l("proj.affectsNever")})]})]})}function x(e){var l;let{name:t,dir:s,repoOk:a,repoProblem:n,mirror:i,isDefault:d=!1,busy:c,onName:u,onNameBlur:m,onDir:h,onDirBlur:p,onBrowse:j,onRemove:x,removeLabel:f,onFolders:g}=e,{t:y}=(0,o.kj)();return(0,r.jsxs)("div",{className:"panel inner",style:{marginTop:10},children:[(0,r.jsxs)("div",{className:"row",children:[(0,r.jsxs)("div",{style:{width:200},children:[(0,r.jsx)("label",{children:y("proj.entryName")}),(0,r.jsx)("input",{type:"text",value:t,onChange:e=>u(e.target.value),onBlur:m,placeholder:s?null!=(l=s.replace(/[\/]+$/,"").split(/[\/]/).pop())?l:"":y("proj.namePlaceholder"),disabled:c})]}),(0,r.jsxs)("div",{className:"grow",children:[(0,r.jsx)("label",{children:y("proj.entryDir")}),(0,r.jsx)("input",{type:"text",value:s,onChange:e=>h(e.target.value),onBlur:p,placeholder:"C:\\Projects\\my-app",disabled:c})]}),(0,r.jsx)("button",{onClick:j,disabled:c,children:y("mirror.browse")}),x&&(0,r.jsx)("button",{className:"quiet",onClick:x,disabled:c,children:f})]}),(0,r.jsxs)("div",{className:"row small",style:{marginTop:6},children:[d&&(0,r.jsx)("span",{className:"chip",title:y("proj.isDefaultWhy"),children:y("proj.isDefault")}),s&&(0,r.jsx)("span",{className:"badge ".concat(a?"done":""),title:a?y("proj.isRepo"):n,children:y(a?"proj.otherRepo":"proj.otherNotRepo")}),s&&!a&&(0,r.jsx)("span",{className:"muted",children:n||y("proj.notRepoWhy")})]}),s&&(0,r.jsxs)("details",{className:"small",style:{marginTop:8},children:[(0,r.jsx)("summary",{children:y("proj.folders")}),(0,r.jsx)(v,{rootDir:s,value:i,onSave:g,busy:c})]})]})}function v(e){var l,t,a,n;let{rootDir:i,value:c,onSave:m,busy:j}=e,{t:x}=(0,o.kj)(),[v,f]=(0,s.useState)((null!=(l=null==c?void 0:c.includeDirs)?l:[]).join("\n")),[g,y]=(0,s.useState)((null!=(t=null==c?void 0:c.excludeDirs)?t:[]).join("\n")),[N,b]=(0,s.useState)(null==(a=null==c?void 0:c.respectGitignore)||a),[w,k]=(0,s.useState)(null!=(n=null==c?void 0:c.includeEnvFiles)&&n),S=e=>e.split("\n").map(e=>e.trim()).filter(Boolean),[D,C]=(0,s.useState)(""),F=async e=>{let l={includeDirs:S(v),excludeDirs:S(g),respectGitignore:N,includeEnvFiles:w,...e};await m(l),C(x("proj.foldersSaved"))},T=h(F),B=async e=>{(!e||await (0,d.Z)(x("mirror.envWarn")))&&(k(e),F({includeEnvFiles:e}))};return(0,r.jsxs)("div",{style:{marginTop:8},children:[(0,r.jsx)("p",{className:"muted small",children:x("proj.foldersHint")}),(0,r.jsxs)("div",{className:"row",style:{alignItems:"flex-start"},children:[(0,r.jsxs)("div",{className:"grow",children:[(0,r.jsx)("label",{children:x("mirror.include")}),(0,r.jsx)("textarea",{value:v,onChange:e=>{f(e.target.value),T({includeDirs:S(e.target.value),excludeDirs:S(g)})},placeholder:"src\ntests",style:{minHeight:70}})]}),(0,r.jsxs)("div",{className:"grow",children:[(0,r.jsx)("label",{children:x("mirror.exclude")}),(0,r.jsx)("textarea",{value:g,onChange:e=>{y(e.target.value),T({includeDirs:S(v),excludeDirs:S(e.target.value)})},placeholder:"src/generated",style:{minHeight:70}})]})]}),(0,r.jsx)(u.k,{rootDir:i,respectGitignore:N,includeEnvFiles:w,include:S(v),exclude:S(g),onChange:(e,l)=>{f(e.join("\n")),y(l.join("\n")),T({includeDirs:e,excludeDirs:l})}}),(0,r.jsx)("div",{className:"option",children:(0,r.jsxs)("label",{children:[(0,r.jsx)("input",{type:"checkbox",checked:N,onChange:e=>{b(e.target.checked),F({respectGitignore:e.target.checked})}}),(0,r.jsx)("span",{children:x("mirror.gitignore")})]})}),(0,r.jsx)("div",{className:"option".concat(w?" warned":""),children:(0,r.jsxs)("label",{children:[(0,r.jsx)("input",{type:"checkbox",checked:w,onChange:e=>void B(e.target.checked)}),(0,r.jsx)("span",{children:x("mirror.env")})]})}),(0,r.jsx)(p,{msg:j?"":D})]})}function f(){let{t:e}=(0,o.kj)(),[l,t]=(0,s.useState)(null),[a,n]=(0,s.useState)(2),[d,c]=(0,s.useState)("none"),[u,m]=(0,s.useState)(2),[j,x]=(0,s.useState)(""),[v,f]=(0,s.useState)(""),[g,y]=(0,s.useState)(!1);(0,s.useEffect)(()=>{i.FH.settings().then(e=>{var l,r,s;t(e.raw);let a=null!=(l=e.raw.limits)?l:{},i="number"==typeof a.retryBlockedInFreshChat?a.retryBlockedInFreshChat:2;n(i),m(i),c(null!=(s=(null!=(r=e.raw.execution)?r:{}).isolation)?s:"none")}).catch(e=>f(e.message))},[]);let N=async r=>{if(l){y(!0),x("");try{var s;let a={...null!=(s=l.limits)?s:{},retryBlockedInFreshChat:r},n={...l,limits:a};await i.FH.saveSettings(n),t(n),m(r),x(e("exec.saved")),f("")}catch(e){f(e.message)}finally{y(!1)}}},b=h(N),w=async r=>{if(l){y(!0),x("");try{var s;let a={...null!=(s=l.execution)?s:{},isolation:r},n={...l,execution:a};await i.FH.saveSettings(n),t(n),x(e("exec.saved")),f("")}catch(e){f(e.message)}finally{y(!1)}}};return(0,r.jsxs)("div",{className:"panel",id:"execution",children:[(0,r.jsx)("h2",{children:e("exec.title")}),(0,r.jsx)("p",{className:"muted small",children:e("exec.intro")}),v&&(0,r.jsx)("div",{className:"err",children:v}),(0,r.jsx)("label",{htmlFor:"retry-blocked",children:e("exec.retryBlocked")}),(0,r.jsxs)("div",{className:"row",children:[(0,r.jsx)("input",{id:"retry-blocked",type:"number",min:0,max:5,value:a,onChange:e=>{let l=Math.max(0,Math.min(5,Number(e.target.value)||0));n(l),b(l)},onBlur:()=>a!==u&&void N(a),style:{width:90},disabled:g||!l}),(0,r.jsx)("span",{className:"muted small",children:e("exec.retryBlockedTimes")})]}),(0,r.jsx)("p",{className:"why",children:e("exec.retryBlockedWhy")}),(0,r.jsx)("label",{htmlFor:"isolation",children:e("exec.isolation")}),(0,r.jsxs)("select",{id:"isolation",value:d,onChange:e=>{let l=e.target.value;c(l),w(l)},disabled:g||!l,children:[(0,r.jsx)("option",{value:"none",children:e("exec.isolationNone")}),(0,r.jsx)("option",{value:"none-accepted",children:e("exec.isolationNoneAccepted")}),(0,r.jsx)("option",{value:"separate-account",children:e("exec.isolationAccount")}),(0,r.jsx)("option",{value:"sandbox",children:e("exec.isolationSandbox")}),(0,r.jsx)("option",{value:"vm",children:e("exec.isolationVm")})]}),(0,r.jsx)(p,{msg:j}),(0,r.jsx)("p",{className:"why",children:e("exec.isolationWhy")})]})}function g(e){var l;let{catalogue:t,setCatalogue:a,refreshModels:n,refreshing:d,refreshMsg:u}=e,{t:m}=(0,o.kj)(),h=(0,o.W3)(),[j,x]=(0,s.useState)(""),[v,f]=(0,s.useState)(""),[g,y]=(0,s.useState)(!1),N=null!=(l=null==t?void 0:t.defaultModel)?l:"",b=async e=>{y(!0),x("");try{let l=await i.FH.setDefaultModel(e);t&&a({...t,defaultModel:l.defaultModel}),x(l.defaultModel?m("def.modelSaved",{name:l.defaultModel}):m("def.modelCleared")),f("")}catch(e){f(e.message)}finally{y(!1)}};return(0,r.jsxs)("div",{className:"panel",id:"model",children:[(0,r.jsx)("h2",{children:m("def.modelTitle")}),(0,r.jsx)("p",{className:"muted small",children:m("def.modelIntro")}),v&&(0,r.jsx)("div",{className:"err",children:v}),(0,r.jsx)("label",{htmlFor:"default-model",children:m("def.modelField")}),(0,r.jsxs)("div",{className:"row",children:[(0,r.jsx)(c.Y,{id:"default-model",chosen:N,onChange:e=>void b(e),none:m("def.modelNone"),catalogue:t,disabled:g||d}),(0,r.jsx)("button",{className:"quiet",onClick:()=>void b(""),disabled:g||!N,children:m("proj.clear")}),(0,r.jsx)("button",{onClick:()=>void n(),disabled:g||d,children:m("model.refresh")})]}),(0,r.jsx)(p,{msg:j||u}),(0,r.jsx)("p",{className:"muted small",style:{marginTop:8},children:(null==t?void 0:t.readAt)?m("model.readAt",{t:h(t.readAt),n:t.options.length}):m("model.neverRead")}),(0,r.jsx)("h3",{children:m("proj.affects")}),(0,r.jsxs)("ul",{className:"muted small",style:{margin:0,paddingLeft:20},children:[(0,r.jsx)("li",{children:m("def.modelAffectsNew")}),(0,r.jsx)("li",{children:m("def.modelAffectsExisting")}),(0,r.jsx)("li",{children:m("def.modelAffectsBatch")})]})]})}function y(e){var l,t;let{catalogue:a,setCatalogue:d,refreshModels:u,refreshing:m,refreshMsg:h}=e,{t:j}=(0,o.kj)(),[x,v]=(0,s.useState)(""),[f,g]=(0,s.useState)(""),[y,N]=(0,s.useState)(!1),b=null!=(l=null==a?void 0:a.defaultReviewModel)?l:"",w=async e=>{N(!0),v("");try{let l=await i.FH.setDefaultReviewModel(e);a&&d({...a,defaultReviewModel:l.defaultReviewModel}),v(l.defaultReviewModel?j("def.reviewSaved",{name:l.defaultReviewModel}):j("def.reviewCleared")),g("")}catch(e){g(e.message)}finally{N(!1)}},k=""!==b&&b===(null!=(t=null==a?void 0:a.defaultModel)?t:"");return(0,r.jsxs)("div",{className:"panel",id:"review",children:[(0,r.jsx)("h2",{children:j("def.reviewTitle")}),(0,r.jsx)("p",{className:"muted small",children:j("def.reviewIntro")}),f&&(0,r.jsx)("div",{className:"err",children:f}),(0,r.jsx)("label",{htmlFor:"default-review-model",children:j("def.reviewField")}),(0,r.jsxs)("div",{className:"row",children:[(0,r.jsx)(c.Y,{id:"default-review-model",chosen:b,onChange:e=>void w(e),none:j("def.reviewNone"),catalogue:a,disabled:y||m}),(0,r.jsx)("button",{className:"quiet",onClick:()=>void w(""),disabled:y||!b,children:j("proj.clear")}),(0,r.jsx)("button",{onClick:()=>void u(),disabled:y||m,children:j("model.refresh")})]}),k&&(0,r.jsx)("p",{className:"why",style:{color:"var(--warn)"},children:j("def.reviewSame")}),(0,r.jsx)(p,{msg:x||h}),(0,r.jsx)("h3",{children:j("proj.affects")}),(0,r.jsxs)("ul",{className:"muted small",style:{margin:0,paddingLeft:20},children:[(0,r.jsx)("li",{children:j("def.reviewAffectsNew")}),(0,r.jsx)("li",{children:j("def.reviewAffectsExisting")}),(0,r.jsx)("li",{children:j("def.reviewAffectsBatch")})]}),(0,r.jsxs)("div",{className:"row",style:{marginTop:12},children:[(0,r.jsx)(n(),{href:"/",children:(0,r.jsx)("button",{children:j("proj.toSessions")})}),(0,r.jsx)(n(),{href:"/import",children:(0,r.jsx)("button",{className:"quiet",children:j("proj.toImport")})})]})]})}},4784:(e,l,t)=>{"use strict";t.d(l,{Y:()=>i});var r=t(3365),s=t(1521),a=t(5549),n=t(867);function i(e){var l,t;let{id:i,chosen:o,onChange:d,none:c,catalogue:u,disabled:m=!1,style:h}=e,{t:p}=(0,n.kj)(),j=function(e){let[l,t]=(0,s.useState)(null);return(0,s.useEffect)(()=>{if(void 0!==e)return;let l=!0;return a.FH.models().then(e=>{l&&t(e)}).catch(()=>void 0),()=>{l=!1}},[e]),void 0!==e?e:l}(u),x=null!=(l=null==j?void 0:j.options)?l:[],v=x.some(e=>e.name===o),f=x.filter(e=>!e.group),g=new Map;for(let e of x)e.group&&g.set(e.group,[...null!=(t=g.get(e.group))?t:[],e]);return(0,r.jsxs)("select",{id:i,value:o,onChange:e=>d(e.target.value),disabled:m,style:{width:"auto",minWidth:280,...h},children:[(0,r.jsx)("option",{value:"",children:c}),o&&!v&&(0,r.jsx)("option",{value:o,children:p("model.notInList",{name:o})}),f.map(e=>(0,r.jsxs)("option",{value:e.name,disabled:e.disabled,children:[e.name,e.disabled?" — ".concat(p("model.unavailable")):""]},e.name)),[...g.entries()].map(e=>{let[l,t]=e;return(0,r.jsx)("optgroup",{label:l,children:t.map(e=>(0,r.jsxs)("option",{value:e.name,disabled:e.disabled,children:[e.name,e.disabled?" — ".concat(p("model.unavailable")):""]},e.name))},l)})]})}}},e=>{e.O(0,[197,867,643,347,131,358],()=>e(e.s=1896)),_N_E=e.O()}]);
@@ -1 +0,0 @@
1
- (self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[322],{5515:(e,s,a)=>{Promise.resolve().then(a.bind(a,9262))},9262:(e,s,a)=>{"use strict";a.r(s),a.d(s,{default:()=>o});var l=a(3365),n=a(1521),t=a(8197),i=a.n(t),r=a(5549),c=a(1035),d=a(867);function o(){var e,s;let{t:a,locale:t}=(0,d.kj)(),o=(0,d.W3)(),[m,h]=(0,n.useState)(""),[u,x]=(0,n.useState)(""),[j,v]=(0,n.useState)(!1),[g,y]=(0,n.useState)(""),[N,k]=(0,n.useState)(""),[f,w]=(0,n.useState)(0),[b,C]=(0,n.useState)(""),[S,T]=(0,n.useState)(!1),[H,F]=(0,n.useState)(null),[E,P]=(0,n.useState)(""),[D,_]=(0,n.useState)(""),A=(0,n.useRef)(null),[B,R]=(0,n.useState)(null);(0,n.useEffect)(()=>{let e=!1;return r.FH.planBrief(t).then(s=>{e||(h(s.text),x(s.software),k(""))}).catch(s=>{e||k(s.message)}),()=>{e=!0}},[t,f]);let z=(0,n.useCallback)(async(e,s)=>{try{await navigator.clipboard.writeText(s),y(e),window.setTimeout(()=>y(""),2500)}catch(e){_(a("plan.copyFailed"))}},[a]),I=(0,n.useCallback)(async e=>{if(e.size>2097152)return void _(a("plan.fileTooBig",{size:"".concat(Math.round(e.size/1024)," KB")}));try{C(await e.text()),F(null),R(null),_("")}catch(e){_(a("plan.fileError",{reason:e.message}))}},[a]),O=async()=>{P("check"),_("");try{F(await r.FH.checkPlan(b))}catch(e){_(e.message)}finally{P("")}},W=async()=>{var e;let s=H&&!H.ok?[]:null!=(e=null==H?void 0:H.duplicates)?e:[];if(s.length>0){let e=s.map(e=>"• ".concat(e.name," (").concat(e.tasks,")")).join("\n");if(!await (0,c.Z)(a("plan.duplicateConfirm",{names:e})))return}P("import"),_("");try{let e=await r.FH.importPlan(b);e.ok?(R(e),F({ok:!0,warnings:e.result.warnings,summary:e.summary,duplicates:e.duplicates}),C("")):(R(null),F(e.check))}catch(e){_(e.message)}finally{P("")}},q=(H&&!H.ok?H.issues:[]).map(e=>e.path?"- ".concat(e.path,": ").concat(e.message):"- ".concat(e.message)).join("\n");return(0,l.jsxs)(l.Fragment,{children:[(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("h2",{children:a("plan.title")}),(0,l.jsx)("p",{className:"muted small",children:a("plan.intro")})]}),(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("h2",{children:a("plan.step1")}),(0,l.jsx)("p",{className:"muted small",children:a("plan.step1Hint")}),(0,l.jsx)("h3",{children:a("plan.briefAsks")}),(0,l.jsx)("p",{className:"why",children:a("plan.briefAsksWhy")}),(0,l.jsxs)("div",{className:"row",style:{marginTop:12},children:[(0,l.jsx)("button",{className:"primary",onClick:()=>void z("brief",m),disabled:!m,children:a("plan.copyBrief")}),"brief"===g&&(0,l.jsx)("span",{className:"badge done",children:a("plan.copied")}),(0,l.jsx)("span",{className:"muted small",children:a("plan.briefLang")})]}),N&&(0,l.jsx)("div",{className:"err",children:N}),(0,l.jsx)("h3",{style:{marginTop:16},children:a("plan.persona")}),(0,l.jsx)("p",{className:"why",children:a("plan.personaWhy")}),(0,l.jsxs)("details",{style:{marginTop:8},open:j,onToggle:e=>v(e.target.open),children:[(0,l.jsx)("summary",{children:a("plan.softwarePart")}),(0,l.jsx)("textarea",{readOnly:!0,value:u,style:{minHeight:380,marginTop:10}})]}),(0,l.jsx)(p,{kind:"organisation",onSaved:()=>w(e=>e+1)}),(0,l.jsx)(p,{kind:"persona",onSaved:()=>w(e=>e+1)}),(0,l.jsx)(p,{kind:"work",onSaved:()=>w(e=>e+1)})]}),(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("h2",{children:a("plan.step2")}),(0,l.jsx)("p",{className:"muted small",children:a("plan.step2Hint")}),(0,l.jsxs)("div",{className:"dropzone".concat(S?" active":""),onDragOver:e=>{e.preventDefault(),T(!0)},onDragLeave:()=>T(!1),onDrop:e=>{var s;e.preventDefault(),T(!1);let a=null==(s=e.dataTransfer.files)?void 0:s[0];a&&I(a)},children:[(0,l.jsx)("textarea",{className:"grow",placeholder:a("plan.placeholder"),value:b,onChange:e=>{C(e.target.value),F(null),R(null)},style:{minHeight:220,width:"100%"}}),(0,l.jsx)("p",{className:"muted small",children:S?a("plan.dropActive"):a("plan.drop")})]}),(0,l.jsxs)("div",{className:"row",style:{marginTop:10},children:[(0,l.jsx)("button",{onClick:()=>{var e;return null==(e=A.current)?void 0:e.click()},children:a("plan.browse")}),(0,l.jsx)("input",{ref:A,type:"file",accept:".json,application/json,text/plain",style:{display:"none"},onChange:e=>{var s;let a=null==(s=e.target.files)?void 0:s[0];a&&I(a),e.target.value=""}}),(0,l.jsx)("button",{onClick:()=>void O(),disabled:!b.trim()||""!==E,children:"check"===E?a("plan.checking"):a("plan.check")}),(0,l.jsx)("button",{className:"primary",onClick:()=>void W(),disabled:!b.trim()||""!==E,children:"import"===E?a("plan.importing"):a("plan.import")}),(0,l.jsx)("button",{className:"quiet",onClick:()=>{C(""),F(null),R(null),_("")},disabled:!b&&!H,children:a("plan.clear")})]}),D&&(0,l.jsx)("div",{className:"err",children:D}),B&&""===b.trim()&&(0,l.jsx)("p",{className:"why",children:a("plan.cleared")})]}),H&&!H.ok&&(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("div",{className:"notice",children:(0,l.jsx)("strong",{children:a("plan.invalid")})}),(0,l.jsx)("h3",{children:a("plan.issues")}),(0,l.jsx)("p",{className:"muted small",children:a("plan.issuesHint")}),(0,l.jsx)("pre",{children:q}),(0,l.jsxs)("div",{className:"row",children:[(0,l.jsx)("button",{onClick:()=>void z("issues",q),children:a("plan.copyIssues")}),"issues"===g&&(0,l.jsx)("span",{className:"badge done",children:a("plan.copied")})]})]}),(null!=(e=null==H?void 0:H.duplicates.length)?e:0)>0&&(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsxs)("div",{className:"notice caution",children:[(0,l.jsx)("strong",{children:a("plan.duplicates")}),(0,l.jsx)("ul",{children:(null!=(s=null==H?void 0:H.duplicates)?s:[]).map(e=>(0,l.jsx)("li",{children:(0,l.jsx)(i(),{href:(0,r.aT)(e.sessionId),children:a("plan.duplicateRow",{name:e.name,tasks:e.tasks,when:o(e.createdAt)})})},e.sessionId))})]}),(0,l.jsx)("p",{className:"muted small",children:a("plan.duplicatesHint")})]}),(null==H?void 0:H.ok)&&(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("div",{className:"notice calm",children:(0,l.jsx)("strong",{children:B?a("plan.imported",{sessions:B.result.sessions.length,tasks:B.result.taskCount}):a("plan.valid",{sessions:H.summary.sessions.length,tasks:H.summary.taskCount})})}),H.summary.plan&&(0,l.jsx)("p",{children:H.summary.plan}),(0,l.jsxs)("p",{className:"muted small",children:[a("plan.col.planFail"),":"," ","continue"===H.summary.onFailure?a("batch.independent"):a("batch.chain")]}),(0,l.jsx)("h3",{children:a("plan.preview")}),(0,l.jsxs)("table",{children:[(0,l.jsx)("thead",{children:(0,l.jsxs)("tr",{children:[(0,l.jsx)("th",{children:a("plan.col.session")}),(0,l.jsx)("th",{children:a("plan.col.tasks")}),(0,l.jsx)("th",{children:a("plan.col.chain")}),(0,l.jsx)("th",{children:a("plan.col.repo")})]})}),(0,l.jsx)("tbody",{children:H.summary.sessions.map((e,s)=>{let n=null==B?void 0:B.result.sessions[s];return(0,l.jsxs)("tr",{children:[(0,l.jsx)("td",{children:n?(0,l.jsx)(i(),{href:(0,r.aT)(n.id),children:e.name}):e.name}),(0,l.jsxs)("td",{className:"small",children:[e.tasks.length,(0,l.jsx)("div",{className:"muted small",children:e.tasks.join(", ")})]}),(0,l.jsx)("td",{className:"small",children:"continue"===e.onFailure?a("chain.continue"):a("chain.stop")}),(0,l.jsx)("td",{className:"small muted",children:e.repoDir||a("plan.noRepo")})]},"".concat(e.name,"-").concat(s))})})]}),H.summary.notes&&(0,l.jsxs)(l.Fragment,{children:[(0,l.jsx)("h3",{children:a("plan.notes")}),(0,l.jsx)("p",{className:"muted small",style:{whiteSpace:"pre-wrap"},children:H.summary.notes})]}),H.warnings.length>0&&(0,l.jsxs)("div",{className:"notice caution",children:[(0,l.jsx)("strong",{children:a("plan.warnings")}),(0,l.jsx)("ul",{children:H.warnings.map(e=>(0,l.jsx)("li",{children:e},e))})]})]}),B&&(0,l.jsxs)("div",{className:"panel",children:[(0,l.jsx)("h2",{children:a("plan.step3")}),(0,l.jsx)("p",{className:"muted small",children:a("plan.step3Hint")}),(0,l.jsxs)("div",{className:"row",children:[(0,l.jsx)(i(),{href:"/?run=".concat(encodeURIComponent(B.result.sessions.map(e=>e.id).join(",")),"&fail=").concat(B.summary.onFailure),children:(0,l.jsx)("button",{className:"primary",children:a("plan.runThese")})}),(0,l.jsx)(i(),{href:"/",children:(0,l.jsx)("button",{children:a("plan.toSessions")})})]})]})]})}function p(e){let{kind:s,onSaved:a}=e,{t,locale:i}=(0,d.kj)(),[o,p]=(0,n.useState)(""),[m,h]=(0,n.useState)(""),[u,x]=(0,n.useState)(""),[j,v]=(0,n.useState)(!1),[g,y]=(0,n.useState)(""),N=(0,n.useRef)(null);(0,n.useEffect)(()=>{let e=!1;return r.FH.context(s,i).then(s=>{e||(p(s.content),h(s.content),x(s.example),v(s.customised))}).catch(e=>y(e.message)),()=>{e=!0}},[s,i]);let k=async e=>{try{await r.FH.setContext(s,e),h(e),v(""!==e.trim()),y(t("plan.ctxSaved")),a()}catch(e){y(e.message)}},f=async()=>{if(await (0,c.Z)(t("plan.ctxClearConfirm")))try{let e=await r.FH.resetContext(s,i);p(e.content),h(e.content),v(e.customised),y(t("plan.ctxCleared")),a()}catch(e){y(e.message)}},w="organisation"===s?t("plan.orgPart"):"persona"===s?t("plan.personaPart"):t("plan.workPart"),b="organisation"===s?t("plan.orgHint"):"persona"===s?t("plan.personaHint"):t("plan.workHint");return(0,l.jsxs)("details",{style:{marginTop:8},open:!0,children:[(0,l.jsxs)("summary",{children:[w," ",(0,l.jsxs)("span",{className:"muted small",children:["— ",j?t("plan.ctxWritten"):t("plan.ctxEmpty")]})]}),(0,l.jsx)("p",{className:"muted small",style:{marginTop:8},children:b}),(0,l.jsx)("textarea",{value:o,onChange:e=>{var s;p(e.target.value),s=e.target.value,N.current&&clearTimeout(N.current),N.current=setTimeout(()=>void k(s),900)},onBlur:()=>o!==m&&void k(o),placeholder:u,style:{minHeight:220}}),(0,l.jsxs)("div",{className:"row",style:{marginTop:6},children:[(0,l.jsx)("button",{className:"quiet",onClick:()=>void f(),disabled:!j,children:t("plan.ctxClear")}),(0,l.jsx)("span",{className:"muted small",role:"status",children:g||t("def.savedAutomatically")})]})]})}}},e=>{e.O(0,[197,867,643,347,131,358],()=>e(e.s=5515)),_N_E=e.O()}]);
@@ -1 +0,0 @@
1
- (self.webpackChunk_N_E=self.webpackChunk_N_E||[]).push([[177],{952:()=>{},1205:(e,t,a)=>{"use strict";a.d(t,{AppearanceProvider:()=>d,K:()=>h,themeScript:()=>i});var n=a(3365),r=a(1521);let s={theme:"light",textSize:"normal",highContrast:!1,reduceMotion:!1,underlineLinks:!1,strongFocus:!1},o="cop.appearance",i="\n(function () {\n try {\n var d = document.documentElement;\n var raw = localStorage.getItem('".concat(o,"');\n var a = raw ? JSON.parse(raw) : {};\n d.dataset.theme = a.theme === 'dark' ? 'dark' : 'light';\n d.dataset.textsize = a.textSize || 'normal';\n d.dataset.contrast = a.highContrast ? 'high' : 'normal';\n d.dataset.motion = a.reduceMotion ? 'reduced' : 'normal';\n d.dataset.links = a.underlineLinks ? 'underline' : 'plain';\n d.dataset.focus = a.strongFocus ? 'strong' : 'normal';\n } catch (e) {}\n})();\n");function l(e){let t=document.documentElement;t.dataset.theme=e.theme,t.dataset.textsize=e.textSize,t.dataset.contrast=e.highContrast?"high":"normal",t.dataset.motion=e.reduceMotion?"reduced":"normal",t.dataset.links=e.underlineLinks?"underline":"plain",t.dataset.focus=e.strongFocus?"strong":"normal"}let c=(0,r.createContext)({appearance:s,set:()=>void 0,reset:()=>void 0,loaded:!1});function d(e){let{children:t}=e,[a,i]=(0,r.useState)(s),[d,h]=(0,r.useState)(!1);(0,r.useEffect)(()=>{let e=s;try{let t=window.localStorage.getItem(o);t?e={...s,...JSON.parse(t)}:window.matchMedia("(prefers-color-scheme: dark)").matches&&(e={...e,theme:"dark"}),window.matchMedia("(prefers-reduced-motion: reduce)").matches&&!t&&(e={...e,reduceMotion:!0})}catch(e){}i(e),l(e),h(!0)},[]);let u=(0,r.useCallback)(e=>{i(t=>{let a={...t,...e};l(a);try{window.localStorage.setItem(o,JSON.stringify(a))}catch(e){}return a})},[]),m=(0,r.useCallback)(()=>{i(s),l(s);try{window.localStorage.removeItem(o)}catch(e){}},[]);return(0,n.jsx)(c.Provider,{value:{appearance:a,set:u,reset:m,loaded:d},children:t})}function h(){return(0,r.useContext)(c)}},1702:(e,t,a)=>{"use strict";var n=a(9962);a.o(n,"usePathname")&&a.d(t,{usePathname:function(){return n.usePathname}}),a.o(n,"useSearchParams")&&a.d(t,{useSearchParams:function(){return n.useSearchParams}})},5007:(e,t,a)=>{Promise.resolve().then(a.t.bind(a,8197,23)),Promise.resolve().then(a.bind(a,1035)),Promise.resolve().then(a.t.bind(a,952,23)),Promise.resolve().then(a.bind(a,8214)),Promise.resolve().then(a.bind(a,1205)),Promise.resolve().then(a.bind(a,867))},8214:(e,t,a)=>{"use strict";a.d(t,{Nav:()=>m,SkipLink:()=>u});var n=a(3365),r=a(1521),s=a(8197),o=a.n(s),i=a(1702),l=a(5549),c=a(867);let d={sessions:(0,n.jsx)("path",{d:"M4 5h16v4H4zM4 11h16v4H4zM4 17h10v2H4z"}),defaults:(0,n.jsx)("path",{d:"M12 8a4 4 0 1 0 0 8 4 4 0 0 0 0-8zm8.5 4 1.5 1-1.6 2.8-1.8-.4a7 7 0 0 1-1.5 1.5l.4 1.8L14.7 21l-1-1.5a7 7 0 0 1-3.4 0l-1 1.5-2.8-1.6.4-1.8A7 7 0 0 1 5.4 16l-1.8.4L2 13.6 3.5 12.6V11.4L2 10.4l1.6-2.8 1.8.4A7 7 0 0 1 6.9 6.5l-.4-1.8L9.3 3l1 1.5a7 7 0 0 1 3.4 0l1-1.5 2.8 1.6-.4 1.8a7 7 0 0 1 1.5 1.5l1.8-.4L22 10.4l-1.5 1z"}),import:(0,n.jsx)("path",{d:"M12 3v10m0 0 4-4m-4 4-4-4M4 15v4a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2v-4",fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinecap:"round",strokeLinejoin:"round"}),history:(0,n.jsx)("path",{d:"M12 3a9 9 0 1 0 8.5 6M12 7v5l3 2M3 4v5h5",fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinecap:"round",strokeLinejoin:"round"}),level1:(0,n.jsx)("path",{d:"M6 3h9l5 5v13H6zM14 3v6h6M9 13h7M9 17h7",fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinejoin:"round"}),presets:(0,n.jsx)("path",{d:"M5 4h14v4H5zM5 10h14v4H5zM5 16h9v4H5z",fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinejoin:"round"}),appearance:(0,n.jsx)("path",{d:"M12 3a9 9 0 0 0 0 18c1.5 0 2-1 2-2s-1-1.5-1-2.5S14 15 15.5 15H17a4 4 0 0 0 4-4 8 8 0 0 0-9-8zM8 9a1 1 0 1 0 0 2 1 1 0 0 0 0-2zm4-3a1 1 0 1 0 0 2 1 1 0 0 0 0-2zm4 3a1 1 0 1 0 0 2 1 1 0 0 0 0-2z"}),system:(0,n.jsx)("path",{d:"M4 5h16v10H4zM2 19h20M9 15v4M15 15v4",fill:"none",stroke:"currentColor",strokeWidth:"2",strokeLinejoin:"round"})},h=[{href:"/",label:"nav.sessions",icon:"sessions"},{href:"/defaults",label:"nav.defaults",icon:"defaults"},{href:"/import",label:"nav.import",icon:"import"},{href:"/history",label:"nav.history",icon:"history"},{href:"/level1",label:"nav.level1",icon:"level1"},{href:"/presets",label:"nav.presets",icon:"presets"},{href:"/appearance",label:"nav.appearance",icon:"appearance"},{href:"/system",label:"nav.system",icon:"system"}];function u(){let{t:e}=(0,c.kj)();return(0,n.jsx)("a",{className:"skip-link",href:"#main",children:e("a11y.skip")})}function m(){let{t:e}=(0,c.kj)(),t=(0,i.usePathname)(),a=function(){let[e,t]=(0,r.useState)(0);return(0,r.useEffect)(()=>{let e=!0,a=()=>l.FH.activity().then(a=>{e&&t(a.sessions)}).catch(()=>void 0);a();let n=setInterval(a,4e3);return()=>{e=!1,clearInterval(n)}},[]),e}();return(0,n.jsxs)("nav",{"aria-label":e("nav.label"),children:[h.map(r=>(0,n.jsxs)(o(),{href:r.href,"aria-current":t===r.href?"page":void 0,children:[(0,n.jsx)("svg",{className:"nav-icon",viewBox:"0 0 24 24",width:"16",height:"16",fill:"currentColor","aria-hidden":"true",children:d[r.icon]}),(0,n.jsx)("span",{children:e(r.label)}),"/history"===r.href&&a>0&&(0,n.jsxs)("span",{className:"live",title:e("nav.liveTitle",{n:a}),children:[(0,n.jsx)("span",{className:"dot","aria-hidden":"true"}),e("nav.live")]})]},r.href)),(0,n.jsx)(c.c5,{})]})}}},e=>{e.O(0,[353,197,867,643,347,131,358],()=>e(e.s=5007)),_N_E=e.O()}]);