@cursor/bdk 0.2.14 → 0.2.16
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/AGENTS.md +51 -52
- package/README.md +1 -1
- package/dist/bin/agent-sdk.js +0 -0
- package/dist/bin/agent-serve.js +41 -3
- package/dist/channels/github/index.d.ts +1 -1
- package/dist/channels/github/index.d.ts.map +1 -1
- package/dist/channels/github/index.js +1 -1
- package/dist/channels/slack/attachments.d.ts +2 -0
- package/dist/channels/slack/attachments.d.ts.map +1 -1
- package/dist/channels/slack/attachments.js +17 -5
- package/dist/channels/slack/channel-watch.d.ts +4 -2
- package/dist/channels/slack/channel-watch.d.ts.map +1 -1
- package/dist/channels/slack/channel-watch.js +4 -2
- package/dist/channels/slack/slack-channel.d.ts.map +1 -1
- package/dist/channels/slack/slack-channel.js +4 -2
- package/dist/channels/slack/types.d.ts +6 -4
- package/dist/channels/slack/types.d.ts.map +1 -1
- package/dist/connections.d.ts +29 -0
- package/dist/connections.d.ts.map +1 -1
- package/dist/connections.js +54 -0
- package/dist/docs/404.html +2 -2
- package/dist/docs/assets/{app.BN3sgOOo.js → app.BSrZkTHD.js} +4 -4
- package/dist/docs/assets/{building-with-agents.md.Df87rAe1.js → building-with-agents.md.Bi9CQ-bR.js} +3 -3
- package/dist/docs/assets/{building-with-agents.md.Df87rAe1.lean.js → building-with-agents.md.Bi9CQ-bR.lean.js} +1 -1
- package/dist/docs/assets/chunks/@localSearchIndexroot.JUnN1Be1.js +1 -0
- package/dist/docs/assets/chunks/{VPLocalSearchBox.CbA00dML.js → VPLocalSearchBox.BxmgcwIX.js} +1 -1
- package/dist/docs/assets/chunks/{arc.Byug8CZM.js → arc.CAid9y9R.js} +1 -1
- package/dist/docs/assets/chunks/{architectureDiagram-Q4EWVU46.D1_qmnQy.js → architectureDiagram-Q4EWVU46.kLxg-1A5.js} +1 -1
- package/dist/docs/assets/chunks/{baseUniq.Dj-Nurf-.js → baseUniq.BWvpjFlO.js} +1 -1
- package/dist/docs/assets/chunks/{blockDiagram-DXYQGD6D.BZwq3EIg.js → blockDiagram-DXYQGD6D.DyjX8R7M.js} +1 -1
- package/dist/docs/assets/chunks/{c4Diagram-AHTNJAMY.dx75urO7.js → c4Diagram-AHTNJAMY.DBdWlnqr.js} +1 -1
- package/dist/docs/assets/chunks/channel.CWc3NN9g.js +1 -0
- package/dist/docs/assets/chunks/{chunk-4BX2VUAB.CIoddsDQ.js → chunk-4BX2VUAB.T5enPS2D.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-4TB4RGXK.O3VsVBES.js → chunk-4TB4RGXK.D6zswRAS.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-55IACEB6.WNNWh0Pe.js → chunk-55IACEB6.Bh05N-a3.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-EDXVE4YY.BKVQwEME.js → chunk-EDXVE4YY.DZv_O-d9.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-FMBD7UC4.Cv5iBz7A.js → chunk-FMBD7UC4.BY53CZaL.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-OYMX7WX6.wCDCToee.js → chunk-OYMX7WX6.CO5lI2PE.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-QZHKN3VN.D3IGXhXA.js → chunk-QZHKN3VN.DMfpW0s4.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-YZCP3GAM.CAPPh-E7.js → chunk-YZCP3GAM.COPT56Nr.js} +1 -1
- package/dist/docs/assets/chunks/classDiagram-6PBFFD2Q.D5a745iS.js +1 -0
- package/dist/docs/assets/chunks/classDiagram-v2-HSJHXN6E.D5a745iS.js +1 -0
- package/dist/docs/assets/chunks/clone.CCGVqN_B.js +1 -0
- package/dist/docs/assets/chunks/{cose-bilkent-S5V4N54A.BQCFH3M5.js → cose-bilkent-S5V4N54A.BJSj7zzd.js} +1 -1
- package/dist/docs/assets/chunks/{dagre-KV5264BT.lHmdrh7L.js → dagre-KV5264BT.DDv7IQZT.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-5BDNPKRD.EtSPnHgD.js → diagram-5BDNPKRD.BUoE9HFH.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-G4DWMVQ6.DCyUnQT8.js → diagram-G4DWMVQ6.BF3JtrnJ.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-MMDJMWI5._E0Qqblb.js → diagram-MMDJMWI5.BvuCWc4e.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-TYMM5635.BDj4oyy_.js → diagram-TYMM5635._EqUGqFN.js} +1 -1
- package/dist/docs/assets/chunks/{erDiagram-SMLLAGMA.CrvnO6a3.js → erDiagram-SMLLAGMA.DxNvSdzj.js} +1 -1
- package/dist/docs/assets/chunks/{flowDiagram-DWJPFMVM.DIhYc-2F.js → flowDiagram-DWJPFMVM.DVtRP546.js} +1 -1
- package/dist/docs/assets/chunks/{ganttDiagram-T4ZO3ILL.hFqm_vio.js → ganttDiagram-T4ZO3ILL.Bn9vb7xI.js} +1 -1
- package/dist/docs/assets/chunks/{gitGraphDiagram-UUTBAWPF.N3GDaVDD.js → gitGraphDiagram-UUTBAWPF.45r6n737.js} +1 -1
- package/dist/docs/assets/chunks/{graph.DK28rMBx.js → graph.BOkX3Ws_.js} +1 -1
- package/dist/docs/assets/chunks/{infoDiagram-42DDH7IO.DHmE6W9M.js → infoDiagram-42DDH7IO.DyBCcxOm.js} +1 -1
- package/dist/docs/assets/chunks/{ishikawaDiagram-UXIWVN3A.ByUJuOYm.js → ishikawaDiagram-UXIWVN3A.kg0ywDlx.js} +1 -1
- package/dist/docs/assets/chunks/{journeyDiagram-VCZTEJTY.BIUChFMh.js → journeyDiagram-VCZTEJTY.BUfrLnXA.js} +1 -1
- package/dist/docs/assets/chunks/{kanban-definition-6JOO6SKY.CNgFXwo-.js → kanban-definition-6JOO6SKY.Bn7X35b2.js} +1 -1
- package/dist/docs/assets/chunks/{layout.BDnwE4ET.js → layout.B0QW6d8M.js} +1 -1
- package/dist/docs/assets/chunks/{linear.DmrYLXFs.js → linear.C59eCF0D.js} +1 -1
- package/dist/docs/assets/chunks/{min.BbYcWakN.js → min.BnDl0p08.js} +1 -1
- package/dist/docs/assets/chunks/{mindmap-definition-QFDTVHPH.C9x-klkv.js → mindmap-definition-QFDTVHPH.u2HYLooo.js} +1 -1
- package/dist/docs/assets/chunks/{pieDiagram-DEJITSTG.iufpEbi0.js → pieDiagram-DEJITSTG.CbnIrr9l.js} +1 -1
- package/dist/docs/assets/chunks/{quadrantDiagram-34T5L4WZ.DdoXbWL9.js → quadrantDiagram-34T5L4WZ.D2zWIixq.js} +1 -1
- package/dist/docs/assets/chunks/{requirementDiagram-MS252O5E.XL1-_pNk.js → requirementDiagram-MS252O5E.DvOFa3oO.js} +1 -1
- package/dist/docs/assets/chunks/{sankeyDiagram-XADWPNL6.DySXofNs.js → sankeyDiagram-XADWPNL6.BfKCkH3x.js} +1 -1
- package/dist/docs/assets/chunks/{sequenceDiagram-FGHM5R23.Cp0GZoOU.js → sequenceDiagram-FGHM5R23.CUPKdYN0.js} +1 -1
- package/dist/docs/assets/chunks/{stateDiagram-FHFEXIEX.DvK-sXUX.js → stateDiagram-FHFEXIEX.CimDCRiK.js} +1 -1
- package/dist/docs/assets/chunks/stateDiagram-v2-QKLJ7IA2.ClNUVSTQ.js +1 -0
- package/dist/docs/assets/chunks/{theme.Clup4iIo.js → theme.CKht7z82.js} +2 -2
- package/dist/docs/assets/chunks/{timeline-definition-GMOUNBTQ.gHI9ZLm6.js → timeline-definition-GMOUNBTQ.BFTd5qKs.js} +1 -1
- package/dist/docs/assets/chunks/{vennDiagram-DHZGUBPP.G2N2zXYe.js → vennDiagram-DHZGUBPP.N6t5MmCb.js} +1 -1
- package/dist/docs/assets/chunks/wardley-RL74JXVD.D2G6Zyds.js +162 -0
- package/dist/docs/assets/chunks/{wardleyDiagram-NUSXRM2D.BgUKEagd.js → wardleyDiagram-NUSXRM2D.BqScALbL.js} +1 -1
- package/dist/docs/assets/chunks/{xychartDiagram-5P7HB3ND.CwH7oege.js → xychartDiagram-5P7HB3ND.Br0WiDkT.js} +1 -1
- package/dist/docs/assets/deployment.md.hKKN9I4c.js +31 -0
- package/dist/docs/assets/{deployment.md.BYuEcDBv.lean.js → deployment.md.hKKN9I4c.lean.js} +1 -1
- package/dist/docs/assets/{evals.md.C851kViu.js → evals.md.CHR34K1Y.js} +3 -7
- package/dist/docs/assets/{evals.md.C851kViu.lean.js → evals.md.CHR34K1Y.lean.js} +1 -1
- package/dist/docs/assets/guides_cloud-agents.md.CBK7W0-O.js +9 -0
- package/dist/docs/assets/guides_cloud-agents.md.CBK7W0-O.lean.js +1 -0
- package/dist/docs/assets/guides_grokbot-agents.md.BwAykJ7U.js +15 -0
- package/dist/docs/assets/{guides_grokbot-agents.md.tD1smFhU.lean.js → guides_grokbot-agents.md.BwAykJ7U.lean.js} +1 -1
- package/dist/docs/assets/{guides_hooks.md.5Ce3NXxZ.js → guides_hooks.md.B_bKG1oA.js} +1 -1
- package/dist/docs/assets/{guides_improve.md.CRrYq22s.js → guides_improve.md.CZKVt1cT.js} +2 -3
- package/dist/docs/assets/{guides_improve.md.CRrYq22s.lean.js → guides_improve.md.CZKVt1cT.lean.js} +1 -1
- package/dist/docs/assets/{guides_mcp-oauth.md.DR3zhC9r.js → guides_mcp-oauth.md.BM_eFC0L.js} +3 -15
- package/dist/docs/assets/guides_mcp-oauth.md.BM_eFC0L.lean.js +1 -0
- package/dist/docs/assets/{guides_webhooks.md.BBvAm_VF.js → guides_webhooks.md.Cpdc3BDX.js} +13 -12
- package/dist/docs/assets/{guides_webhooks.md.BBvAm_VF.lean.js → guides_webhooks.md.Cpdc3BDX.lean.js} +1 -1
- package/dist/docs/assets/{index.md.Dxxr7pFa.js → index.md.BIBHIQtU.js} +1 -1
- package/dist/docs/assets/{quickstart.md.BK5gjHM2.js → quickstart.md.CduLGBAB.js} +1 -1
- package/dist/docs/assets/{reference_agent-config.md.DrtLxWgR.js → reference_agent-config.md.DYA6ge6t.js} +7 -4
- package/dist/docs/assets/{reference_agent-config.md.DrtLxWgR.lean.js → reference_agent-config.md.DYA6ge6t.lean.js} +1 -1
- package/dist/docs/assets/reference_channels.md.DYg0CLud.js +22 -0
- package/dist/docs/assets/{reference_channels.md.LbNIJBwd.lean.js → reference_channels.md.DYg0CLud.lean.js} +1 -1
- package/dist/docs/assets/{reference_cli.md.dYCAL2lB.js → reference_cli.md.2d2Y0O-d.js} +16 -13
- package/dist/docs/assets/{reference_cli.md.dYCAL2lB.lean.js → reference_cli.md.2d2Y0O-d.lean.js} +1 -1
- package/dist/docs/assets/{reference_connections.md.DLrgAd5f.js → reference_connections.md.CxbLpaaP.js} +4 -5
- package/dist/docs/assets/{reference_connections.md.DLrgAd5f.lean.js → reference_connections.md.CxbLpaaP.lean.js} +1 -1
- package/dist/docs/assets/{reference_evals.md.D5i8PuXJ.js → reference_evals.md.Ccwp4x3o.js} +4 -4
- package/dist/docs/assets/{reference_evals.md.D5i8PuXJ.lean.js → reference_evals.md.Ccwp4x3o.lean.js} +1 -1
- package/dist/docs/assets/{reference_hooks.md.B-eGa2km.js → reference_hooks.md.DbJC8mcZ.js} +1 -1
- package/dist/docs/assets/reference_http-api.md.CrqhTv6S.js +11 -0
- package/dist/docs/assets/{reference_http-api.md.DbFNOubV.lean.js → reference_http-api.md.CrqhTv6S.lean.js} +1 -1
- package/dist/docs/assets/reference_playground.md.q4MI-0td.js +1 -0
- package/dist/docs/assets/reference_playground.md.q4MI-0td.lean.js +1 -0
- package/dist/docs/assets/{reference_schedules.md.BuJ8fgMa.js → reference_schedules.md.03Ryy9ca.js} +5 -5
- package/dist/docs/assets/{reference_schedules.md.BuJ8fgMa.lean.js → reference_schedules.md.03Ryy9ca.lean.js} +1 -1
- package/dist/docs/assets/reference_sessions.md.C_uzIWuy.js +1 -0
- package/dist/docs/assets/{reference_skills.md.ClkMoQsV.js → reference_skills.md.C2GWh7g8.js} +4 -4
- package/dist/docs/assets/{reference_tools.md.DzIY9JzY.js → reference_tools.md.08XR7lIl.js} +3 -14
- package/dist/docs/assets/reference_tools.md.08XR7lIl.lean.js +1 -0
- package/dist/docs/assets/{templates_grokbot-agents.md.2sydjFiO.js → templates_grokbot-agents.md.DgpPEs7B.js} +1 -1
- package/dist/docs/assets/troubleshooting.md.PCafNCb5.js +1 -0
- package/dist/docs/assets/{troubleshooting.md.x-GBa7wN.lean.js → troubleshooting.md.PCafNCb5.lean.js} +1 -1
- package/dist/docs/building-with-agents.html +37 -37
- package/dist/docs/building-with-agents.md +5 -5
- package/dist/docs/deployment.html +43 -41
- package/dist/docs/deployment.md +70 -33
- package/dist/docs/evals.html +38 -42
- package/dist/docs/evals.md +1 -16
- package/dist/docs/guides/agent-to-agent.html +35 -35
- package/dist/docs/guides/bitbucket.html +35 -35
- package/dist/docs/guides/cloud-agents.html +38 -39
- package/dist/docs/guides/cloud-agents.md +2 -8
- package/dist/docs/guides/convert-automation.html +35 -35
- package/dist/docs/guides/github.html +35 -35
- package/dist/docs/guides/gitlab.html +35 -35
- package/dist/docs/guides/grokbot-agents.html +37 -38
- package/dist/docs/guides/grokbot-agents.md +9 -13
- package/dist/docs/guides/hooks.html +37 -37
- package/dist/docs/guides/hooks.md +0 -1
- package/dist/docs/guides/improve.html +37 -38
- package/dist/docs/guides/improve.md +4 -6
- package/dist/docs/guides/jev.html +35 -35
- package/dist/docs/guides/mcp-oauth.html +39 -51
- package/dist/docs/guides/mcp-oauth.md +17 -40
- package/dist/docs/guides/migrate.html +35 -35
- package/dist/docs/guides/opentelemetry.html +35 -35
- package/dist/docs/guides/slack.html +35 -35
- package/dist/docs/guides/webhooks.html +47 -46
- package/dist/docs/guides/webhooks.md +35 -18
- package/dist/docs/hashmap.json +1 -1
- package/dist/docs/hillclimbing.html +35 -35
- package/dist/docs/index.html +36 -36
- package/dist/docs/index.md +1 -1
- package/dist/docs/llms-full.txt +388 -272
- package/dist/docs/llms.txt +4 -4
- package/dist/docs/quickstart.html +37 -37
- package/dist/docs/quickstart.md +2 -2
- package/dist/docs/reference/agent-config.html +41 -38
- package/dist/docs/reference/agent-config.md +26 -1
- package/dist/docs/reference/artifacts.html +35 -35
- package/dist/docs/reference/channels.html +42 -43
- package/dist/docs/reference/channels.md +29 -13
- package/dist/docs/reference/cli.html +50 -47
- package/dist/docs/reference/cli.md +115 -42
- package/dist/docs/reference/connections.html +39 -40
- package/dist/docs/reference/connections.md +6 -5
- package/dist/docs/reference/evals.html +38 -38
- package/dist/docs/reference/evals.md +15 -4
- package/dist/docs/reference/extensions.html +35 -35
- package/dist/docs/reference/hooks.html +37 -37
- package/dist/docs/reference/hooks.md +0 -1
- package/dist/docs/reference/http-api.html +38 -38
- package/dist/docs/reference/http-api.md +7 -17
- package/dist/docs/reference/instructions.html +35 -35
- package/dist/docs/reference/playground.html +37 -37
- package/dist/docs/reference/playground.md +1 -4
- package/dist/docs/reference/project-layout.html +35 -35
- package/dist/docs/reference/prompt.html +35 -35
- package/dist/docs/reference/schedules.html +39 -39
- package/dist/docs/reference/schedules.md +26 -3
- package/dist/docs/reference/sessions.html +36 -36
- package/dist/docs/reference/sessions.md +1 -2
- package/dist/docs/reference/skills.html +39 -39
- package/dist/docs/reference/skills.md +1 -1
- package/dist/docs/reference/subagents.html +35 -35
- package/dist/docs/reference/tools.html +39 -50
- package/dist/docs/reference/tools.md +2 -28
- package/dist/docs/templates/agentic-owners.html +35 -35
- package/dist/docs/templates/grokbot-agents.html +37 -37
- package/dist/docs/templates/grokbot-agents.md +1 -1
- package/dist/docs/templates/security-reviewer.html +35 -35
- package/dist/docs/templates/thermo-quality-review.html +35 -35
- package/dist/docs/templates/thermo-review.html +35 -35
- package/dist/docs/templates/triage.html +35 -35
- package/dist/docs/troubleshooting.html +36 -36
- package/dist/docs/troubleshooting.md +12 -7
- package/dist/extensions/cursor-cloud-agents/extension.d.ts +5 -1
- package/dist/extensions/cursor-cloud-agents/extension.d.ts.map +1 -1
- package/dist/extensions/cursor-cloud-agents/extension.js +4 -0
- package/dist/extensions/cursor-cloud-agents/lib/channels.d.ts.map +1 -1
- package/dist/extensions/cursor-cloud-agents/lib/channels.js +5 -1
- package/dist/filesystem.d.ts.map +1 -1
- package/dist/filesystem.js +4 -8
- package/dist/internal/cli-convert-automation.js +9 -19
- package/dist/internal/cli-deploy.d.ts +1 -1
- package/dist/internal/cli-deploy.d.ts.map +1 -1
- package/dist/internal/cli-deploy.js +18 -3
- package/dist/internal/cli-init-grokbot.d.ts +29 -0
- package/dist/internal/cli-init-grokbot.d.ts.map +1 -0
- package/dist/internal/cli-init-grokbot.js +181 -0
- package/dist/internal/cli-slack.js +1 -1
- package/dist/internal/comment-safe.d.ts +8 -0
- package/dist/internal/comment-safe.d.ts.map +1 -0
- package/dist/internal/comment-safe.js +12 -0
- package/dist/internal/continuation-identity.js +1 -1
- package/dist/internal/convert-automation/convert-workflow.d.ts.map +1 -1
- package/dist/internal/convert-automation/convert-workflow.js +2 -14
- package/dist/internal/convert-grokbot/answers.d.ts +127 -0
- package/dist/internal/convert-grokbot/answers.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/answers.js +443 -0
- package/dist/internal/convert-grokbot/bot.d.ts +50 -0
- package/dist/internal/convert-grokbot/bot.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/bot.js +72 -0
- package/dist/internal/convert-grokbot/checks.d.ts +26 -0
- package/dist/internal/convert-grokbot/checks.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/checks.js +170 -0
- package/dist/internal/convert-grokbot/convert.d.ts +60 -0
- package/dist/internal/convert-grokbot/convert.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/convert.js +470 -0
- package/dist/internal/convert-grokbot/handoff.d.ts +44 -0
- package/dist/internal/convert-grokbot/handoff.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/handoff.js +160 -0
- package/dist/internal/convert-grokbot/recipe.d.ts +61 -0
- package/dist/internal/convert-grokbot/recipe.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/recipe.js +94 -0
- package/dist/internal/convert-grokbot/routine.d.ts +51 -0
- package/dist/internal/convert-grokbot/routine.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/routine.js +128 -0
- package/dist/internal/convert-grokbot/slack.d.ts +28 -0
- package/dist/internal/convert-grokbot/slack.d.ts.map +1 -0
- package/dist/internal/convert-grokbot/slack.js +50 -0
- package/dist/internal/deploy-client.d.ts +0 -2
- package/dist/internal/deploy-client.d.ts.map +1 -1
- package/dist/internal/deploy-client.js +2 -11
- package/dist/internal/discovery/agent-config.d.ts +6 -0
- package/dist/internal/discovery/agent-config.d.ts.map +1 -1
- package/dist/internal/discovery/agent-config.js +19 -0
- package/dist/internal/discovery/agent.d.ts.map +1 -1
- package/dist/internal/discovery/agent.js +2 -1
- package/dist/internal/discovery/names.d.ts +2 -0
- package/dist/internal/discovery/names.d.ts.map +1 -1
- package/dist/internal/discovery/names.js +2 -0
- package/dist/internal/discovery/project.d.ts.map +1 -1
- package/dist/internal/discovery/project.js +1 -3
- package/dist/internal/eval-judge-model.d.ts +10 -5
- package/dist/internal/eval-judge-model.d.ts.map +1 -1
- package/dist/internal/eval-judge-model.js +36 -25
- package/dist/internal/filesystem/subagent-inherit.d.ts +39 -0
- package/dist/internal/filesystem/subagent-inherit.d.ts.map +1 -0
- package/dist/internal/filesystem/subagent-inherit.js +96 -0
- package/dist/internal/filesystem/tools.d.ts +6 -0
- package/dist/internal/filesystem/tools.d.ts.map +1 -1
- package/dist/internal/filesystem/tools.js +38 -1
- package/dist/internal/hosted-catch-protocol.d.ts +2 -0
- package/dist/internal/hosted-catch-protocol.d.ts.map +1 -1
- package/dist/internal/hosted-catch-protocol.js +2 -0
- package/dist/internal/hosted-catch.d.ts +2 -3
- package/dist/internal/hosted-catch.d.ts.map +1 -1
- package/dist/internal/hosted-catch.js +2 -3
- package/dist/internal/hosted-delivery.d.ts.map +1 -1
- package/dist/internal/hosted-delivery.js +46 -13
- package/dist/internal/hosted-execution-flush.d.ts +6 -3
- package/dist/internal/hosted-execution-flush.d.ts.map +1 -1
- package/dist/internal/hosted-execution-flush.js +28 -31
- package/dist/internal/hosting.d.ts +1 -1
- package/dist/internal/hosting.d.ts.map +1 -1
- package/dist/internal/hosting.js +7 -3
- package/dist/internal/init-interview.d.ts +3 -5
- package/dist/internal/init-interview.d.ts.map +1 -1
- package/dist/internal/init-interview.js +15 -88
- package/dist/internal/init-project.d.ts +13 -0
- package/dist/internal/init-project.d.ts.map +1 -1
- package/dist/internal/init-project.js +30 -37
- package/dist/internal/init-scaffold.d.ts +11 -0
- package/dist/internal/init-scaffold.d.ts.map +1 -1
- package/dist/internal/init-scaffold.js +47 -13
- package/dist/internal/interview/agent-questions.d.ts +19 -0
- package/dist/internal/interview/agent-questions.d.ts.map +1 -0
- package/dist/internal/interview/agent-questions.js +120 -0
- package/dist/internal/interview/question.d.ts +82 -0
- package/dist/internal/interview/question.d.ts.map +1 -0
- package/dist/internal/interview/question.js +198 -0
- package/dist/internal/local-control-plane.d.ts.map +1 -1
- package/dist/internal/local-control-plane.js +5 -1
- package/dist/internal/otel/collector.d.ts +2 -0
- package/dist/internal/otel/collector.d.ts.map +1 -1
- package/dist/internal/otel/collector.js +4 -0
- package/dist/internal/peer-connections.d.ts +6 -2
- package/dist/internal/peer-connections.d.ts.map +1 -1
- package/dist/internal/peer-connections.js +23 -19
- package/dist/internal/resolve-prod-target.d.ts.map +1 -1
- package/dist/internal/resolve-prod-target.js +2 -1
- package/dist/internal/sdk-runner.d.ts.map +1 -1
- package/dist/internal/sdk-runner.js +43 -16
- package/dist/internal/sdk-subagent-inherit-support.d.ts +9 -0
- package/dist/internal/sdk-subagent-inherit-support.d.ts.map +1 -0
- package/dist/internal/sdk-subagent-inherit-support.js +89 -0
- package/dist/internal/server.d.ts.map +1 -1
- package/dist/internal/server.js +6 -5
- package/dist/internal/session-engine.d.ts +13 -0
- package/dist/internal/session-engine.d.ts.map +1 -1
- package/dist/internal/session-engine.js +62 -11
- package/dist/internal/session-run-log.d.ts.map +1 -1
- package/dist/internal/session-run-log.js +26 -11
- package/dist/internal/{convert-automation/slug.d.ts → slug.d.ts} +4 -1
- package/dist/internal/slug.d.ts.map +1 -0
- package/dist/internal/{convert-automation/slug.js → slug.js} +11 -1
- package/dist/playground/assets/index-7fVUOA5l.css +1 -0
- package/dist/playground/assets/{index-ClxRl2Cw.js → index-U3TRnwAP.js} +43 -43
- package/dist/playground/index.html +2 -2
- package/dist/types.d.ts +26 -1
- package/dist/types.d.ts.map +1 -1
- package/docs/README.md +1 -1
- package/docs/building-with-agents.md +5 -5
- package/docs/deployment.md +70 -33
- package/docs/evals.md +1 -16
- package/docs/guides/cloud-agents.md +3 -9
- package/docs/guides/grokbot-agents.md +10 -14
- package/docs/guides/hooks.md +0 -1
- package/docs/guides/improve.md +4 -6
- package/docs/guides/mcp-oauth.md +18 -41
- package/docs/guides/webhooks.md +35 -18
- package/docs/quickstart.md +2 -2
- package/docs/reference/agent-config.md +26 -1
- package/docs/reference/channels.md +29 -13
- package/docs/reference/cli.md +115 -42
- package/docs/reference/connections.md +6 -5
- package/docs/reference/evals.md +15 -4
- package/docs/reference/hooks.md +0 -1
- package/docs/reference/http-api.md +7 -17
- package/docs/reference/playground.md +2 -5
- package/docs/reference/schedules.md +26 -3
- package/docs/reference/sessions.md +1 -2
- package/docs/reference/skills.md +1 -1
- package/docs/reference/tools.md +3 -29
- package/docs/templates/grokbot-agents.md +1 -1
- package/docs/troubleshooting.md +12 -7
- package/package.json +36 -35
- package/schemas/grokbot-answers.schema.json +343 -0
- package/skills/create-agent/SKILL.md +16 -11
- package/skills/debug/SKILL.md +3 -4
- package/skills/evals/SKILL.md +2 -2
- package/skills/framework-map/SKILL.md +10 -10
- package/skills/mcp-auth/SKILL.md +10 -34
- package/skills/migrate-v2/SKILL.md +13 -9
- package/skills/setup-slack/SKILL.md +0 -13
- package/templates/agentic-owners/bot/lib/owners/handles.ts +1 -1
- package/templates/agentic-owners/bot/lib/owners/matching.ts +20 -9
- package/templates/agents-md/README.md +3 -3
- package/templates/agents-md/bot/channels/queue.ts +3 -8
- package/templates/agents-md/bot/instructions.md +1 -2
- package/templates/agents-md/bot/tools/apply_agents.ts +0 -1
- package/templates/agents-md/evals/agents.eval.ts +2 -2
- package/templates/demo/bot/channels/queue.ts +5 -15
- package/templates/grokbot-agents/.gitignore +4 -0
- package/templates/pr-autofixer/bot/channels/drive.ts +3 -16
- package/templates/security-help/.gitignore +4 -0
- package/templates/triage/bot/channels/queue.ts +11 -22
- package/templates/triage/bot/channels/webhook.ts +3 -6
- package/templates/triage/bot/lib/parse-queue-event.ts +0 -6
- package/dist/docs/assets/chunks/@localSearchIndexroot.CzrtdJ8s.js +0 -1
- package/dist/docs/assets/chunks/channel.6ebHhoF9.js +0 -1
- package/dist/docs/assets/chunks/classDiagram-6PBFFD2Q.BJ-CwKwu.js +0 -1
- package/dist/docs/assets/chunks/classDiagram-v2-HSJHXN6E.BJ-CwKwu.js +0 -1
- package/dist/docs/assets/chunks/clone.DfV2fkWH.js +0 -1
- package/dist/docs/assets/chunks/stateDiagram-v2-QKLJ7IA2.DNdUCJyd.js +0 -1
- package/dist/docs/assets/chunks/wardley-RL74JXVD.C46G0P5a.js +0 -162
- package/dist/docs/assets/deployment.md.BYuEcDBv.js +0 -29
- package/dist/docs/assets/guides_cloud-agents.md.CWJjS9No.js +0 -10
- package/dist/docs/assets/guides_cloud-agents.md.CWJjS9No.lean.js +0 -1
- package/dist/docs/assets/guides_grokbot-agents.md.tD1smFhU.js +0 -16
- package/dist/docs/assets/guides_mcp-oauth.md.DR3zhC9r.lean.js +0 -1
- package/dist/docs/assets/reference_channels.md.LbNIJBwd.js +0 -23
- package/dist/docs/assets/reference_http-api.md.DbFNOubV.js +0 -11
- package/dist/docs/assets/reference_playground.md.1hx0gcIu.js +0 -1
- package/dist/docs/assets/reference_playground.md.1hx0gcIu.lean.js +0 -1
- package/dist/docs/assets/reference_sessions.md.CyM7ARz1.js +0 -1
- package/dist/docs/assets/reference_tools.md.DzIY9JzY.lean.js +0 -1
- package/dist/docs/assets/troubleshooting.md.x-GBa7wN.js +0 -1
- package/dist/internal/convert-automation/slug.d.ts.map +0 -1
- package/dist/playground/assets/index-BKSsuEMw.css +0 -1
- /package/dist/docs/assets/{guides_hooks.md.5Ce3NXxZ.lean.js → guides_hooks.md.B_bKG1oA.lean.js} +0 -0
- /package/dist/docs/assets/{index.md.Dxxr7pFa.lean.js → index.md.BIBHIQtU.lean.js} +0 -0
- /package/dist/docs/assets/{quickstart.md.BK5gjHM2.lean.js → quickstart.md.CduLGBAB.lean.js} +0 -0
- /package/dist/docs/assets/{reference_hooks.md.B-eGa2km.lean.js → reference_hooks.md.DbJC8mcZ.lean.js} +0 -0
- /package/dist/docs/assets/{reference_sessions.md.CyM7ARz1.lean.js → reference_sessions.md.C_uzIWuy.lean.js} +0 -0
- /package/dist/docs/assets/{reference_skills.md.ClkMoQsV.lean.js → reference_skills.md.C2GWh7g8.lean.js} +0 -0
- /package/dist/docs/assets/{templates_grokbot-agents.md.2sydjFiO.lean.js → templates_grokbot-agents.md.DgpPEs7B.lean.js} +0 -0
|
@@ -0,0 +1,470 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Pure Grok Bot → BDK project mapping. Takes the recipe's bot and resolved
|
|
3
|
+
* answers; returns the project files as an in-memory tree plus a preview a
|
|
4
|
+
* client renders before confirming. No I/O and no clock: `generatedAt`
|
|
5
|
+
* comes from the caller.
|
|
6
|
+
*/
|
|
7
|
+
import { channelPostIdEntries } from "../../channels/slack/channel-watch.js";
|
|
8
|
+
import { envPrefixFromName, slackEnvKeys } from "../../channels/slack/credentials.js";
|
|
9
|
+
import { DEFAULT_MODEL } from "../../types.js";
|
|
10
|
+
import { commentSafe } from "../comment-safe.js";
|
|
11
|
+
import { isValidCron } from "../cron.js";
|
|
12
|
+
import { CLI_COMMAND_NAME, PACKAGE_NAME } from "../distribution.js";
|
|
13
|
+
import { serializeFrontmatter } from "../frontmatter.js";
|
|
14
|
+
import { EVALS_CONFIG_TS, formatModelLiteral, GITIGNORE, JOURNAL_INSTRUCTIONS, MEMORY_TS, packageJson, SMOKE_EVAL_TS, tsconfig, } from "../init-scaffold.js";
|
|
15
|
+
import { DEFAULT_MODEL_ID } from "../interview/agent-questions.js";
|
|
16
|
+
import { mcpOauthSecretNames } from "../mcp-oauth.js";
|
|
17
|
+
import { CANONICAL_PROJECT_ROOT, projectPath } from "../project-layout.js";
|
|
18
|
+
import { SlugRegistry, slugFromDirectoryName } from "../slug.js";
|
|
19
|
+
import { code, redactDeep, redactSecretValues } from "./checks.js";
|
|
20
|
+
import { EXPORT_RECORD_PATH, handoffFiles, SLACK_PATH, } from "./handoff.js";
|
|
21
|
+
import { fillInText, liveChannel, normalizeFillIn, triggerLabel, } from "./routine.js";
|
|
22
|
+
import { emptySlackWiring, renderSlackChannel } from "./slack.js";
|
|
23
|
+
export const EXPORT_RECORD_VERSION = 1;
|
|
24
|
+
export const PREVIEW_VERSION = 1;
|
|
25
|
+
export function convertGrokbot(input) {
|
|
26
|
+
const { answers, defaulted, ignored } = input.resolved;
|
|
27
|
+
const { bot, excluded } = selectBot(input.bot, answers);
|
|
28
|
+
const root = input.projectRoot ?? CANONICAL_PROJECT_ROOT;
|
|
29
|
+
const pluginSlugs = new Set(bot.plugins.map((plugin) => plugin.slug));
|
|
30
|
+
const out = {
|
|
31
|
+
root,
|
|
32
|
+
channels: new Set(answers.channels),
|
|
33
|
+
files: [],
|
|
34
|
+
from: new Map(),
|
|
35
|
+
preview: {
|
|
36
|
+
version: PREVIEW_VERSION,
|
|
37
|
+
name: answers.name,
|
|
38
|
+
answers,
|
|
39
|
+
defaulted,
|
|
40
|
+
ignored,
|
|
41
|
+
files: [],
|
|
42
|
+
excluded,
|
|
43
|
+
unmapped: bot.unknownFields.map((field) => ({
|
|
44
|
+
from: field,
|
|
45
|
+
reason: "Unknown recipe field; ignored.",
|
|
46
|
+
})),
|
|
47
|
+
fillIns: [],
|
|
48
|
+
secrets: { names: [], reauth: [] },
|
|
49
|
+
warnings: [],
|
|
50
|
+
setupSteps: [],
|
|
51
|
+
},
|
|
52
|
+
secrets: new Map(answers.secrets?.names?.map((name) => [name, {}])),
|
|
53
|
+
egress: new Set(),
|
|
54
|
+
reauth: new Set(answers.secrets?.reauth?.filter((slug) => pluginSlugs.has(slug))),
|
|
55
|
+
skillDirs: new SlugRegistry(),
|
|
56
|
+
scheduleNames: new SlugRegistry(),
|
|
57
|
+
};
|
|
58
|
+
for (const skill of bot.skills) {
|
|
59
|
+
out.skillDirs.claim(skill.slug);
|
|
60
|
+
}
|
|
61
|
+
if (bot.avatar !== undefined) {
|
|
62
|
+
out.preview.unmapped.push({
|
|
63
|
+
from: "profile.avatar",
|
|
64
|
+
reason: `BDK agents have no avatar; kept in ${EXPORT_RECORD_PATH} for the Slack app icon.`,
|
|
65
|
+
});
|
|
66
|
+
}
|
|
67
|
+
const directory = input.directoryName ?? answers.name;
|
|
68
|
+
const generator = `${PACKAGE_NAME}@${input.packageVersion}`;
|
|
69
|
+
emitSkills(bot, out);
|
|
70
|
+
const wiring = emitRoutines(bot, answers, out);
|
|
71
|
+
emitConnections(bot, answers, out);
|
|
72
|
+
const knowledge = emitMemory(bot, answers, out);
|
|
73
|
+
const slack = answers.slack === undefined
|
|
74
|
+
? undefined
|
|
75
|
+
: emitSlackChannel(wiring, answers.slack, directory, out);
|
|
76
|
+
emitInstructions(bot, answers, out, wiring, knowledge);
|
|
77
|
+
emit(out, projectPath(root, "hooks/memory.ts"), MEMORY_TS, "scaffold");
|
|
78
|
+
emit(out, "evals/evals.config.ts", EVALS_CONFIG_TS, "scaffold");
|
|
79
|
+
emit(out, "evals/smoke.eval.ts", SMOKE_EVAL_TS, "scaffold");
|
|
80
|
+
emit(out, "package.json", packageJson({ name: directory, packageVersion: input.packageVersion }), "scaffold");
|
|
81
|
+
emit(out, "tsconfig.json", tsconfig(root), "scaffold");
|
|
82
|
+
emit(out, ".gitignore", GITIGNORE, "scaffold");
|
|
83
|
+
if (out.channels.has("github")) {
|
|
84
|
+
out.preview.setupSteps.push(`Add a GitHub channel under ${projectPath(root, "channels/")} (see the ${CLI_COMMAND_NAME} github skill).`);
|
|
85
|
+
}
|
|
86
|
+
if (out.channels.has("webhook")) {
|
|
87
|
+
out.preview.setupSteps.push(`Add a custom webhook channel under ${projectPath(root, "channels/")} and protect it with bearerAuth.`);
|
|
88
|
+
}
|
|
89
|
+
out.preview.secrets = { names: [...out.secrets.keys()].sort(), reauth: [...out.reauth].sort() };
|
|
90
|
+
emit(out, projectPath(root, "agent.ts"), renderAgentTs(bot, answers, out), "profile");
|
|
91
|
+
emit(out, EXPORT_RECORD_PATH, renderExportRecord({ input, generator, secrets: out.preview.secrets, slack }), "answers");
|
|
92
|
+
for (const file of handoffFiles({
|
|
93
|
+
root,
|
|
94
|
+
answers,
|
|
95
|
+
preview: out.preview,
|
|
96
|
+
secrets: out.secrets,
|
|
97
|
+
slug: slugFromDirectoryName(directory),
|
|
98
|
+
generator,
|
|
99
|
+
slack,
|
|
100
|
+
})) {
|
|
101
|
+
emit(out, file.path, file.contents, file.from);
|
|
102
|
+
}
|
|
103
|
+
const files = out.files.sort((a, b) => a.path.localeCompare(b.path));
|
|
104
|
+
out.preview.files = files.map((file) => ({
|
|
105
|
+
path: file.path,
|
|
106
|
+
from: out.from.get(file.path) ?? [],
|
|
107
|
+
}));
|
|
108
|
+
return { files, preview: redactDeep(out.preview) };
|
|
109
|
+
}
|
|
110
|
+
/** The items the answers keep, and the ones they leave out. */
|
|
111
|
+
function selectBot(bot, answers) {
|
|
112
|
+
const excluded = [];
|
|
113
|
+
const keep = (kind, items) => {
|
|
114
|
+
const include = answers[kind]?.include;
|
|
115
|
+
const kept = items.filter((item) => include?.includes(item.slug) ?? true);
|
|
116
|
+
for (const item of items.filter((candidate) => !kept.includes(candidate))) {
|
|
117
|
+
excluded.push(`${kind}/${item.slug}`);
|
|
118
|
+
}
|
|
119
|
+
return kept;
|
|
120
|
+
};
|
|
121
|
+
const skills = keep("skills", bot.skills);
|
|
122
|
+
const routines = keep("routines", bot.routines);
|
|
123
|
+
const plugins = keep("plugins", bot.plugins);
|
|
124
|
+
const dropMemory = answers.memory === "drop" && bot.memory.length > 0;
|
|
125
|
+
if (dropMemory) {
|
|
126
|
+
excluded.push("memory");
|
|
127
|
+
}
|
|
128
|
+
return {
|
|
129
|
+
bot: {
|
|
130
|
+
...bot,
|
|
131
|
+
skills,
|
|
132
|
+
routines,
|
|
133
|
+
plugins,
|
|
134
|
+
memory: dropMemory ? [] : bot.memory,
|
|
135
|
+
gettingStarted: skills.some((skill) => skill.slug === bot.gettingStarted)
|
|
136
|
+
? bot.gettingStarted
|
|
137
|
+
: undefined,
|
|
138
|
+
},
|
|
139
|
+
excluded,
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
/** Secret-shaped values never reach a written file. */
|
|
143
|
+
function emit(out, path, contents, ...from) {
|
|
144
|
+
const { text, redacted } = redactSecretValues(contents);
|
|
145
|
+
if (redacted > 0) {
|
|
146
|
+
out.preview.warnings.push(`${path}: removed ${redacted} value(s) that look like secrets. Store each with \`${CLI_COMMAND_NAME} secrets set\` and list its name in the answers (secrets.names).`);
|
|
147
|
+
}
|
|
148
|
+
out.files.push({ path, contents: text });
|
|
149
|
+
out.from.set(path, [...new Set(from)]);
|
|
150
|
+
}
|
|
151
|
+
function own(record, key) {
|
|
152
|
+
return record !== undefined && Object.hasOwn(record, key) ? record[key] : undefined;
|
|
153
|
+
}
|
|
154
|
+
function oneLine(text) {
|
|
155
|
+
return text.replace(/\s+/g, " ").trim();
|
|
156
|
+
}
|
|
157
|
+
function skillFile(name, description, body) {
|
|
158
|
+
return `${serializeFrontmatter({ name, description: oneLine(description) })}${body.trim()}\n`;
|
|
159
|
+
}
|
|
160
|
+
function emitSchedule(out, slug, cron, body, from) {
|
|
161
|
+
const path = projectPath(out.root, `schedules/${out.scheduleNames.claim(slug)}.md`);
|
|
162
|
+
emit(out, path, `${serializeFrontmatter({ cron })}${body.trim()}\n`, from);
|
|
163
|
+
return path;
|
|
164
|
+
}
|
|
165
|
+
/** Schedules and Slack triggers are wired; GitHub and webhooks need a channel written by hand. */
|
|
166
|
+
function planTrigger(trigger, out) {
|
|
167
|
+
const channel = liveChannel(trigger);
|
|
168
|
+
if (channel === undefined) {
|
|
169
|
+
return {
|
|
170
|
+
kind: "skip",
|
|
171
|
+
reason: trigger.kind === "cron"
|
|
172
|
+
? `Paused schedule ${code(trigger.cron)}; add a file under ${projectPath(out.root, "schedules/")} to run it.`
|
|
173
|
+
: `${code(triggerLabel(trigger))} trigger has no BDK channel.`,
|
|
174
|
+
};
|
|
175
|
+
}
|
|
176
|
+
if (!out.channels.has(channel)) {
|
|
177
|
+
return {
|
|
178
|
+
kind: "skip",
|
|
179
|
+
reason: `${code(triggerLabel(trigger))} trigger dropped: the ${channel} channel is off.`,
|
|
180
|
+
};
|
|
181
|
+
}
|
|
182
|
+
if (trigger.kind === "cron" && !isValidCron(trigger.cron)) {
|
|
183
|
+
return { kind: "skip", reason: `${code(trigger.cron)} is not a five-field cron expression.` };
|
|
184
|
+
}
|
|
185
|
+
return trigger.kind === "github" || trigger.kind === "webhook"
|
|
186
|
+
? { kind: "manual" }
|
|
187
|
+
: { kind: "wire" };
|
|
188
|
+
}
|
|
189
|
+
function emitSkills(bot, out) {
|
|
190
|
+
for (const skill of bot.skills) {
|
|
191
|
+
const from = `skills/${skill.slug}`;
|
|
192
|
+
emit(out, projectPath(out.root, `skills/${skill.slug}/SKILL.md`), skillFile(skill.name, skill.description, skill.body), from);
|
|
193
|
+
for (const trigger of skill.triggers) {
|
|
194
|
+
const plan = planTrigger(trigger, out);
|
|
195
|
+
if (plan.kind === "skip") {
|
|
196
|
+
out.preview.unmapped.push({ from: `${from}.trigger`, reason: plan.reason });
|
|
197
|
+
}
|
|
198
|
+
else {
|
|
199
|
+
emitSchedule(out, skill.slug, trigger.cron, `Use the \`${skill.slug}\` skill.`, from);
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
}
|
|
203
|
+
}
|
|
204
|
+
function emitRoutines(bot, answers, out) {
|
|
205
|
+
const slack = emptySlackWiring();
|
|
206
|
+
for (const routine of bot.routines) {
|
|
207
|
+
const from = `routines/${routine.slug}`;
|
|
208
|
+
const values = fillInValues(routine, answers);
|
|
209
|
+
const job = fillInText(routine.job, values);
|
|
210
|
+
recordFillIns(routine, values, job, out);
|
|
211
|
+
let wired = false;
|
|
212
|
+
const manual = [];
|
|
213
|
+
for (const trigger of routine.triggers) {
|
|
214
|
+
const plan = planTrigger(trigger, out);
|
|
215
|
+
if (plan.kind === "skip") {
|
|
216
|
+
out.preview.unmapped.push({ from, reason: plan.reason });
|
|
217
|
+
}
|
|
218
|
+
else if (plan.kind === "manual") {
|
|
219
|
+
manual.push(code(triggerLabel(trigger)));
|
|
220
|
+
}
|
|
221
|
+
else if (trigger.kind === "cron") {
|
|
222
|
+
wired = true;
|
|
223
|
+
const path = emitSchedule(out, routine.slug, trigger.cron, job, from);
|
|
224
|
+
if (routine.fillIns.some((fill) => fill.id === "timezone")) {
|
|
225
|
+
out.preview.warnings.push(`${from}: BDK runs \`${trigger.cron}\` in UTC${values.timezone === undefined ? "" : `, not ${values.timezone}`}; adjust the cron in ${path} if the time matters.`);
|
|
226
|
+
}
|
|
227
|
+
}
|
|
228
|
+
else if (trigger.kind === "slack") {
|
|
229
|
+
wired = true;
|
|
230
|
+
wireSlack(slack, routine, trigger.match, values, job, from);
|
|
231
|
+
}
|
|
232
|
+
}
|
|
233
|
+
let skill;
|
|
234
|
+
if (!wired) {
|
|
235
|
+
skill = projectPath(out.root, `skills/${out.skillDirs.claim(routine.slug)}/SKILL.md`);
|
|
236
|
+
const description = fillInText(routine.description, values);
|
|
237
|
+
emit(out, skill, skillFile(routine.name, `${description} Not wired to a trigger yet; run it on request.`, job), from);
|
|
238
|
+
}
|
|
239
|
+
if (manual.length > 0) {
|
|
240
|
+
out.preview.setupSteps.push(`Wire ${code(from)}${skill === undefined ? "" : ` (${code(skill)})`} to ${manual.join(", ")}.`);
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
return slack;
|
|
244
|
+
}
|
|
245
|
+
function fillInValues(routine, answers) {
|
|
246
|
+
return Object.fromEntries(Object.entries(own(answers.fillIns, routine.slug) ?? {}).map(([id, value]) => [
|
|
247
|
+
id,
|
|
248
|
+
normalizeFillIn(id, value),
|
|
249
|
+
]));
|
|
250
|
+
}
|
|
251
|
+
function recordFillIns(routine, values, job, out) {
|
|
252
|
+
for (const fill of routine.fillIns) {
|
|
253
|
+
out.preview.fillIns.push({
|
|
254
|
+
routine: routine.slug,
|
|
255
|
+
id: fill.id,
|
|
256
|
+
label: fill.label,
|
|
257
|
+
value: own(values, fill.id),
|
|
258
|
+
});
|
|
259
|
+
}
|
|
260
|
+
const unfilled = routine.fillIns.filter((fill) => own(values, fill.id) === undefined && job.includes(`{${fill.id}}`));
|
|
261
|
+
if (unfilled.length > 0) {
|
|
262
|
+
out.preview.warnings.push(`routines/${routine.slug}: placeholders ${unfilled.map((fill) => `{${fill.id}}`).join(", ")} are unfilled; set fillIns.${routine.slug} in the answers or edit the text.`);
|
|
263
|
+
}
|
|
264
|
+
}
|
|
265
|
+
function wireSlack(slack, routine, match, values, job, from) {
|
|
266
|
+
const channel = values.slack_channel;
|
|
267
|
+
const lead = {
|
|
268
|
+
mention: "when someone mentions you",
|
|
269
|
+
message: `new posts in ${channel ?? "a watched channel"}`,
|
|
270
|
+
keyword: `posts in ${channel ?? "a watched channel"} that mention "${values.slack_keyword ?? "{slack_keyword}"}"`,
|
|
271
|
+
reaction: `:${values.slack_emoji ?? "{slack_emoji}"}: reactions`,
|
|
272
|
+
}[match];
|
|
273
|
+
slack.sections.push({ title: `${routine.name} (${lead})`, body: job, from });
|
|
274
|
+
if (match === "mention") {
|
|
275
|
+
return;
|
|
276
|
+
}
|
|
277
|
+
if (match === "reaction") {
|
|
278
|
+
if (values.slack_emoji === undefined) {
|
|
279
|
+
slack.todos.push(`${routine.name}: set the reaction emoji (fillIns.${routine.slug}.slack_emoji).`);
|
|
280
|
+
}
|
|
281
|
+
else {
|
|
282
|
+
slack.emojis.push(values.slack_emoji);
|
|
283
|
+
}
|
|
284
|
+
return;
|
|
285
|
+
}
|
|
286
|
+
const [id] = channel === undefined ? [] : channelPostIdEntries([channel]);
|
|
287
|
+
if (id === undefined) {
|
|
288
|
+
slack.todos.push(`${routine.name}: add the watched channel's id (C…) to engagement.channelPosts.allow (fillIns.${routine.slug}.slack_channel${channel === undefined ? "" : ` is ${JSON.stringify(channel)}`}).`);
|
|
289
|
+
}
|
|
290
|
+
else {
|
|
291
|
+
slack.watch.push(id);
|
|
292
|
+
}
|
|
293
|
+
if (match === "message") {
|
|
294
|
+
slack.allPosts = true;
|
|
295
|
+
}
|
|
296
|
+
else if (values.slack_keyword === undefined) {
|
|
297
|
+
slack.todos.push(`${routine.name}: set the keyword (fillIns.${routine.slug}.slack_keyword).`);
|
|
298
|
+
}
|
|
299
|
+
else {
|
|
300
|
+
slack.keywords.push(values.slack_keyword.toLowerCase());
|
|
301
|
+
}
|
|
302
|
+
}
|
|
303
|
+
/** Names every shell reads the same inside single quotes; PowerShell also ends quotes at ‘’. */
|
|
304
|
+
const PLAIN_NAME = /^[\p{L}\p{N} ._-]+$/u;
|
|
305
|
+
function emitSlackChannel(wiring, answers, directoryName, out) {
|
|
306
|
+
const envPrefix = envPrefixFromName(directoryName);
|
|
307
|
+
const keys = slackEnvKeys(envPrefix);
|
|
308
|
+
const path = projectPath(out.root, "channels/slack.ts");
|
|
309
|
+
out.secrets.set(keys.bot, { file: path });
|
|
310
|
+
out.secrets.set(keys.app, { file: path });
|
|
311
|
+
const rendered = renderSlackChannel(wiring, envPrefix);
|
|
312
|
+
out.preview.warnings.push(...rendered.warnings);
|
|
313
|
+
emit(out, path, rendered.contents, ...(wiring.sections.length === 0
|
|
314
|
+
? ["answers"]
|
|
315
|
+
: wiring.sections.map((section) => section.from)));
|
|
316
|
+
const named = PLAIN_NAME.test(answers.botName);
|
|
317
|
+
const create = named
|
|
318
|
+
? `${CLI_COMMAND_NAME} slack create --dir . --name '${answers.botName}'`
|
|
319
|
+
: `${CLI_COMMAND_NAME} slack create --dir .`;
|
|
320
|
+
const naming = named ? "" : `; name it ${code(answers.botName)} in the wizard`;
|
|
321
|
+
out.preview.setupSteps.push(answers.app === "move"
|
|
322
|
+
? `Slack: move the bot's existing Slack app and store its tokens in ${keys.bot} and ${keys.app} (see ${SLACK_PATH}).`
|
|
323
|
+
: `Slack: \`${create}\` mints the app and stores ${keys.bot} and ${keys.app}${naming} (see ${SLACK_PATH}).`);
|
|
324
|
+
return { answers, create, keys };
|
|
325
|
+
}
|
|
326
|
+
function emitConnections(bot, answers, out) {
|
|
327
|
+
for (const plugin of bot.plugins) {
|
|
328
|
+
const connector = own(answers.connectors, plugin.slug);
|
|
329
|
+
if (connector === undefined) {
|
|
330
|
+
throw new Error(`No connector answer for plugin "${plugin.slug}".`);
|
|
331
|
+
}
|
|
332
|
+
const path = projectPath(out.root, `mcp-connections/${plugin.slug}.ts`);
|
|
333
|
+
emit(out, path, [
|
|
334
|
+
`import { defineConnection } from "${PACKAGE_NAME}/connections";`,
|
|
335
|
+
"",
|
|
336
|
+
`// Grok Bot plugin "${commentSafe(plugin.name)}".`,
|
|
337
|
+
...connectionBody(plugin, connector),
|
|
338
|
+
"",
|
|
339
|
+
].join("\n"), `plugins/${plugin.slug}`);
|
|
340
|
+
if (connector.auth === "cursor-account") {
|
|
341
|
+
continue;
|
|
342
|
+
}
|
|
343
|
+
out.egress.add(new URL(connector.url).hostname);
|
|
344
|
+
if (connector.auth === "secret") {
|
|
345
|
+
out.secrets.set(connector.secret, { file: path });
|
|
346
|
+
continue;
|
|
347
|
+
}
|
|
348
|
+
const names = mcpOauthSecretNames(plugin.slug);
|
|
349
|
+
for (const name of [names.accessToken, names.refreshToken, names.clientId]) {
|
|
350
|
+
out.secrets.set(name, { file: path, oauth: true });
|
|
351
|
+
}
|
|
352
|
+
out.reauth.add(plugin.slug);
|
|
353
|
+
}
|
|
354
|
+
}
|
|
355
|
+
function connectionBody(plugin, connector) {
|
|
356
|
+
switch (connector.auth) {
|
|
357
|
+
case "cursor-account":
|
|
358
|
+
return [
|
|
359
|
+
"// Tools run on the Cursor backend with your account's stored credentials,",
|
|
360
|
+
"// so no token lives in this project. Authorize the connector in Cursor",
|
|
361
|
+
"// (dashboard -> MCP) for the account this agent runs as.",
|
|
362
|
+
"export default defineConnection({",
|
|
363
|
+
" cursorAccount: true,",
|
|
364
|
+
` servers: [${JSON.stringify(connector.server)}],`,
|
|
365
|
+
"});",
|
|
366
|
+
];
|
|
367
|
+
case "oauth":
|
|
368
|
+
return [
|
|
369
|
+
`// Sign in with \`${CLI_COMMAND_NAME} mcp oauth ${plugin.slug}\` (add --store for a hosted deploy).`,
|
|
370
|
+
"export default defineConnection({",
|
|
371
|
+
` url: ${JSON.stringify(connector.url)},`,
|
|
372
|
+
" oauth: true,",
|
|
373
|
+
"});",
|
|
374
|
+
];
|
|
375
|
+
case "secret":
|
|
376
|
+
return [
|
|
377
|
+
`// \${${connector.secret}} expands from the environment when a client opens.`,
|
|
378
|
+
"export default defineConnection({",
|
|
379
|
+
` url: ${JSON.stringify(connector.url)},`,
|
|
380
|
+
` headers: { authorization: "Bearer \${${connector.secret}}" },`,
|
|
381
|
+
"});",
|
|
382
|
+
];
|
|
383
|
+
}
|
|
384
|
+
}
|
|
385
|
+
function emitMemory(bot, answers, out) {
|
|
386
|
+
if (bot.memory.length === 0) {
|
|
387
|
+
return undefined;
|
|
388
|
+
}
|
|
389
|
+
if (answers.memory === "kv") {
|
|
390
|
+
const path = projectPath(out.root, "lib/memory-seed.json");
|
|
391
|
+
emit(out, path, `${JSON.stringify(bot.memory, null, 2)}\n`, "memory");
|
|
392
|
+
out.preview.warnings.push(`memory: BDK has no built-in KV seed. The memories are data in ${path}; load them into ctx.host.kv from your own code, or re-export with memory "skill".`);
|
|
393
|
+
return undefined;
|
|
394
|
+
}
|
|
395
|
+
const slug = out.skillDirs.claim("knowledge");
|
|
396
|
+
emit(out, projectPath(out.root, `skills/${slug}/SKILL.md`), skillFile("knowledge", `What ${bot.name} already knows about its user and team, carried over from its Grok Bot memory. Read it before answering questions about people, preferences, or past decisions.`, knowledgeBody(bot.memory)), "memory");
|
|
397
|
+
return slug;
|
|
398
|
+
}
|
|
399
|
+
function knowledgeBody(memory) {
|
|
400
|
+
const groups = [
|
|
401
|
+
["Profile", memory.filter((row) => row.kind === "profile")],
|
|
402
|
+
["Log", memory.filter((row) => row.kind === "log")],
|
|
403
|
+
["Notes", memory.filter((row) => row.kind !== "profile" && row.kind !== "log")],
|
|
404
|
+
];
|
|
405
|
+
return groups
|
|
406
|
+
.filter(([, rows]) => rows.length > 0)
|
|
407
|
+
.map(([title, rows]) => `## ${title}\n\n${rows
|
|
408
|
+
.map((row) => `- ${row.createdAt === undefined ? "" : `${row.createdAt.slice(0, 10)}: `}${row.content}`)
|
|
409
|
+
.join("\n")}`)
|
|
410
|
+
.join("\n\n");
|
|
411
|
+
}
|
|
412
|
+
function emitInstructions(bot, answers, out, slack, knowledge) {
|
|
413
|
+
const sections = [`# ${bot.name}`, answers.description];
|
|
414
|
+
const from = ["profile"];
|
|
415
|
+
if (bot.gettingStarted !== undefined) {
|
|
416
|
+
sections.push(`## Getting started\n\nWhen someone talks to you for the first time, start with the \`${bot.gettingStarted}\` skill.`);
|
|
417
|
+
from.push("gettingStarted");
|
|
418
|
+
}
|
|
419
|
+
if (slack.sections.length > 0) {
|
|
420
|
+
sections.push([
|
|
421
|
+
"## Slack",
|
|
422
|
+
...slack.sections.map((section) => `### ${section.title}\n\n${section.body}`),
|
|
423
|
+
].join("\n\n"));
|
|
424
|
+
from.push(...slack.sections.map((section) => section.from));
|
|
425
|
+
}
|
|
426
|
+
if (knowledge !== undefined) {
|
|
427
|
+
sections.push(`## What you know\n\nWhat you already know about your user and team is in the \`${knowledge}\` skill. Read it before answering questions about people, preferences, or past decisions.`);
|
|
428
|
+
from.push("memory");
|
|
429
|
+
}
|
|
430
|
+
sections.push(JOURNAL_INSTRUCTIONS.trim());
|
|
431
|
+
emit(out, projectPath(out.root, "instructions.md"), `${sections.join("\n\n")}\n`, ...from);
|
|
432
|
+
}
|
|
433
|
+
function renderAgentTs(bot, answers, out) {
|
|
434
|
+
const model = formatModelLiteral(answers.model === DEFAULT_MODEL_ID ? DEFAULT_MODEL : answers.model);
|
|
435
|
+
const lines = [
|
|
436
|
+
`import { defineAgent } from "${PACKAGE_NAME}";`,
|
|
437
|
+
"",
|
|
438
|
+
"export default defineAgent({",
|
|
439
|
+
` name: ${JSON.stringify(bot.name)},`,
|
|
440
|
+
` description: ${JSON.stringify(oneLine(answers.description))},`,
|
|
441
|
+
` model: ${model},`,
|
|
442
|
+
];
|
|
443
|
+
const secretNames = [...out.secrets.keys()].sort();
|
|
444
|
+
const egress = [...out.egress].sort();
|
|
445
|
+
if (secretNames.length > 0 || egress.length > 0) {
|
|
446
|
+
lines.push(" hosting: {");
|
|
447
|
+
if (secretNames.length > 0) {
|
|
448
|
+
lines.push(` secretNames: [${secretNames.map((name) => JSON.stringify(name)).join(", ")}],`);
|
|
449
|
+
}
|
|
450
|
+
if (egress.length > 0) {
|
|
451
|
+
lines.push(` egressDomains: [${egress.map((host) => JSON.stringify(host)).join(", ")}],`);
|
|
452
|
+
}
|
|
453
|
+
lines.push(" },");
|
|
454
|
+
}
|
|
455
|
+
lines.push("});", "");
|
|
456
|
+
return lines.join("\n");
|
|
457
|
+
}
|
|
458
|
+
function renderExportRecord(args) {
|
|
459
|
+
const { input, slack } = args;
|
|
460
|
+
const record = {
|
|
461
|
+
version: EXPORT_RECORD_VERSION,
|
|
462
|
+
generatedAt: input.generatedAt,
|
|
463
|
+
generator: args.generator,
|
|
464
|
+
recipe: { name: input.bot.name, avatar: input.bot.avatar },
|
|
465
|
+
secrets: args.secrets,
|
|
466
|
+
slackTokens: slack === undefined ? null : [slack.keys.bot, slack.keys.app],
|
|
467
|
+
answers: input.resolved.answers,
|
|
468
|
+
};
|
|
469
|
+
return `${JSON.stringify(record, null, 2)}\n`;
|
|
470
|
+
}
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The files that carry an export's follow-up work: SECRETS.md, SLACK.md
|
|
3
|
+
* (app plan, review justification, scopes), a finish-the-export skill, an
|
|
4
|
+
* AGENTS.md that points at all three, and a Cloud Agent environment. Coding
|
|
5
|
+
* agents read these as instructions, so they name the project by its
|
|
6
|
+
* validated slug and keep recipe text to single quoted lines.
|
|
7
|
+
*/
|
|
8
|
+
import type { ProjectRoot } from "../project-layout.js";
|
|
9
|
+
import type { ResolvedAnswers, ResolvedSlack } from "./answers.js";
|
|
10
|
+
import type { GrokbotPreview, Source } from "./convert.js";
|
|
11
|
+
export declare const EXPORT_RECORD_PATH = "grokbot-export.json";
|
|
12
|
+
export declare const SECRETS_PATH = "SECRETS.md";
|
|
13
|
+
export declare const SLACK_PATH = "SLACK.md";
|
|
14
|
+
export declare const FINISH_SKILL_PATH = ".cursor/skills/finish-grokbot-export/SKILL.md";
|
|
15
|
+
/** Where a secret is read: a project file, OAuth for a connection, or only the answers. */
|
|
16
|
+
export interface SecretUse {
|
|
17
|
+
file?: string;
|
|
18
|
+
oauth?: boolean;
|
|
19
|
+
}
|
|
20
|
+
export interface SlackApp {
|
|
21
|
+
answers: ResolvedSlack;
|
|
22
|
+
/** The `slack create` command that mints a new app. */
|
|
23
|
+
create: string;
|
|
24
|
+
keys: {
|
|
25
|
+
bot: string;
|
|
26
|
+
app: string;
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
export interface HandoffInput {
|
|
30
|
+
root: ProjectRoot;
|
|
31
|
+
answers: ResolvedAnswers;
|
|
32
|
+
preview: GrokbotPreview;
|
|
33
|
+
secrets: ReadonlyMap<string, SecretUse>;
|
|
34
|
+
/** Deploy slug, when the directory name makes a valid one. */
|
|
35
|
+
slug?: string;
|
|
36
|
+
generator: string;
|
|
37
|
+
slack?: SlackApp;
|
|
38
|
+
}
|
|
39
|
+
export declare function handoffFiles(input: HandoffInput): Array<{
|
|
40
|
+
path: string;
|
|
41
|
+
contents: string;
|
|
42
|
+
from: Source;
|
|
43
|
+
}>;
|
|
44
|
+
//# sourceMappingURL=handoff.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"handoff.d.ts","sourceRoot":"","sources":["../../../src/internal/convert-grokbot/handoff.ts"],"names":[],"mappings":"AAAA;;;;;;GAMG;AAMH,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AACxD,OAAO,KAAK,EAAE,eAAe,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAEnE,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAE3D,eAAO,MAAM,kBAAkB,wBAAwB,CAAC;AACxD,eAAO,MAAM,YAAY,eAAe,CAAC;AACzC,eAAO,MAAM,UAAU,aAAa,CAAC;AACrC,eAAO,MAAM,iBAAiB,kDAAkD,CAAC;AAEjF,2FAA2F;AAC3F,MAAM,WAAW,SAAS;IACxB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,KAAK,CAAC,EAAE,OAAO,CAAC;CACjB;AAED,MAAM,WAAW,QAAQ;IACvB,OAAO,EAAE,aAAa,CAAC;IACvB,uDAAuD;IACvD,MAAM,EAAE,MAAM,CAAC;IACf,IAAI,EAAE;QAAE,GAAG,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAA;KAAE,CAAC;CACpC;AAED,MAAM,WAAW,YAAY;IAC3B,IAAI,EAAE,WAAW,CAAC;IAClB,OAAO,EAAE,eAAe,CAAC;IACzB,OAAO,EAAE,cAAc,CAAC;IACxB,OAAO,EAAE,WAAW,CAAC,MAAM,EAAE,SAAS,CAAC,CAAC;IACxC,8DAA8D;IAC9D,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,CAAC,EAAE,QAAQ,CAAC;CAClB;AAED,wBAAgB,YAAY,CAC1B,KAAK,EAAE,YAAY,GAClB,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,QAAQ,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAAC,CAezD"}
|
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The files that carry an export's follow-up work: SECRETS.md, SLACK.md
|
|
3
|
+
* (app plan, review justification, scopes), a finish-the-export skill, an
|
|
4
|
+
* AGENTS.md that points at all three, and a Cloud Agent environment. Coding
|
|
5
|
+
* agents read these as instructions, so they name the project by its
|
|
6
|
+
* validated slug and keep recipe text to single quoted lines.
|
|
7
|
+
*/
|
|
8
|
+
import { buildSlackManifest } from "../../channels/slack/manifest.js";
|
|
9
|
+
import { CLI_COMMAND_NAME as CLI } from "../distribution.js";
|
|
10
|
+
import { serializeFrontmatter } from "../frontmatter.js";
|
|
11
|
+
import { agentsMd } from "../init-scaffold.js";
|
|
12
|
+
import { code, singleLine } from "./checks.js";
|
|
13
|
+
export const EXPORT_RECORD_PATH = "grokbot-export.json";
|
|
14
|
+
export const SECRETS_PATH = "SECRETS.md";
|
|
15
|
+
export const SLACK_PATH = "SLACK.md";
|
|
16
|
+
export const FINISH_SKILL_PATH = ".cursor/skills/finish-grokbot-export/SKILL.md";
|
|
17
|
+
export function handoffFiles(input) {
|
|
18
|
+
const files = [
|
|
19
|
+
{ path: SECRETS_PATH, contents: secretsMd(input), from: "answers" },
|
|
20
|
+
{ path: FINISH_SKILL_PATH, contents: finishSkill(input), from: "answers" },
|
|
21
|
+
{ path: "AGENTS.md", contents: agentsMdWithExport(input), from: "scaffold" },
|
|
22
|
+
{
|
|
23
|
+
path: ".cursor/environment.json",
|
|
24
|
+
contents: `${JSON.stringify({ name: input.answers.name, install: "npm install" }, null, 2)}\n`,
|
|
25
|
+
from: "scaffold",
|
|
26
|
+
},
|
|
27
|
+
];
|
|
28
|
+
if (input.slack !== undefined) {
|
|
29
|
+
files.push({ path: SLACK_PATH, contents: slackMd(input.slack), from: "answers" });
|
|
30
|
+
}
|
|
31
|
+
return files;
|
|
32
|
+
}
|
|
33
|
+
function secretUse(use) {
|
|
34
|
+
if (use.file === undefined) {
|
|
35
|
+
return "your own code (named in the answers)";
|
|
36
|
+
}
|
|
37
|
+
return use.oauth === true
|
|
38
|
+
? `OAuth for ${code(use.file)} (written by \`${CLI} mcp oauth\`)`
|
|
39
|
+
: code(use.file);
|
|
40
|
+
}
|
|
41
|
+
function secretsMd(input) {
|
|
42
|
+
const lines = [
|
|
43
|
+
"# Secrets",
|
|
44
|
+
"",
|
|
45
|
+
"The project reads these secrets by name. The Grok Bot recipe carried no values, so set each one before you run the agent.",
|
|
46
|
+
"",
|
|
47
|
+
];
|
|
48
|
+
if (input.secrets.size === 0) {
|
|
49
|
+
lines.push("None yet.");
|
|
50
|
+
}
|
|
51
|
+
else {
|
|
52
|
+
lines.push("| Name | Read by |", "| --- | --- |");
|
|
53
|
+
for (const [name, use] of [...input.secrets].sort(([a], [b]) => a.localeCompare(b))) {
|
|
54
|
+
lines.push(`| \`${name}\` | ${secretUse(use)} |`);
|
|
55
|
+
}
|
|
56
|
+
}
|
|
57
|
+
lines.push("", `Local runs read secrets from the environment. A deployment reads the values you store with \`${CLI} secrets set ${input.slug ?? "<slug>"} NAME...\`.`);
|
|
58
|
+
const reauth = input.preview.secrets.reauth;
|
|
59
|
+
if (reauth.length > 0) {
|
|
60
|
+
lines.push("", "## Fresh sign-ins", "", "These connectors need a new sign-in; tokens never move with an export.", "", ...reauth.map((slug) => `- \`${slug}\`: \`${CLI} mcp oauth ${slug}\` for an OAuth connector (add \`--store\` for a deployment), or reconnect it in your Cursor account.`));
|
|
61
|
+
}
|
|
62
|
+
return `${lines.join("\n")}\n`;
|
|
63
|
+
}
|
|
64
|
+
function cutoverLine(slack) {
|
|
65
|
+
switch (slack.cutover) {
|
|
66
|
+
case "manual":
|
|
67
|
+
return "switch Slack traffic to this agent by hand once it works.";
|
|
68
|
+
case "after-deploy":
|
|
69
|
+
return "switch Slack traffic to this agent after its first deploy.";
|
|
70
|
+
case "scheduled":
|
|
71
|
+
return `switch Slack traffic to this agent at ${slack.cutoverAt}.`;
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
function slackMd({ answers, create, keys }) {
|
|
75
|
+
const prefix = answers.teamPrefix === undefined ? "" : ` (team prefix ${code(answers.teamPrefix)})`;
|
|
76
|
+
const lines = [
|
|
77
|
+
"# Slack app",
|
|
78
|
+
"",
|
|
79
|
+
answers.app === "move"
|
|
80
|
+
? `- App: move the Grok Bot's existing Slack app. Put its bot token in \`${keys.bot}\` and its app-level token in \`${keys.app}\`.`
|
|
81
|
+
: `- App: mint a new one with ${code(create)}.`,
|
|
82
|
+
`- Bot name: ${code(answers.botName)}${prefix}`,
|
|
83
|
+
`- Cutover: ${cutoverLine(answers)}`,
|
|
84
|
+
"",
|
|
85
|
+
"## Security justification",
|
|
86
|
+
"",
|
|
87
|
+
"Paste this into the Slack app approval request.",
|
|
88
|
+
"",
|
|
89
|
+
...answers.justification.split(/\r\n?|\n/).map((line) => `> ${line}`.trimEnd()),
|
|
90
|
+
"",
|
|
91
|
+
"## Scopes",
|
|
92
|
+
"",
|
|
93
|
+
"The app requests these bot scopes:",
|
|
94
|
+
"",
|
|
95
|
+
...buildSlackManifest({ name: answers.botName, env: "prod" }).oauth_config.scopes.bot.map((scope) => `- \`${scope}\``),
|
|
96
|
+
];
|
|
97
|
+
return `${lines.join("\n")}\n`;
|
|
98
|
+
}
|
|
99
|
+
function deployLine(deploy) {
|
|
100
|
+
const command = `\`${CLI} deploy\``;
|
|
101
|
+
switch (deploy.when) {
|
|
102
|
+
case "after-review":
|
|
103
|
+
return `Deploy with ${command} once the steps above check out.`;
|
|
104
|
+
case "now":
|
|
105
|
+
return `Deploy with ${command} as soon as the steps above are done.`;
|
|
106
|
+
case "scheduled":
|
|
107
|
+
return `Deploy with ${command} at ${deploy.at}.`;
|
|
108
|
+
case "never":
|
|
109
|
+
return "No deploy is planned; keep the agent local.";
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
function finishSkill(input) {
|
|
113
|
+
const { answers, preview } = input;
|
|
114
|
+
const repo = answers.repo.namespace === undefined
|
|
115
|
+
? answers.repo.name
|
|
116
|
+
: `${answers.repo.namespace}/${answers.repo.name}`;
|
|
117
|
+
const steps = [
|
|
118
|
+
`Set the secrets in \`${SECRETS_PATH}\`.`,
|
|
119
|
+
...preview.setupSteps,
|
|
120
|
+
`Run \`${CLI} validate\`, then \`${CLI} dev\`, and try the agent in the playground.`,
|
|
121
|
+
`Push the project to a \`${repo}\` repository; the export does not create it.`,
|
|
122
|
+
deployLine(answers.deploy),
|
|
123
|
+
];
|
|
124
|
+
const lines = [
|
|
125
|
+
`# Finish the ${answers.name} export`,
|
|
126
|
+
"",
|
|
127
|
+
`${input.generator} generated this project from a Grok Bot recipe. \`${EXPORT_RECORD_PATH}\` records the recipe and every answer.`,
|
|
128
|
+
"",
|
|
129
|
+
...steps.map((step, index) => `${index + 1}. ${singleLine(step)}`),
|
|
130
|
+
];
|
|
131
|
+
const leftBehind = [
|
|
132
|
+
...preview.excluded.map((from) => `- ${code(from)}: left out by the answers.`),
|
|
133
|
+
...preview.unmapped.map((entry) => `- ${code(entry.from)}: ${singleLine(entry.reason)}`),
|
|
134
|
+
];
|
|
135
|
+
if (leftBehind.length > 0) {
|
|
136
|
+
lines.push("", "## Not carried over", "", ...leftBehind);
|
|
137
|
+
}
|
|
138
|
+
if (preview.warnings.length > 0) {
|
|
139
|
+
lines.push("", "## Review before deploying", "", ...preview.warnings.map((warning) => `- ${singleLine(warning)}`));
|
|
140
|
+
}
|
|
141
|
+
const frontmatter = serializeFrontmatter({
|
|
142
|
+
name: "finish-grokbot-export",
|
|
143
|
+
description: `Finish moving ${answers.name} off Grok Bot: secrets, connector sign-ins, the Slack app, and deploy. Use when asked to finish, deploy, or cut over this exported agent.`,
|
|
144
|
+
});
|
|
145
|
+
return `${frontmatter}${lines.join("\n")}\n`;
|
|
146
|
+
}
|
|
147
|
+
function agentsMdWithExport(input) {
|
|
148
|
+
const files = [
|
|
149
|
+
`\`${EXPORT_RECORD_PATH}\` records the recipe and every answer`,
|
|
150
|
+
`\`${SECRETS_PATH}\` lists the secrets it reads`,
|
|
151
|
+
];
|
|
152
|
+
if (input.slack !== undefined) {
|
|
153
|
+
files.push(`\`${SLACK_PATH}\` holds the Slack app plan and review text`);
|
|
154
|
+
}
|
|
155
|
+
return `${agentsMd(input.answers.name, input.root)}
|
|
156
|
+
## Exported from Grok Bot
|
|
157
|
+
|
|
158
|
+
This project came from a Grok Bot recipe. ${files.join(", ")}, and \`${FINISH_SKILL_PATH}\` lists what is left to do.
|
|
159
|
+
`;
|
|
160
|
+
}
|