tarsk 0.6.87 → 0.6.88
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bundled-skills/email-me/SKILL.md +15 -0
- package/dist/bundled-skills/email-me/scripts/__tests__/email_me.test.js +64 -0
- package/dist/bundled-skills/email-me/scripts/email_me.js +45 -0
- package/dist/bundled-skills/handoff/SKILL.md +19 -0
- package/dist/bundled-skills/tarsk-agent/SKILL.md +372 -0
- package/dist/bundled-skills/tarsk-ask-user/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-ask-user/scripts/ask_user.js +101 -0
- package/dist/bundled-skills/tarsk-bash/SKILL.md +17 -0
- package/dist/bundled-skills/tarsk-bash/scripts/bash.js +248 -0
- package/dist/bundled-skills/tarsk-browser/SKILL.md +17 -0
- package/dist/bundled-skills/tarsk-browser/scripts/browser.js +252 -0
- package/dist/bundled-skills/tarsk-chat-title/SKILL.md +14 -0
- package/dist/bundled-skills/tarsk-chat-title/scripts/chat_title.js +37 -0
- package/dist/bundled-skills/tarsk-connect-mcp/SKILL.md +23 -0
- package/dist/bundled-skills/tarsk-connect-mcp/scripts/__tests__/connect_mcp.test.js +68 -0
- package/dist/bundled-skills/tarsk-connect-mcp/scripts/connect_mcp.js +119 -0
- package/dist/bundled-skills/tarsk-create-project/SKILL.md +25 -0
- package/dist/bundled-skills/tarsk-create-project/scripts/__tests__/create_project.test.js +94 -0
- package/dist/bundled-skills/tarsk-create-project/scripts/create_project.js +88 -0
- package/dist/bundled-skills/tarsk-edit/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-edit/scripts/edit.js +118 -0
- package/dist/bundled-skills/tarsk-execute-skill-script/SKILL.md +19 -0
- package/dist/bundled-skills/tarsk-execute-skill-script/scripts/execute_skill_script.js +77 -0
- package/dist/bundled-skills/tarsk-fetch/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-fetch/scripts/fetch.js +38 -0
- package/dist/bundled-skills/tarsk-find/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-find/scripts/find.js +78 -0
- package/dist/bundled-skills/tarsk-find-images/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-find-images/scripts/find_images.js +78 -0
- package/dist/bundled-skills/tarsk-generate-image/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-generate-image/scripts/generate_image.js +55 -0
- package/dist/bundled-skills/tarsk-get-observation/SKILL.md +19 -0
- package/dist/bundled-skills/tarsk-get-observation/scripts/get_observation.js +293 -0
- package/dist/bundled-skills/tarsk-grep/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-grep/scripts/grep.js +174 -0
- package/dist/bundled-skills/tarsk-history/SKILL.md +15 -0
- package/dist/bundled-skills/tarsk-history/scripts/history.js +68 -0
- package/dist/bundled-skills/tarsk-improve/SKILL.md +232 -0
- package/dist/bundled-skills/tarsk-improve/references/signals.md +16 -0
- package/dist/bundled-skills/tarsk-improve/scripts/durable-runs.ts +635 -0
- package/dist/bundled-skills/tarsk-improve/scripts/ensure-exported.ts +238 -0
- package/dist/bundled-skills/tarsk-improve/scripts/export-tool-skills-lib.ts +299 -0
- package/dist/bundled-skills/tarsk-improve/scripts/summarize-session.ts +126 -0
- package/dist/bundled-skills/tarsk-jobs/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-jobs/scripts/job_kill.js +45 -0
- package/dist/bundled-skills/tarsk-jobs/scripts/job_list.js +64 -0
- package/dist/bundled-skills/tarsk-jobs/scripts/job_output.js +66 -0
- package/dist/bundled-skills/tarsk-notes/SKILL.md +17 -0
- package/dist/bundled-skills/tarsk-notes/scripts/notes.js +86 -0
- package/dist/bundled-skills/tarsk-projects/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-projects/scripts/projects.js +54 -0
- package/dist/bundled-skills/tarsk-prompt-project/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-prompt-project/scripts/prompt_project.js +58 -0
- package/dist/bundled-skills/tarsk-propose-branch/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-propose-branch/scripts/propose_branch.js +45 -0
- package/dist/bundled-skills/tarsk-read/SKILL.md +17 -0
- package/dist/bundled-skills/tarsk-read/scripts/read.js +331 -0
- package/dist/bundled-skills/tarsk-read-skill/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-read-skill/scripts/read_skill.js +37 -0
- package/dist/bundled-skills/tarsk-read-skill-reference/SKILL.md +19 -0
- package/dist/bundled-skills/tarsk-read-skill-reference/scripts/read_skill_reference.js +60 -0
- package/dist/bundled-skills/tarsk-run-js/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-run-js/scripts/run_js.js +192 -0
- package/dist/bundled-skills/tarsk-tasks/SKILL.md +18 -0
- package/dist/bundled-skills/tarsk-tasks/scripts/tasks.js +96 -0
- package/dist/bundled-skills/tarsk-todo/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-todo/scripts/todo.js +165 -0
- package/dist/bundled-skills/tarsk-web-search/SKILL.md +15 -0
- package/dist/bundled-skills/tarsk-web-search/scripts/web_search.js +120 -0
- package/dist/bundled-skills/tarsk-write/SKILL.md +16 -0
- package/dist/bundled-skills/tarsk-write/scripts/write.js +57 -0
- package/dist/index.js +215804 -210026
- package/dist/node_modules/@libsql/darwin-arm64/README.md +3 -0
- package/dist/node_modules/@libsql/{darwin-x64 → darwin-arm64}/index.node +0 -0
- package/dist/node_modules/@libsql/{darwin-x64 → darwin-arm64}/package.json +6 -6
- package/dist/public/assets/account-view-DkuCOxkE.js +1 -0
- package/dist/public/assets/{alert-dialog-DVaEQlVa.js → alert-dialog-BcZULJsX.js} +1 -1
- package/dist/public/assets/api-B_GSyYGh.js +1 -0
- package/dist/public/assets/api-C4ukGdyH.js +2 -0
- package/dist/public/assets/{async-error-boundary-DH6Sqgmt.js → async-error-boundary-FT8_xvjy.js} +1 -1
- package/dist/public/assets/browser-tab-DCjHytQ8.js +12 -0
- package/dist/public/assets/button-DDaJhJP1.js +1 -0
- package/dist/public/assets/{card-BkOGFps5.js → card-DAc45J1v.js} +1 -1
- package/dist/public/assets/chat-dock-context-a2bV9cnz.js +1 -0
- package/dist/public/assets/chat-handlers-context-2xSKzkKa.js +9 -0
- package/dist/public/assets/commit-dialog-C1oUFznJ.js +1 -0
- package/dist/public/assets/{commit-error-dialog-D3S6kRVr.js → commit-error-dialog--NTHg7Aw.js} +1 -1
- package/dist/public/assets/{commit-method-fields-BEKfSRyW.js → commit-method-fields-Xt3vbwUg.js} +1 -1
- package/dist/public/assets/{conversation-history-view-CVMD8hUU.js → conversation-history-view-CdfE7JTD.js} +1 -1
- package/dist/public/assets/{create-project-dialog-nquqlloK.js → create-project-dialog-BdR6iQE9.js} +2 -2
- package/dist/public/assets/{create-project-workspace-C4tXAUWJ.js → create-project-workspace-DSTTGom_.js} +2 -2
- package/dist/public/assets/create-repo-dialog-gw-8Rpdm.js +1 -0
- package/dist/public/assets/{delete-confirm-dialog-SpYpU1AX.js → delete-confirm-dialog-D1N86piR.js} +1 -1
- package/dist/public/assets/dialog-D_12AsZd.js +1 -0
- package/dist/public/assets/diff-view-B6JJNyn1.js +4 -0
- package/dist/public/assets/{dist-NcyjV9Gu.js → dist-2xH_pFmV.js} +1 -1
- package/dist/public/assets/{dist-BTu7PDzc.js → dist-AbkJBHH5.js} +1 -1
- package/dist/public/assets/{dist-lFBinzor.js → dist-B-h6Wj39.js} +1 -1
- package/dist/public/assets/dist-CgbWuuq4.js +1 -0
- package/dist/public/assets/{dist-f54JuzFV.js → dist-DOz2WXwX.js} +1 -1
- package/dist/public/assets/{dist-CqrmQxmV.js → dist-DfnQ9YJh.js} +1 -1
- package/dist/public/assets/{dist-BOfRC57H.js → dist-JGbQ_EJY.js} +1 -1
- package/dist/public/assets/{dist-ButPmyjr.js → dist-pCVg1Jdl.js} +1 -1
- package/dist/public/assets/dist-v_MvKS2-.js +2 -0
- package/dist/public/assets/{es2015-CE7VcoOH.js → es2015-eNVkKfFF.js} +1 -1
- package/dist/public/assets/{explorer-file-drop-CEbBlDEp.js → explorer-file-drop-CzyAqZgf.js} +1 -1
- package/dist/public/assets/{explorer-monaco-editor-Bgo9Y1cP.js → explorer-monaco-editor-ChJZBFy5.js} +1 -1
- package/dist/public/assets/explorer-tab-view-CiUPh4uK.js +2 -0
- package/dist/public/assets/explorer-tree-BA12VLz_.js +1 -0
- package/dist/public/assets/{explorer-view-BuTa_0Uq.js → explorer-view-Daxl93oM.js} +3 -3
- package/dist/public/assets/git-history-dialog-Dqj1p35g.js +1 -0
- package/dist/public/assets/index-CoY8DilQ.js +97 -0
- package/dist/public/assets/index-D14wLW4o.css +1 -0
- package/dist/public/assets/{label-C31qF5zZ.js → label-BCs5CZEs.js} +1 -1
- package/dist/public/assets/markdown-renderer-D2VcKU4g.js +10 -0
- package/dist/public/assets/{mcp-manager-C3K_62H2.js → mcp-manager-D1HmLT3t.js} +1 -1
- package/dist/public/assets/{minus-l6BdrAEk.js → minus-CgQcbBQT.js} +1 -1
- package/dist/public/assets/{model-list-controls-DwW8S18v.js → model-list-controls-rXmaDp2r.js} +1 -1
- package/dist/public/assets/onboarding-dialog-DSqBJyBa.js +1 -0
- package/dist/public/assets/{pill-tabs-CmvvHdKG.js → pill-tabs-DtdTmrg7.js} +1 -1
- package/dist/public/assets/progress-indicator-hJ74ac5W.js +1 -0
- package/dist/public/assets/project-coding-view-DP4qKePE.js +1 -0
- package/dist/public/assets/{project-danger-zone-view-D18k4pUF.js → project-danger-zone-view-CGxIenpr.js} +1 -1
- package/dist/public/assets/{project-env-vars-view-BWFqoaFD.js → project-env-vars-view-DKyQkh7h.js} +1 -1
- package/dist/public/assets/project-model-aliases-view-BewwJZAx.js +1 -0
- package/dist/public/assets/project-settings-view-CE4nAz5B.js +1 -0
- package/dist/public/assets/{project-tools-view-DT87KPjE.js → project-tools-view-CbDfst02.js} +1 -1
- package/dist/public/assets/providers-list-view-BtwccvX2.js +1 -0
- package/dist/public/assets/pull-request-dialog-nKYATjbm.js +1 -0
- package/dist/public/assets/pull-with-changes-dialog-zzoFzCv4.js +1 -0
- package/dist/public/assets/push-before-pr-dialog-DH91JHEC.js +1 -0
- package/dist/public/assets/remote-media-url-CyuN31H_.js +1 -0
- package/dist/public/assets/{scroll-area-BWc4OPsj.js → scroll-area-CGEZ1gAL.js} +1 -1
- package/dist/public/assets/{select-B6RizwDW.js → select-BR2pG61R.js} +1 -1
- package/dist/public/assets/settings-general-tabs-view-BWR0UX2P.js +2 -0
- package/dist/public/assets/settings-general-view-BhtrDmJH.js +1 -0
- package/dist/public/assets/{settings-list-D35rpAof.js → settings-list-Dgip9HpD.js} +1 -1
- package/dist/public/assets/settings-logs-view-CS29x4VT.js +5 -0
- package/dist/public/assets/settings-mcp-servers-view-B5ithpfh.js +5 -0
- package/dist/public/assets/settings-models-view-DS7nm54P.js +1 -0
- package/dist/public/assets/settings-plugins-view-avaUE36r.js +2 -0
- package/dist/public/assets/settings-providers-view-B39k1iRQ.js +2 -0
- package/dist/public/assets/settings-remote-machines-view-BXondQG_.js +1 -0
- package/dist/public/assets/settings-setup-view-I5MGUi_D.js +2 -0
- package/dist/public/assets/settings-skills-view-BKrUABbi.js +2 -0
- package/dist/public/assets/{settings-slack-view-DkclyaBc.js → settings-slack-view-B0p-96GC.js} +1 -1
- package/dist/public/assets/settings-slash-commands-view-DA1scWv1.js +1 -0
- package/dist/public/assets/{settings-statistics-view-B03ZZjEy.js → settings-statistics-view-B3g6BD7p.js} +1 -1
- package/dist/public/assets/settings-storage-view-BJvjhI4f.js +1 -0
- package/dist/public/assets/settings-subagents-view-BziLwvNq.js +2 -0
- package/dist/public/assets/settings-system-prompt-view-BqAk56cD.js +1 -0
- package/dist/public/assets/{settings-tab-bar-ajzyt79U.js → settings-tab-bar-DYzU_lmi.js} +1 -1
- package/dist/public/assets/settings-view-zjMs7jNe.js +2 -0
- package/dist/public/assets/{slug-utils-D2jhPz-o.js → slug-utils-CO6nui1C.js} +1 -1
- package/dist/public/assets/square-CtxvwmM2.js +1 -0
- package/dist/public/assets/store-W78TGOIO.js +8 -0
- package/dist/public/assets/{table-C3Hc0Gwy.js → table-CQMqIW_-.js} +1 -1
- package/dist/public/assets/task-utils-BZPVmvY4.js +1 -0
- package/dist/public/assets/tasks-view-wFf77AQX.js +1 -0
- package/dist/public/assets/{terminal-panel-DCKqScJu.js → terminal-panel-Bm_ZelN-.js} +2 -2
- package/dist/public/assets/{toggle-group-DqSxGqvP.js → toggle-group-CPmseZfb.js} +1 -1
- package/dist/public/assets/{tooltip-CJKJfu0l.js → tooltip-CqwCZ7wt.js} +1 -1
- package/dist/public/assets/{use-account-settings-query-AUeOqKvo.js → use-account-settings-query-C-zOdREq.js} +1 -1
- package/dist/public/assets/{use-active-dock-panel-instance-BvAhUd_V.js → use-active-dock-panel-instance-4Ss8lB9K.js} +1 -1
- package/dist/public/assets/use-browser-overlay-block-CO1pUEAZ.js +1 -0
- package/dist/public/assets/use-git-check-CumqGAvN.js +1 -0
- package/dist/public/assets/{use-installed-ai-files-iy_AB0dN.js → use-installed-ai-files-DQey9Zm3.js} +1 -1
- package/dist/public/assets/use-open-chat-dock-panel-DqfWJ8e8.js +1 -0
- package/dist/public/assets/use-projects-CizIH2Fa.js +2 -0
- package/dist/public/assets/utils-CqsIXqSC.js +1 -0
- package/dist/public/assets/web-BNWoiS4w.js +1 -0
- package/dist/public/assets/web-CGP-jEpi.js +1 -0
- package/dist/public/assets/web-CKC9gpFi.js +1 -0
- package/dist/public/assets/web-Dlo3GwCf.js +1 -0
- package/dist/public/fonts/schibsted-grotesk-latin-ext-wght-normal.woff2 +0 -0
- package/dist/public/fonts/schibsted-grotesk-latin-wght-normal.woff2 +0 -0
- package/dist/public/index.html +45 -45
- package/package.json +6 -6
- package/dist/node_modules/@libsql/darwin-x64/README.md +0 -3
- package/dist/public/assets/account-view-5q3pHEHY.js +0 -1
- package/dist/public/assets/ai-spinner-DHwhlk4j.js +0 -1
- package/dist/public/assets/api-BdebJfuN.js +0 -1
- package/dist/public/assets/api-COO2LfdU.js +0 -2
- package/dist/public/assets/browser-overlay-block-CiDtkfup.js +0 -1
- package/dist/public/assets/browser-tab-CVdYLmW5.js +0 -12
- package/dist/public/assets/button-Dp5XDZNR.js +0 -1
- package/dist/public/assets/chat-dock-context-ymLoO90X.js +0 -1
- package/dist/public/assets/checkbox-D-BV8-Z_.js +0 -1
- package/dist/public/assets/commit-dialog-CEbCFh1x.js +0 -1
- package/dist/public/assets/create-repo-dialog-B5IE3pUJ.js +0 -1
- package/dist/public/assets/dialog-pHPeIGaB.js +0 -1
- package/dist/public/assets/diff-view-Cy6nPdX-.js +0 -4
- package/dist/public/assets/dist-D5vgS4RP.js +0 -2
- package/dist/public/assets/explorer-tab-view-C-8QZO9S.js +0 -2
- package/dist/public/assets/explorer-tree-HrLSFgcI.js +0 -1
- package/dist/public/assets/git-history-dialog-ClfF5IOn.js +0 -1
- package/dist/public/assets/index-BBLA5zVt.css +0 -1
- package/dist/public/assets/index-CalVAwXj.js +0 -104
- package/dist/public/assets/markdown-renderer-DXRBG7uP.js +0 -10
- package/dist/public/assets/onboarding-dialog-BtLy0wjC.js +0 -1
- package/dist/public/assets/progress-indicator-4zQXqOqP.js +0 -1
- package/dist/public/assets/project-coding-view-CyJwnJes.js +0 -1
- package/dist/public/assets/project-model-aliases-view-D3tYNkkM.js +0 -1
- package/dist/public/assets/project-settings-view-0oN9vFvD.js +0 -1
- package/dist/public/assets/providers-list-view-DCnh0W-5.js +0 -1
- package/dist/public/assets/pull-request-dialog-BdJxYQwu.js +0 -1
- package/dist/public/assets/pull-with-changes-dialog-Do9x9neW.js +0 -1
- package/dist/public/assets/push-before-pr-dialog-C-9z2O0-.js +0 -1
- package/dist/public/assets/remote-media-url-B8OFqxOM.js +0 -1
- package/dist/public/assets/settings-general-tabs-view-Dcek-ysB.js +0 -2
- package/dist/public/assets/settings-general-view-DhA2N6G5.js +0 -1
- package/dist/public/assets/settings-logs-view-eEUTIMeb.js +0 -5
- package/dist/public/assets/settings-mcp-servers-view-_oeuVkUe.js +0 -5
- package/dist/public/assets/settings-models-view-DW-ZmVup.js +0 -1
- package/dist/public/assets/settings-plugins-view-DTooco_c.js +0 -2
- package/dist/public/assets/settings-providers-view-CEeJkhg9.js +0 -2
- package/dist/public/assets/settings-remote-machines-view--UB8GlCK.js +0 -1
- package/dist/public/assets/settings-setup-view-DFL6DlYS.js +0 -2
- package/dist/public/assets/settings-skills-view-xS569-Kb.js +0 -2
- package/dist/public/assets/settings-slash-commands-view-DrCiayfq.js +0 -1
- package/dist/public/assets/settings-storage-view-CQnaVOt_.js +0 -1
- package/dist/public/assets/settings-subagents-view-DIctUJcE.js +0 -2
- package/dist/public/assets/settings-system-prompt-view-BMDbrFRR.js +0 -1
- package/dist/public/assets/settings-view-8M6sbGiX.js +0 -2
- package/dist/public/assets/store-CxUwqrZ5.js +0 -8
- package/dist/public/assets/task-utils-WAei2PDi.js +0 -1
- package/dist/public/assets/tasks-view-DKyqgGdE.js +0 -1
- package/dist/public/assets/use-browser-overlay-block-z9imTmiZ.js +0 -1
- package/dist/public/assets/use-git-check-B_5Jak2s.js +0 -1
- package/dist/public/assets/use-open-chat-dock-panel-w3hc5Vxn.js +0 -1
- package/dist/public/assets/use-projects-BmhAMgxB.js +0 -2
- package/dist/public/assets/utils-mYB1USG6.js +0 -1
- package/dist/public/assets/web-C6Gm4nQ0.js +0 -1
- package/dist/public/assets/web-DFlyNg8o.js +0 -1
- package/dist/public/assets/web-DlEPs8Xe.js +0 -1
- package/dist/public/assets/web-Gx3xReQH.js +0 -1
- package/dist/public/backgrounds/arctic-tundra.avif +0 -0
- package/dist/public/backgrounds/autumn-leaves.avif +0 -0
- package/dist/public/backgrounds/coastal-cliff.avif +0 -0
- package/dist/public/backgrounds/floating-waterfall.avif +0 -0
- package/dist/public/backgrounds/forest-path.avif +0 -0
- package/dist/public/backgrounds/garden-path.avif +0 -0
- package/dist/public/backgrounds/glow-marsh.avif +0 -0
- package/dist/public/backgrounds/golden-wheat.avif +0 -0
- package/dist/public/backgrounds/moon-desert.avif +0 -0
- package/dist/public/backgrounds/night-pond.avif +0 -0
- package/dist/public/backgrounds/prairie-grassland.avif +0 -0
- package/dist/public/backgrounds/river-winding.avif +0 -0
- package/dist/public/backgrounds/salt-flat.avif +0 -0
- package/dist/public/backgrounds/salt-marsh.avif +0 -0
- package/dist/public/backgrounds/sandy-beach.avif +0 -0
- package/dist/public/backgrounds/snow-river.avif +0 -0
- package/dist/public/backgrounds/sunset-pond.avif +0 -0
- package/dist/public/fonts/plus-jakarta-sans-cyrillic-ext-wght-normal.woff2 +0 -0
- package/dist/public/fonts/plus-jakarta-sans-latin-ext-wght-normal.woff2 +0 -0
- package/dist/public/fonts/plus-jakarta-sans-latin-wght-normal.woff2 +0 -0
- package/dist/public/fonts/plus-jakarta-sans-vietnamese-wght-normal.woff2 +0 -0
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: email-me
|
|
3
|
+
description: Use when the user asks "email me".
|
|
4
|
+
version: 1.0.0
|
|
5
|
+
tools:
|
|
6
|
+
- email_me
|
|
7
|
+
---
|
|
8
|
+
# Email me
|
|
9
|
+
|
|
10
|
+
Sends an email to the signed-in Tarsk user.
|
|
11
|
+
|
|
12
|
+
- Put the information the user wants into `body`. Keep `subject` short.
|
|
13
|
+
- Call `email_me` once, then report its answer.
|
|
14
|
+
- When it reports that no one is signed in, ask the user to log in to Tarsk.
|
|
15
|
+
Do not call the tool again until the user is signed in.
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import assert from "node:assert/strict";
|
|
2
|
+
import test from "node:test";
|
|
3
|
+
|
|
4
|
+
import { execute } from "../email_me.js";
|
|
5
|
+
|
|
6
|
+
function contextReturning(result) {
|
|
7
|
+
const calls = [];
|
|
8
|
+
return {
|
|
9
|
+
calls,
|
|
10
|
+
email: {
|
|
11
|
+
async sendToSelf(message) {
|
|
12
|
+
calls.push(message);
|
|
13
|
+
return result;
|
|
14
|
+
},
|
|
15
|
+
},
|
|
16
|
+
};
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
void test("asks the user to log in to Tarsk when no account is signed in", async () => {
|
|
20
|
+
const context = contextReturning({ status: "not-signed-in" });
|
|
21
|
+
|
|
22
|
+
const result = await execute({ body: "The build is green." }, context);
|
|
23
|
+
|
|
24
|
+
assert.match(result.content[0].text, /log in to Tarsk/i);
|
|
25
|
+
assert.equal(context.calls.length, 1);
|
|
26
|
+
});
|
|
27
|
+
|
|
28
|
+
void test("sends the requested subject and body and names the address", async () => {
|
|
29
|
+
const context = contextReturning({ status: "sent", to: "owner@example.com" });
|
|
30
|
+
|
|
31
|
+
const result = await execute(
|
|
32
|
+
{ subject: "Status", body: "The build is green." },
|
|
33
|
+
context,
|
|
34
|
+
);
|
|
35
|
+
|
|
36
|
+
assert.deepEqual(context.calls, [{ subject: "Status", body: "The build is green." }]);
|
|
37
|
+
assert.match(result.content[0].text, /owner@example\.com/);
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
void test("defaults the subject when none is given", async () => {
|
|
41
|
+
const context = contextReturning({ status: "sent", to: "owner@example.com" });
|
|
42
|
+
|
|
43
|
+
await execute({ body: "The build is green." }, context);
|
|
44
|
+
|
|
45
|
+
assert.equal(context.calls[0].subject, "Message from Tarsk");
|
|
46
|
+
});
|
|
47
|
+
|
|
48
|
+
void test("reports a failed send with the service message", async () => {
|
|
49
|
+
const context = contextReturning({ status: "failed", message: "rate limited" });
|
|
50
|
+
|
|
51
|
+
const result = await execute({ body: "The build is green." }, context);
|
|
52
|
+
|
|
53
|
+
assert.match(result.content[0].text, /rate limited/);
|
|
54
|
+
assert.equal(context.calls.length, 1);
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
void test("refuses an empty body without sending", async () => {
|
|
58
|
+
const context = contextReturning({ status: "sent", to: "owner@example.com" });
|
|
59
|
+
|
|
60
|
+
const result = await execute({ body: " " }, context);
|
|
61
|
+
|
|
62
|
+
assert.match(result.content[0].text, /body/i);
|
|
63
|
+
assert.equal(context.calls.length, 0);
|
|
64
|
+
});
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
export const description =
|
|
2
|
+
'Send an email to the signed-in Tarsk user. Use when the user says "email me".';
|
|
3
|
+
|
|
4
|
+
export const parameters = {
|
|
5
|
+
type: "object",
|
|
6
|
+
properties: {
|
|
7
|
+
subject: { type: "string", description: "Short subject line for the email" },
|
|
8
|
+
body: {
|
|
9
|
+
type: "string",
|
|
10
|
+
description: "Email body: the information the user asked to include",
|
|
11
|
+
},
|
|
12
|
+
},
|
|
13
|
+
required: ["body"],
|
|
14
|
+
};
|
|
15
|
+
|
|
16
|
+
export async function execute(args, context) {
|
|
17
|
+
const subject = String(args.subject ?? "").trim() || "Message from Tarsk";
|
|
18
|
+
const body = String(args.body ?? "").trim();
|
|
19
|
+
if (!body) {
|
|
20
|
+
return {
|
|
21
|
+
content: [{ type: "text", text: "email_me: `body` is empty. Put the information to send in `body`." }],
|
|
22
|
+
};
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
const result = await context.email.sendToSelf({ subject, body });
|
|
26
|
+
|
|
27
|
+
if (result.status === "not-signed-in") {
|
|
28
|
+
return {
|
|
29
|
+
content: [
|
|
30
|
+
{
|
|
31
|
+
type: "text",
|
|
32
|
+
text: "No Tarsk account is signed in. Please log in to Tarsk and ask again.",
|
|
33
|
+
},
|
|
34
|
+
],
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
if (result.status === "failed") {
|
|
39
|
+
return {
|
|
40
|
+
content: [{ type: "text", text: `The email was not sent: ${result.message}` }],
|
|
41
|
+
};
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
return { content: [{ type: "text", text: `Email sent to ${result.to}.` }] };
|
|
45
|
+
}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: handoff
|
|
3
|
+
description: use if user asks for handoff
|
|
4
|
+
argument-hint: "Optional focus for the new chat"
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Handoff
|
|
8
|
+
|
|
9
|
+
When the user asks for a handoff or invokes this skill, create a new chat in the current project. Do not only write a summary or a temporary handoff file.
|
|
10
|
+
|
|
11
|
+
Prepare a concise, self-contained first message for the new chat. Include the original ask, decisions and constraints, relevant verified facts, completed work, current state, important paths or links, checks and their outcomes, and unfinished work. Keep details that the next agent needs; do not repeat artifacts that can be referenced by path or URL. Do not include secrets.
|
|
12
|
+
|
|
13
|
+
If the user provides a focus for the next chat, make it the new chat's primary task. Keep the prior task context that supports that focus, and distinguish facts from assumptions.
|
|
14
|
+
|
|
15
|
+
List the exact skill references that were used or referenced in this conversation under a "Skills carried forward" section in the first message. Use /name for project or global skills and //name for bundled skills. Do not invent references. The handoff operation copies the current chat's enabled and disabled skill settings and adds a link to the source chat; the listed references preserve explicit skill uses that are not part of those settings.
|
|
16
|
+
|
|
17
|
+
Choose a short title that describes the focus. Start the new chat by calling context.chat.startHandoff with the title, complete first-message prompt, and skill names. Use context.chat.normalizeTitle to normalize the title. Do not say the new chat started unless the call succeeds.
|
|
18
|
+
|
|
19
|
+
After success, give the user a markdown link to the new chat using the returned URL. If the launch fails after creating a chat, show the recovery link from the error and state that the first message did not start.
|
|
@@ -0,0 +1,372 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: tarsk-agent
|
|
3
|
+
description: >-
|
|
4
|
+
How to author, edit, and package Tarsk Tool skills: SKILL.md front matter,
|
|
5
|
+
scripts/{name}.js contract, Agent runtime (context), and export/resolution.
|
|
6
|
+
Use when creating or modifying a Tool skill, changing a tool
|
|
7
|
+
description/schema/execute, or asking what context.* APIs provide.
|
|
8
|
+
version: 2.0.1
|
|
9
|
+
when_to_use: >-
|
|
10
|
+
Before creating or editing any Skill under .agents/skills or cli/bundled-skills
|
|
11
|
+
that publishes tools, or when changing tool behavior, parameters, or descriptions.
|
|
12
|
+
Also when a tool repeatedly fails or a goal burned excessive turns/tokens due to
|
|
13
|
+
tool design (noisy output, missing select, serial multi-hop).
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
# Agent runtime & Tool skills (`tarsk-agent`)
|
|
17
|
+
|
|
18
|
+
Read this before creating or editing a Tool skill. Tool skill scripts must not
|
|
19
|
+
import modules (no `import` / `require`). They receive a `context` object (the
|
|
20
|
+
Agent runtime) as the second argument to `execute`. Project scripts that import
|
|
21
|
+
are rejected at load; use only `context.*`.
|
|
22
|
+
|
|
23
|
+
## When to update a Tool skill
|
|
24
|
+
|
|
25
|
+
Edit the project Tool skill (usually `.agents/skills/tarsk-<area>/`) when:
|
|
26
|
+
|
|
27
|
+
- The same tool call fails repeatedly for a fixable reason (bad defaults, weak
|
|
28
|
+
validation message, schema that invites wrong args, brittle formatting).
|
|
29
|
+
- Reaching the user's goal took excessive turns or tokens because of tool design
|
|
30
|
+
(dumping huge results instead of `select` / truncation, forcing grep→read
|
|
31
|
+
loops that belong in `run_js`, descriptions that send the model down a dead path).
|
|
32
|
+
- A description or parameter shape no longer matches how the tool should be used.
|
|
33
|
+
|
|
34
|
+
Prefer a small change to `description`, `parameters`, or `execute` over teaching
|
|
35
|
+
the model a one-off workaround in chat. After edit, the next tool load picks it
|
|
36
|
+
up. Do not invent host APIs — use `context.*` below.
|
|
37
|
+
|
|
38
|
+
## Split of responsibility
|
|
39
|
+
|
|
40
|
+
| Lives in | Responsibility |
|
|
41
|
+
| ----------------------- | ----------------------------------------------------------------------------------------------------------------------------------------- |
|
|
42
|
+
| **Tool skill scripts** | Tool logic: description, parameters, orchestration, formatting, policy text the agent may edit |
|
|
43
|
+
| **CLI / Agent runtime** | Security and light host: cwd/path checks, permission gates, seatbelt, fetch allowlist, DB/network clients, truncate helpers, job registry |
|
|
44
|
+
|
|
45
|
+
Prefer implementing behavior in `scripts/{name}.js` using `context` primitives.
|
|
46
|
+
Heavy engines (edit matching, browser, shell spawn) stay behind dedicated
|
|
47
|
+
`context.*` host APIs — never import Node modules or `cli/src`.
|
|
48
|
+
|
|
49
|
+
### What you can change
|
|
50
|
+
|
|
51
|
+
| Goal | How |
|
|
52
|
+
| ------------------------------------ | ------------------------------------------------------------------------ |
|
|
53
|
+
| Change Tool behavior the agent owns | Edit `execute` / `description` / `parameters` in the Skill script |
|
|
54
|
+
| Need filesystem/shell/network safely | Call the matching **secure or light** `context.*` API (documented below) |
|
|
55
|
+
|
|
56
|
+
## Package layout
|
|
57
|
+
|
|
58
|
+
A Tool skill is a normal Skill whose front matter lists `tools`:
|
|
59
|
+
|
|
60
|
+
```text
|
|
61
|
+
.agents/skills/my-notes/ # project copy (edit here)
|
|
62
|
+
SKILL.md
|
|
63
|
+
scripts/
|
|
64
|
+
notes.js # one file per name in tools:
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
Tarsk-shipped defaults live under `cli/bundled-skills/tarsk-*`. To change one, **export**
|
|
68
|
+
it into the Project’s `.agents/skills` (`tarsk-improve`’s `ensure-exported.ts`) and
|
|
69
|
+
**edit the project copy** under `.agents/skills/…` so your changes stick. Chat load
|
|
70
|
+
never creates copies — it only **prunes** project copies that still match bundled — so
|
|
71
|
+
export before editing. The `tarsk-` prefix is a shipping convention for export only;
|
|
72
|
+
any Skill with a `tools` array publishes Tools.
|
|
73
|
+
|
|
74
|
+
### Front matter
|
|
75
|
+
|
|
76
|
+
```yaml
|
|
77
|
+
---
|
|
78
|
+
name: my-notes # must match the directory name
|
|
79
|
+
description: Short trigger text for humans and skill discovery
|
|
80
|
+
version: 1.0.0 # semver; used by export
|
|
81
|
+
tools:
|
|
82
|
+
- notes # model-facing Tool name(s)
|
|
83
|
+
# deferred-tools: # optional; subset of tools → behind tool_search
|
|
84
|
+
# - notes
|
|
85
|
+
---
|
|
86
|
+
```
|
|
87
|
+
|
|
88
|
+
- `tools: [name, …]` — required for a Tool skill. Each name needs `scripts/{name}.js`.
|
|
89
|
+
Add the name here **before** creating the script: the write guard validates only
|
|
90
|
+
declared Tool scripts, so a file it does not know is an ordinary helper script
|
|
91
|
+
(it may import modules; it has no `description`/`parameters`/`execute` contract).
|
|
92
|
+
- `deferred-tools` — optional subset of `tools`; omitted means all eager. Prefer deferring
|
|
93
|
+
rare tools (browser, jobs, images, web, observations, …) so schemas stay out of every
|
|
94
|
+
request; keep the coding core eager.
|
|
95
|
+
- A deferred tool is reachable only through `tool_search`, which matches a tool's name and
|
|
96
|
+
`description` — never its `parameters`. Name every capability a model might search for
|
|
97
|
+
(for example `screenshot`, `capture`) in the script's `description`, or keyword search
|
|
98
|
+
cannot find the tool and the model concludes the capability does not exist.
|
|
99
|
+
- Host injects a shared `select` parameter for `read` and `bash` at load time — do not
|
|
100
|
+
duplicate that schema in the Skill script.
|
|
101
|
+
- Not the same as `allowed-tools` (that only restricts which existing Tools a Skill may use).
|
|
102
|
+
- Directory name must equal front matter `name`.
|
|
103
|
+
|
|
104
|
+
### Script contract
|
|
105
|
+
|
|
106
|
+
Each `scripts/{name}.js` (or `.ts`) exports:
|
|
107
|
+
|
|
108
|
+
- `description` — string shown to the model for this Tool
|
|
109
|
+
- `parameters` — JSON Schema object for arguments
|
|
110
|
+
- `execute(args, context, options?)` — returns
|
|
111
|
+
`{ content: [{ type: "text", text }], details? }`
|
|
112
|
+
(throw or return an error text on failure)
|
|
113
|
+
|
|
114
|
+
The Tool **name** comes from the `tools` array, not from inside the file.
|
|
115
|
+
A script not listed in `tools` is an ordinary skill script (`execute_skill_script`),
|
|
116
|
+
not a model Tool.
|
|
117
|
+
|
|
118
|
+
`options` (third argument): `{ signal?, onUpdate? }` for abort and streaming
|
|
119
|
+
progress.
|
|
120
|
+
|
|
121
|
+
## Where files live (export & resolution)
|
|
122
|
+
|
|
123
|
+
1. **Resolution for a run:** Project `.agents/skills/<name>` if present, else
|
|
124
|
+
bundled `cli/bundled-skills/<name>`. Load never writes. Script imports are
|
|
125
|
+
cache-busted by mtime so edits apply on the next tool load. Project scripts
|
|
126
|
+
must not `import`/`require` modules (rejected at load).
|
|
127
|
+
2. **Export (deliberate):** Run `tarsk-improve`’s `ensure-exported.ts` to copy
|
|
128
|
+
bundled Skills whose names start with `tarsk-` into `.agents/skills`:
|
|
129
|
+
- missing project copy → copy
|
|
130
|
+
- same `version` → leave
|
|
131
|
+
- bundled **major** > project major → overwrite
|
|
132
|
+
- otherwise (project ahead, or only minor/patch ahead) → leave project copy
|
|
133
|
+
Chat load never copies. It only **prunes** a project copy that is byte-identical
|
|
134
|
+
to bundled, so untouched packages never persist in the repo.
|
|
135
|
+
3. **Where edits land:** in the Tarsk checkout the built-ins under
|
|
136
|
+
`cli/bundled-skills/tarsk-*` _are_ this repo's own files, so
|
|
137
|
+
`ensure-exported.ts` copies nothing and `.agents/skills/tarsk-*` stays absent —
|
|
138
|
+
edit `cli/bundled-skills/tarsk-*` directly. In any other repo do not hand-edit
|
|
139
|
+
`cli/bundled-skills/`; the project export is the edit surface.
|
|
140
|
+
4. Bump `version` in front matter when you intentionally publish a new Skill
|
|
141
|
+
revision. A major bump on the bundled side can overwrite local copies.
|
|
142
|
+
|
|
143
|
+
## Enable / disable
|
|
144
|
+
|
|
145
|
+
- Tool skills are **enabled by default**.
|
|
146
|
+
- Disabling the Skill (thread skill settings) hides every Tool in its `tools` array.
|
|
147
|
+
- Project `disabledTools` still hides individual Tool names.
|
|
148
|
+
- Disabling `tarsk-agent` does not remove Tools; the CLI always injects `context`.
|
|
149
|
+
|
|
150
|
+
## `context` API
|
|
151
|
+
|
|
152
|
+
### Identifiers
|
|
153
|
+
|
|
154
|
+
| Field | Meaning |
|
|
155
|
+
| ---------------- | --------------------------------- |
|
|
156
|
+
| `cwd` | Working directory for the run |
|
|
157
|
+
| `projectId` | Current Project id (may be empty) |
|
|
158
|
+
| `threadId` | Current Thread id |
|
|
159
|
+
| `conversationId` | Current Conversation id |
|
|
160
|
+
| `messageId` | Optional message id |
|
|
161
|
+
| `threadPath` | Optional Thread checkout path |
|
|
162
|
+
|
|
163
|
+
### `context.notes`
|
|
164
|
+
|
|
165
|
+
Project-scoped durable notes:
|
|
166
|
+
|
|
167
|
+
- `list()` — note metadata
|
|
168
|
+
- `read(name, offset?)` — paged content, or `null` if missing
|
|
169
|
+
- `write(name, content)` — replace; empty content clears; metadata or `null` when cleared
|
|
170
|
+
- `append(name, content)` — append a record
|
|
171
|
+
- `search(query)` — name and content excerpts
|
|
172
|
+
|
|
173
|
+
### `context.chat`
|
|
174
|
+
|
|
175
|
+
- `titleMaxLength` — max characters for a chat title
|
|
176
|
+
- `normalizeTitle(title)` — normalize a model-supplied title for storage
|
|
177
|
+
|
|
178
|
+
### `context.mcp`
|
|
179
|
+
|
|
180
|
+
```js
|
|
181
|
+
await context.mcp.connectRemoteServer(
|
|
182
|
+
{ serverName, url, transport: "streamableHttp" | "sse", useOAuth },
|
|
183
|
+
options,
|
|
184
|
+
);
|
|
185
|
+
// → { serverName, state, tools, authenticated, error? }
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
Saves and discovers a remote MCP server for the current project. The active run's tool set stays fixed; discovered MCP tools are available on the next message
|
|
189
|
+
in the same conversation. Use the deferred `connect_mcp` Skill instead of calling
|
|
190
|
+
this host API directly from user-facing replies. Never ask for bearer tokens.
|
|
191
|
+
|
|
192
|
+
### `context.web`
|
|
193
|
+
|
|
194
|
+
```js
|
|
195
|
+
await context.web.search({ query, numResults, type, includeDomains, excludeDomains, signal });
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
### `context.email`
|
|
199
|
+
|
|
200
|
+
```js
|
|
201
|
+
await context.email.sendToSelf({ subject, body });
|
|
202
|
+
// → { status: "sent", to } | { status: "not-signed-in" } | { status: "failed", message }
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
Sends an email to the signed-in Tarsk account (the auth service resolves the
|
|
206
|
+
recipient from the sign-in token, so the mail can only reach that user's own
|
|
207
|
+
address). The Skill formats every reply, including the signed-out "log in to
|
|
208
|
+
Tarsk" copy.
|
|
209
|
+
|
|
210
|
+
### `context.util`
|
|
211
|
+
|
|
212
|
+
```js
|
|
213
|
+
context.util.maxBytes;
|
|
214
|
+
context.util.formatSize(bytes);
|
|
215
|
+
context.util.truncateHead(text, { maxLines, maxBytes });
|
|
216
|
+
context.util.compressFindPaths(paths); // { text, applied, banner }
|
|
217
|
+
context.util.compressGrepContent(lines); // { text, applied, banner }
|
|
218
|
+
context.util.compressGrepCount(lines);
|
|
219
|
+
context.util.compressGrepFiles(lines);
|
|
220
|
+
context.util.compressUnifiedDiffPreservingFootnotes(text); // { text, applied }
|
|
221
|
+
await context.util.withAbort(signal, async (isAborted) => {
|
|
222
|
+
/* … */
|
|
223
|
+
});
|
|
224
|
+
```
|
|
225
|
+
|
|
226
|
+
### `context.history`
|
|
227
|
+
|
|
228
|
+
```js
|
|
229
|
+
context.history.available
|
|
230
|
+
await context.history.search({ query, allConversations?, limit? })
|
|
231
|
+
await context.history.read({ entryId, allConversations?, offset? })
|
|
232
|
+
```
|
|
233
|
+
|
|
234
|
+
### `context.jobs`
|
|
235
|
+
|
|
236
|
+
Owner-scoped background jobs (bash `run_in_background`). Kill is a privileged host op.
|
|
237
|
+
|
|
238
|
+
```js
|
|
239
|
+
context.jobs.available
|
|
240
|
+
context.jobs.list()
|
|
241
|
+
context.jobs.readOutput(jobId, { offsetLines?, limitLines? })
|
|
242
|
+
context.jobs.kill(jobId) // { ok, outcome, status, exitCode } | { ok: false }
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
### `context.todos`
|
|
246
|
+
|
|
247
|
+
Thread-scoped todos and progress.txt append:
|
|
248
|
+
|
|
249
|
+
```js
|
|
250
|
+
await context.todos.list()
|
|
251
|
+
await context.todos.add(descriptions, assignedTo?)
|
|
252
|
+
await context.todos.update(ids, { status?, assignedTo?, passes? })
|
|
253
|
+
await context.todos.remove(ids)
|
|
254
|
+
await context.todos.appendLearnings(text)
|
|
255
|
+
```
|
|
256
|
+
|
|
257
|
+
### `context.fs`
|
|
258
|
+
|
|
259
|
+
Secure filesystem (cwd containment). Grow this as more file Tools migrate.
|
|
260
|
+
|
|
261
|
+
```js
|
|
262
|
+
await context.fs.writeText(path, content, { signal? })
|
|
263
|
+
// → { path, absolutePath, previousBytes, nextBytes, supersession }
|
|
264
|
+
await context.fs.glob(pattern, { path?, limit?, signal? })
|
|
265
|
+
// → { paths, limit, resultLimitReached }
|
|
266
|
+
await context.fs.applyEdit(args, { signal? }) // structured; Skill formats copy
|
|
267
|
+
await context.fs.read(args, { signal?, onUpdate?, toolCallId? })
|
|
268
|
+
// → structured (text/directory/image/unchanged/raw); Skill formats copy
|
|
269
|
+
await context.fs.grep(args, { signal? })
|
|
270
|
+
// → structured rows; Skill formats banners / empty tips / pagination
|
|
271
|
+
```
|
|
272
|
+
|
|
273
|
+
### `context.shell` / `context.ask` / `context.web.fetch`
|
|
274
|
+
|
|
275
|
+
```js
|
|
276
|
+
await context.shell.run(args, options)
|
|
277
|
+
// → structured (completed | background | preformatted); Skill formats notices
|
|
278
|
+
context.shell.resolveExit({
|
|
279
|
+
exitCode, executionCommand, outputText, fullOutput, threadId?,
|
|
280
|
+
}) // soft-success / soft-fail classification (policy stays in host)
|
|
281
|
+
context.ask.normalize(args); // coerce legacy ask_user shapes
|
|
282
|
+
await context.ask.wait(questions, options); // blocking gate + credentials; needs toolCallId
|
|
283
|
+
await context.web.fetch(args, options); // fetch (allowlist gate)
|
|
284
|
+
```
|
|
285
|
+
|
|
286
|
+
### `context.observations` (DB only)
|
|
287
|
+
|
|
288
|
+
```js
|
|
289
|
+
context.observations.limits;
|
|
290
|
+
await context.observations.resolveId(rawId);
|
|
291
|
+
await context.observations.fetch(id); // { id, content, toolName } | null
|
|
292
|
+
await context.observations.recordRetrieved(bytes);
|
|
293
|
+
```
|
|
294
|
+
|
|
295
|
+
Paging and model copy live in the `get_observation` Skill.
|
|
296
|
+
|
|
297
|
+
### Other host executors
|
|
298
|
+
|
|
299
|
+
```js
|
|
300
|
+
await context.images.searchAndSave(args, options); // structured; Skill formats
|
|
301
|
+
await context.images.generate(args, options); // structured; Skill formats
|
|
302
|
+
await context.projects.query(args); // structured; Skill formats
|
|
303
|
+
await context.projects.launch(args); // structured; Skill formats
|
|
304
|
+
await context.tasks.query(args); // structured; Skill formats
|
|
305
|
+
await context.browser.run(args, options); // structured payload; Skill formats
|
|
306
|
+
await context.js.run(args, options); // structured ok / trivial_read; Skill formats
|
|
307
|
+
await context.skillsCatalog.read(args); // structured; Skill formats
|
|
308
|
+
await context.skillsCatalog.executeScript(args, options); // structured; Skill formats
|
|
309
|
+
await context.skillsCatalog.readReference(args); // structured; Skill formats
|
|
310
|
+
```
|
|
311
|
+
|
|
312
|
+
Every shipped Tool skill uses a dedicated API above (or pure script logic).
|
|
313
|
+
`propose_branch` is Slack plan-chat only.
|
|
314
|
+
|
|
315
|
+
## Worked example (new Tool skill)
|
|
316
|
+
|
|
317
|
+
`.agents/skills/echo-tool/SKILL.md`:
|
|
318
|
+
|
|
319
|
+
```yaml
|
|
320
|
+
---
|
|
321
|
+
name: echo-tool
|
|
322
|
+
description: Echoes a message back via a small custom Tool.
|
|
323
|
+
version: 1.0.0
|
|
324
|
+
tools:
|
|
325
|
+
- echo_message
|
|
326
|
+
---
|
|
327
|
+
# Echo
|
|
328
|
+
|
|
329
|
+
Publishes `echo_message`. See `tarsk-agent` for the runtime contract.
|
|
330
|
+
```
|
|
331
|
+
|
|
332
|
+
`.agents/skills/echo-tool/scripts/echo_message.js`:
|
|
333
|
+
|
|
334
|
+
```js
|
|
335
|
+
export const description =
|
|
336
|
+
"Echo a short message back to the conversation. Use for smoke-testing Tool skills.";
|
|
337
|
+
|
|
338
|
+
export const parameters = {
|
|
339
|
+
type: "object",
|
|
340
|
+
properties: {
|
|
341
|
+
message: { type: "string", description: "Text to echo" },
|
|
342
|
+
},
|
|
343
|
+
required: ["message"],
|
|
344
|
+
};
|
|
345
|
+
|
|
346
|
+
export async function execute(args, context) {
|
|
347
|
+
const text = String(args.message ?? "");
|
|
348
|
+
return {
|
|
349
|
+
content: [{ type: "text", text: `echo (${context.cwd}): ${text}` }],
|
|
350
|
+
details: undefined,
|
|
351
|
+
};
|
|
352
|
+
}
|
|
353
|
+
```
|
|
354
|
+
|
|
355
|
+
### Wrapping a host Tool (change description / formatting)
|
|
356
|
+
|
|
357
|
+
`.agents/skills/tarsk-bash/scripts/bash.js` (project override after export):
|
|
358
|
+
|
|
359
|
+
```js
|
|
360
|
+
export const description = "/* your revised guidance for the model */";
|
|
361
|
+
|
|
362
|
+
export const parameters = {/* keep or tighten the JSON Schema */};
|
|
363
|
+
|
|
364
|
+
export async function execute(args, context, options) {
|
|
365
|
+
const structured = await context.shell.run(args, options);
|
|
366
|
+
// Format completed / background / preformatted + resolveExit — see bundled bash.js
|
|
367
|
+
// …
|
|
368
|
+
}
|
|
369
|
+
```
|
|
370
|
+
|
|
371
|
+
After editing a project Tool skill, the next run reload picks it up (no restart
|
|
372
|
+
required beyond the next tool load for that chat).
|
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: tarsk-ask-user
|
|
3
|
+
description: >-
|
|
4
|
+
Tarsk Tool skill publishing: ask_user.
|
|
5
|
+
version: 2.0.0
|
|
6
|
+
tools:
|
|
7
|
+
- ask_user
|
|
8
|
+
disable-model-invocation: true
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
# tarsk-ask-user
|
|
12
|
+
|
|
13
|
+
Publishes: ask_user.
|
|
14
|
+
|
|
15
|
+
Question policy text and answer formatting live in `scripts/ask_user.js`.
|
|
16
|
+
|
|
17
|
+
Host (`context.ask`): `normalize` (legacy arg coercion) and `wait` (blocking
|
|
18
|
+
gate + credential store). Secrets never return to the Skill.
|
|
@@ -0,0 +1,101 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* ask_user — question policy + result formatting in the Skill.
|
|
3
|
+
* Host: context.ask.normalize / wait (blocking gate + credential store).
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
export const description =
|
|
7
|
+
"Ask the user for clarification, confirmation, or a decision. Pass `questions` (all answered in one call). Options: `{ label, description }`; recommended first with `(Recommended)`; no `Other` (UI provides custom). Use `multiple: true` when needed. For HTTPS git auth failures, use `credential: { host }` (never ask for a token in chat or put one in a command).";
|
|
8
|
+
|
|
9
|
+
export const parameters = {
|
|
10
|
+
type: "object",
|
|
11
|
+
properties: {
|
|
12
|
+
questions: {
|
|
13
|
+
minItems: 1,
|
|
14
|
+
type: "array",
|
|
15
|
+
items: {
|
|
16
|
+
type: "object",
|
|
17
|
+
required: ["question"],
|
|
18
|
+
properties: {
|
|
19
|
+
question: {
|
|
20
|
+
description:
|
|
21
|
+
"Clear, specific question to clarify requirements, confirm decisions, or gather preferences.",
|
|
22
|
+
type: "string",
|
|
23
|
+
},
|
|
24
|
+
header: {
|
|
25
|
+
description: "Optional short UI title above the question.",
|
|
26
|
+
type: "string",
|
|
27
|
+
},
|
|
28
|
+
options: {
|
|
29
|
+
type: "array",
|
|
30
|
+
items: {
|
|
31
|
+
type: "object",
|
|
32
|
+
required: ["label", "description"],
|
|
33
|
+
properties: {
|
|
34
|
+
label: { type: "string" },
|
|
35
|
+
description: {
|
|
36
|
+
description: "Secondary text for this option; use an empty string when none.",
|
|
37
|
+
type: "string",
|
|
38
|
+
},
|
|
39
|
+
},
|
|
40
|
+
},
|
|
41
|
+
},
|
|
42
|
+
multiple: {
|
|
43
|
+
description: "Allow multiple selections. Defaults to false.",
|
|
44
|
+
type: "boolean",
|
|
45
|
+
},
|
|
46
|
+
credential: {
|
|
47
|
+
description:
|
|
48
|
+
"Collect a Git username and token for this host in a secure dialog. The secret is stored globally for all projects and never shown to you.",
|
|
49
|
+
type: "object",
|
|
50
|
+
required: ["host"],
|
|
51
|
+
properties: {
|
|
52
|
+
host: {
|
|
53
|
+
description: 'HTTPS Git host that needs a credential, e.g. "github.com".',
|
|
54
|
+
type: "string",
|
|
55
|
+
},
|
|
56
|
+
},
|
|
57
|
+
},
|
|
58
|
+
},
|
|
59
|
+
},
|
|
60
|
+
},
|
|
61
|
+
question: {
|
|
62
|
+
description: "Legacy single-question form. Prefer `questions`.",
|
|
63
|
+
type: "string",
|
|
64
|
+
},
|
|
65
|
+
options: {
|
|
66
|
+
description: "Legacy string choices for the single question.",
|
|
67
|
+
type: "array",
|
|
68
|
+
items: { type: "string" },
|
|
69
|
+
},
|
|
70
|
+
context: {
|
|
71
|
+
description: "Legacy brief context for the single question.",
|
|
72
|
+
type: "string",
|
|
73
|
+
},
|
|
74
|
+
},
|
|
75
|
+
};
|
|
76
|
+
|
|
77
|
+
function answerText(answer) {
|
|
78
|
+
return Array.isArray(answer) ? answer.join(", ") : answer;
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
/** Format Q→A for the model; edit this to change turn shape / token use. */
|
|
82
|
+
function formatAskUserResult(questions, answers) {
|
|
83
|
+
const lines = questions.map(function mapQuestion(question, i) {
|
|
84
|
+
const answer = answers[i] ?? "";
|
|
85
|
+
if (i === 0 && questions.length === 1) {
|
|
86
|
+
return answerText(answer);
|
|
87
|
+
}
|
|
88
|
+
return `${i + 1}. ${question.question}\n Answer: ${answerText(answer)}`;
|
|
89
|
+
});
|
|
90
|
+
return lines.join("\n");
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
/** @param {Record<string, unknown>} args @param {import("../../../../src/tools/agent-runtime/types.js").AgentRuntime} context @param {{ signal?: AbortSignal, toolCallId?: string }} [options] */
|
|
94
|
+
export async function execute(args, context, options) {
|
|
95
|
+
const questions = context.ask.normalize(args);
|
|
96
|
+
const answers = await context.ask.wait(questions, options);
|
|
97
|
+
return {
|
|
98
|
+
content: [{ type: "text", text: formatAskUserResult(questions, answers) }],
|
|
99
|
+
details: undefined,
|
|
100
|
+
};
|
|
101
|
+
}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: tarsk-bash
|
|
3
|
+
description: >-
|
|
4
|
+
Tarsk Tool skill publishing: bash.
|
|
5
|
+
version: 3.1.2
|
|
6
|
+
tools:
|
|
7
|
+
- bash
|
|
8
|
+
disable-model-invocation: true
|
|
9
|
+
---
|
|
10
|
+
|
|
11
|
+
# tarsk-bash
|
|
12
|
+
|
|
13
|
+
Publishes: bash.
|
|
14
|
+
|
|
15
|
+
Truncation / background / ignored-flag copy in `scripts/bash.js`. Host
|
|
16
|
+
`context.shell.run` returns structured capture (permissions + seatbelt + exec +
|
|
17
|
+
prepare). Exit soft-success classification via `context.shell.resolveExit`.
|