@cursor/bdk 0.2.3 → 0.2.4
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/bin/agent-serve.js +9 -1
- package/dist/channels/slack/attachments.d.ts +2 -1
- package/dist/channels/slack/attachments.d.ts.map +1 -1
- package/dist/channels/slack/attachments.js +19 -9
- package/dist/channels/slack/dispatch.d.ts.map +1 -1
- package/dist/channels/slack/dispatch.js +26 -24
- package/dist/channels/slack/thread-context.d.ts +21 -11
- package/dist/channels/slack/thread-context.d.ts.map +1 -1
- package/dist/channels/slack/thread-context.js +75 -27
- package/dist/docs/404.html +2 -2
- package/dist/docs/assets/{app.BOIHhrKi.js → app.4kQ8Db_q.js} +4 -4
- package/dist/docs/assets/chunks/@localSearchIndexroot.CvuAJ0My.js +1 -0
- package/dist/docs/assets/chunks/{VPLocalSearchBox.D49zVZqM.js → VPLocalSearchBox.DY1RwB8Q.js} +1 -1
- package/dist/docs/assets/chunks/{arc.hmjb-sc4.js → arc.CxE_fSPK.js} +1 -1
- package/dist/docs/assets/chunks/{architectureDiagram-Q4EWVU46.CxEI1KqM.js → architectureDiagram-Q4EWVU46.CPX426ui.js} +1 -1
- package/dist/docs/assets/chunks/{baseUniq.DHHvBWoV.js → baseUniq.CB52JrKG.js} +1 -1
- package/dist/docs/assets/chunks/{blockDiagram-DXYQGD6D.DnXW-3bu.js → blockDiagram-DXYQGD6D.J0cNaQCL.js} +1 -1
- package/dist/docs/assets/chunks/{c4Diagram-AHTNJAMY.e-47O2jM.js → c4Diagram-AHTNJAMY.DJn3vEGT.js} +1 -1
- package/dist/docs/assets/chunks/channel.BoNycAoN.js +1 -0
- package/dist/docs/assets/chunks/{chunk-4BX2VUAB.3ry4pYXB.js → chunk-4BX2VUAB.Dao618F6.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-4TB4RGXK.DGIZFRx6.js → chunk-4TB4RGXK.QW8Rhjai.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-55IACEB6.DKBnqg9U.js → chunk-55IACEB6.DfRLLKF_.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-EDXVE4YY.BIU8Ue5k.js → chunk-EDXVE4YY.CIV2ApKQ.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-FMBD7UC4.DP-TFhjI.js → chunk-FMBD7UC4.BEheSuxp.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-OYMX7WX6.Ux0OYj5v.js → chunk-OYMX7WX6.CUN88ENB.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-QZHKN3VN.BzHMwYox.js → chunk-QZHKN3VN.CgqCs8b_.js} +1 -1
- package/dist/docs/assets/chunks/{chunk-YZCP3GAM.D4OGAsSP.js → chunk-YZCP3GAM.iCH0nnTJ.js} +1 -1
- package/dist/docs/assets/chunks/classDiagram-6PBFFD2Q.C4x07Gkj.js +1 -0
- package/dist/docs/assets/chunks/classDiagram-v2-HSJHXN6E.C4x07Gkj.js +1 -0
- package/dist/docs/assets/chunks/clone.Db22cH_-.js +1 -0
- package/dist/docs/assets/chunks/{cose-bilkent-S5V4N54A.Jq_7BUNx.js → cose-bilkent-S5V4N54A.BLcUxhWE.js} +1 -1
- package/dist/docs/assets/chunks/{dagre-KV5264BT.Di-skR2x.js → dagre-KV5264BT.Ep7LofOm.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-5BDNPKRD.DeREHIdH.js → diagram-5BDNPKRD.Bzf4GSQ4.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-G4DWMVQ6.C7Kcqxro.js → diagram-G4DWMVQ6.DD6Jh-eM.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-MMDJMWI5.BK3eohyo.js → diagram-MMDJMWI5.oOIl8bWd.js} +1 -1
- package/dist/docs/assets/chunks/{diagram-TYMM5635.C6TyymXT.js → diagram-TYMM5635.DHs85Ade.js} +1 -1
- package/dist/docs/assets/chunks/{erDiagram-SMLLAGMA.DYGG-gGx.js → erDiagram-SMLLAGMA.BIb5ghCk.js} +1 -1
- package/dist/docs/assets/chunks/{flowDiagram-DWJPFMVM.C9nBcSV4.js → flowDiagram-DWJPFMVM.DV4paY9k.js} +1 -1
- package/dist/docs/assets/chunks/{ganttDiagram-T4ZO3ILL.wAg_ymsp.js → ganttDiagram-T4ZO3ILL.AyEKA6_v.js} +1 -1
- package/dist/docs/assets/chunks/{gitGraphDiagram-UUTBAWPF.B87j9Oeg.js → gitGraphDiagram-UUTBAWPF.BltiCDFo.js} +1 -1
- package/dist/docs/assets/chunks/{graph.CuFMj31w.js → graph.DzuEYGdC.js} +1 -1
- package/dist/docs/assets/chunks/{infoDiagram-42DDH7IO.P_mLGumP.js → infoDiagram-42DDH7IO.BV2l981J.js} +1 -1
- package/dist/docs/assets/chunks/{ishikawaDiagram-UXIWVN3A.DyuL_MsT.js → ishikawaDiagram-UXIWVN3A.BA4Izf-m.js} +1 -1
- package/dist/docs/assets/chunks/{journeyDiagram-VCZTEJTY.CtP09IoJ.js → journeyDiagram-VCZTEJTY.DjaFbFS3.js} +1 -1
- package/dist/docs/assets/chunks/{kanban-definition-6JOO6SKY.BoeSYPZo.js → kanban-definition-6JOO6SKY.CfTFieDs.js} +1 -1
- package/dist/docs/assets/chunks/{layout.B0lMMtNo.js → layout.DzfWqTBV.js} +1 -1
- package/dist/docs/assets/chunks/{linear.HxRBiAFX.js → linear.BO6mpulV.js} +1 -1
- package/dist/docs/assets/chunks/{min.BGlFFHwS.js → min.BGgTadgT.js} +1 -1
- package/dist/docs/assets/chunks/{mindmap-definition-QFDTVHPH.JyLBD9M8.js → mindmap-definition-QFDTVHPH.DPuIXVWY.js} +1 -1
- package/dist/docs/assets/chunks/{pieDiagram-DEJITSTG.DnSmNZF8.js → pieDiagram-DEJITSTG.BOnl3bBg.js} +1 -1
- package/dist/docs/assets/chunks/{quadrantDiagram-34T5L4WZ.CUCnbfCa.js → quadrantDiagram-34T5L4WZ.DNB6Ckdc.js} +1 -1
- package/dist/docs/assets/chunks/{requirementDiagram-MS252O5E.py0IVUn5.js → requirementDiagram-MS252O5E.D5-Qo7vb.js} +1 -1
- package/dist/docs/assets/chunks/{sankeyDiagram-XADWPNL6.Bkc-HWYp.js → sankeyDiagram-XADWPNL6.8t65cesf.js} +1 -1
- package/dist/docs/assets/chunks/{sequenceDiagram-FGHM5R23.Dqn8Mlv2.js → sequenceDiagram-FGHM5R23.CaG07BdS.js} +1 -1
- package/dist/docs/assets/chunks/{stateDiagram-FHFEXIEX.JikkoQUU.js → stateDiagram-FHFEXIEX.TKOweTB6.js} +1 -1
- package/dist/docs/assets/chunks/stateDiagram-v2-QKLJ7IA2.CuqmyQc4.js +1 -0
- package/dist/docs/assets/chunks/{theme.b6HQ6zG_.js → theme.Dx-JhpTB.js} +2 -2
- package/dist/docs/assets/chunks/{timeline-definition-GMOUNBTQ.BvpSXiBj.js → timeline-definition-GMOUNBTQ.fE53zQ2s.js} +1 -1
- package/dist/docs/assets/chunks/{vennDiagram-DHZGUBPP.CU7MVnZx.js → vennDiagram-DHZGUBPP.DJsZZaJg.js} +1 -1
- package/dist/docs/assets/chunks/{wardley-RL74JXVD.BKwC4ctG.js → wardley-RL74JXVD.844kyrjl.js} +1 -1
- package/dist/docs/assets/chunks/{wardleyDiagram-NUSXRM2D.BfaF6Uhe.js → wardleyDiagram-NUSXRM2D.CMZ-Ru_t.js} +1 -1
- package/dist/docs/assets/chunks/{xychartDiagram-5P7HB3ND.Bg5dcpj4.js → xychartDiagram-5P7HB3ND.XXrhBc7a.js} +1 -1
- package/dist/docs/assets/{deployment.md.BJ8i7Q6p.js → deployment.md.UhnJIMr-.js} +2 -2
- package/dist/docs/assets/{deployment.md.BJ8i7Q6p.lean.js → deployment.md.UhnJIMr-.lean.js} +1 -1
- package/dist/docs/assets/{guides_jev.md.BNDm14Gy.js → guides_jev.md.CRcgmjDb.js} +2 -2
- package/dist/docs/assets/{guides_jev.md.BNDm14Gy.lean.js → guides_jev.md.CRcgmjDb.lean.js} +1 -1
- package/dist/docs/assets/{reference_agent-config.md.DzGI777n.js → reference_agent-config.md.Cj5uBKp4.js} +1 -1
- package/dist/docs/assets/{reference_extensions.md.CPPrkWlJ.js → reference_extensions.md.pa2tN-e4.js} +4 -3
- package/dist/docs/assets/{reference_extensions.md.CPPrkWlJ.lean.js → reference_extensions.md.pa2tN-e4.lean.js} +1 -1
- package/dist/docs/building-with-agents.html +35 -35
- package/dist/docs/deployment.html +37 -37
- package/dist/docs/deployment.md +4 -1
- package/dist/docs/evals.html +35 -35
- 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 +35 -35
- 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 +35 -35
- package/dist/docs/guides/hooks.html +35 -35
- package/dist/docs/guides/improve.html +35 -35
- package/dist/docs/guides/jev.html +37 -37
- package/dist/docs/guides/jev.md +7 -0
- package/dist/docs/guides/mcp-oauth.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 +35 -35
- package/dist/docs/hashmap.json +1 -1
- package/dist/docs/hillclimbing.html +35 -35
- package/dist/docs/index.html +35 -35
- package/dist/docs/llms-full.txt +25 -2
- package/dist/docs/quickstart.html +35 -35
- package/dist/docs/reference/agent-config.html +37 -37
- package/dist/docs/reference/agent-config.md +1 -1
- package/dist/docs/reference/artifacts.html +35 -35
- package/dist/docs/reference/channels.html +35 -35
- package/dist/docs/reference/cli.html +35 -35
- package/dist/docs/reference/connections.html +35 -35
- package/dist/docs/reference/evals.html +35 -35
- package/dist/docs/reference/extensions.html +39 -38
- package/dist/docs/reference/extensions.md +13 -0
- package/dist/docs/reference/hooks.html +35 -35
- package/dist/docs/reference/http-api.html +35 -35
- package/dist/docs/reference/instructions.html +35 -35
- package/dist/docs/reference/playground.html +35 -35
- package/dist/docs/reference/project-layout.html +35 -35
- package/dist/docs/reference/prompt.html +35 -35
- package/dist/docs/reference/schedules.html +35 -35
- package/dist/docs/reference/sessions.html +35 -35
- package/dist/docs/reference/skills.html +35 -35
- package/dist/docs/reference/subagents.html +35 -35
- package/dist/docs/reference/tools.html +35 -35
- package/dist/docs/templates/agentic-owners.html +35 -35
- 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 +35 -35
- package/dist/extensions/jev/extension.d.ts +3 -0
- package/dist/extensions/jev/extension.d.ts.map +1 -1
- package/dist/extensions/jev/extension.js +10 -1
- package/dist/extensions/jev/lib/evaluate.d.ts +4 -0
- package/dist/extensions/jev/lib/evaluate.d.ts.map +1 -1
- package/dist/extensions/jev/lib/evaluate.js +6 -2
- package/dist/extensions.d.ts +4 -2
- package/dist/extensions.d.ts.map +1 -1
- package/dist/extensions.js +5 -2
- package/dist/internal/cli-deploy.d.ts.map +1 -1
- package/dist/internal/cli-deploy.js +19 -5
- package/dist/internal/discovery/agent-config.d.ts +6 -5
- package/dist/internal/discovery/agent-config.d.ts.map +1 -1
- package/dist/internal/discovery/agent-config.js +29 -28
- package/dist/internal/discovery/agent.js +1 -1
- package/dist/internal/discovery/extensions.d.ts.map +1 -1
- package/dist/internal/discovery/extensions.js +12 -0
- package/dist/internal/hosting.d.ts +8 -0
- package/dist/internal/hosting.d.ts.map +1 -1
- package/dist/internal/hosting.js +24 -0
- package/dist/types.d.ts +18 -2
- package/dist/types.d.ts.map +1 -1
- package/docs/deployment.md +4 -1
- package/docs/guides/jev.md +7 -0
- package/docs/reference/agent-config.md +1 -1
- package/docs/reference/extensions.md +13 -0
- package/package.json +1 -9
- package/dist/docs/assets/chunks/@localSearchIndexroot.D5L-b34G.js +0 -1
- package/dist/docs/assets/chunks/channel.BbOGaJQP.js +0 -1
- package/dist/docs/assets/chunks/classDiagram-6PBFFD2Q.Db58HCb1.js +0 -1
- package/dist/docs/assets/chunks/classDiagram-v2-HSJHXN6E.Db58HCb1.js +0 -1
- package/dist/docs/assets/chunks/clone.Co4MBflG.js +0 -1
- package/dist/docs/assets/chunks/stateDiagram-v2-QKLJ7IA2.CMsKhrW0.js +0 -1
- package/src/artifacts.ts +0 -68
- package/src/bin/agent-serve.ts +0 -1854
- package/src/channels/bitbucket/api.ts +0 -891
- package/src/channels/bitbucket/binding.ts +0 -417
- package/src/channels/bitbucket/bitbucket-channel.ts +0 -162
- package/src/channels/bitbucket/bitbucket-webhook.ts +0 -519
- package/src/channels/bitbucket/checks.ts +0 -146
- package/src/channels/bitbucket/cursor-account.ts +0 -106
- package/src/channels/bitbucket/defaults.ts +0 -100
- package/src/channels/bitbucket/events.ts +0 -74
- package/src/channels/bitbucket/index.ts +0 -51
- package/src/channels/bitbucket/replay.ts +0 -421
- package/src/channels/bitbucket/state.ts +0 -59
- package/src/channels/bitbucket/types.ts +0 -261
- package/src/channels/change-monitors/change-monitors-channel.ts +0 -63
- package/src/channels/change-monitors/index.ts +0 -8
- package/src/channels/change-monitors/types.ts +0 -42
- package/src/channels/checks.ts +0 -185
- package/src/channels/deployments/deployments-channel.ts +0 -224
- package/src/channels/deployments/index.ts +0 -25
- package/src/channels/deployments/types.ts +0 -92
- package/src/channels/github/api.ts +0 -526
- package/src/channels/github/auth.ts +0 -293
- package/src/channels/github/binding.ts +0 -233
- package/src/channels/github/checks.ts +0 -145
- package/src/channels/github/cursor-account.ts +0 -303
- package/src/channels/github/defaults.ts +0 -168
- package/src/channels/github/events.ts +0 -67
- package/src/channels/github/forward.ts +0 -359
- package/src/channels/github/github-channel.ts +0 -2334
- package/src/channels/github/index.ts +0 -54
- package/src/channels/github/progress.ts +0 -365
- package/src/channels/github/replay.ts +0 -372
- package/src/channels/github/state.ts +0 -124
- package/src/channels/github/types.ts +0 -590
- package/src/channels/gitlab/api.ts +0 -329
- package/src/channels/gitlab/binding.ts +0 -231
- package/src/channels/gitlab/checks.ts +0 -228
- package/src/channels/gitlab/cursor-account.ts +0 -105
- package/src/channels/gitlab/defaults.ts +0 -80
- package/src/channels/gitlab/events.ts +0 -37
- package/src/channels/gitlab/gitlab-channel.ts +0 -160
- package/src/channels/gitlab/gitlab-webhook.ts +0 -509
- package/src/channels/gitlab/index.ts +0 -44
- package/src/channels/gitlab/replay.ts +0 -328
- package/src/channels/gitlab/state.ts +0 -55
- package/src/channels/gitlab/types.ts +0 -247
- package/src/channels/issues/index.ts +0 -9
- package/src/channels/issues/issues-channel.ts +0 -45
- package/src/channels/issues/types.ts +0 -38
- package/src/channels/origin/api.ts +0 -507
- package/src/channels/origin/binding.ts +0 -114
- package/src/channels/origin/checks.ts +0 -250
- package/src/channels/origin/cursor-account.ts +0 -58
- package/src/channels/origin/defaults.ts +0 -140
- package/src/channels/origin/events.ts +0 -35
- package/src/channels/origin/index.ts +0 -35
- package/src/channels/origin/origin-channel.ts +0 -815
- package/src/channels/origin/origin-webhook.ts +0 -296
- package/src/channels/origin/reactions.ts +0 -72
- package/src/channels/origin/state.ts +0 -54
- package/src/channels/origin/types.ts +0 -295
- package/src/channels/slack/agentic-delivery.ts +0 -634
- package/src/channels/slack/agentic-posted.ts +0 -135
- package/src/channels/slack/agentic-signals.ts +0 -231
- package/src/channels/slack/api.ts +0 -761
- package/src/channels/slack/approvals.ts +0 -279
- package/src/channels/slack/assistant.ts +0 -76
- package/src/channels/slack/attachments.ts +0 -596
- package/src/channels/slack/auth.ts +0 -127
- package/src/channels/slack/blocks.ts +0 -131
- package/src/channels/slack/bot-mentions.ts +0 -318
- package/src/channels/slack/channel-watch.ts +0 -314
- package/src/channels/slack/cli-project.ts +0 -249
- package/src/channels/slack/code-fences.ts +0 -171
- package/src/channels/slack/constants.ts +0 -38
- package/src/channels/slack/credentials.ts +0 -88
- package/src/channels/slack/defaults.ts +0 -714
- package/src/channels/slack/dispatch.ts +0 -1060
- package/src/channels/slack/doctor.ts +0 -338
- package/src/channels/slack/eval-directive.ts +0 -306
- package/src/channels/slack/event-id-dedupe.ts +0 -30
- package/src/channels/slack/external-policy.ts +0 -75
- package/src/channels/slack/footer.ts +0 -106
- package/src/channels/slack/inbound.ts +0 -416
- package/src/channels/slack/index.ts +0 -53
- package/src/channels/slack/init.ts +0 -169
- package/src/channels/slack/interactive.ts +0 -406
- package/src/channels/slack/links.ts +0 -23
- package/src/channels/slack/live-delivery.ts +0 -489
- package/src/channels/slack/log.ts +0 -70
- package/src/channels/slack/manifest.ts +0 -240
- package/src/channels/slack/message-body.ts +0 -82
- package/src/channels/slack/nudge-carrier.ts +0 -224
- package/src/channels/slack/nudge-store.ts +0 -334
- package/src/channels/slack/paint-start.ts +0 -93
- package/src/channels/slack/placeholder.ts +0 -358
- package/src/channels/slack/pr-ref.ts +0 -74
- package/src/channels/slack/progress-delivery.ts +0 -138
- package/src/channels/slack/reasoning-card.ts +0 -125
- package/src/channels/slack/reasoning-chip.ts +0 -41
- package/src/channels/slack/recording-sink.ts +0 -167
- package/src/channels/slack/redact.ts +0 -6
- package/src/channels/slack/reply-options.ts +0 -279
- package/src/channels/slack/setup.ts +0 -125
- package/src/channels/slack/slack-channel.ts +0 -744
- package/src/channels/slack/socket-mode.ts +0 -140
- package/src/channels/slack/stop.ts +0 -25
- package/src/channels/slack/stream.ts +0 -66
- package/src/channels/slack/thread-context.ts +0 -485
- package/src/channels/slack/tool-approval-events.ts +0 -233
- package/src/channels/slack/tool-cards.ts +0 -198
- package/src/channels/slack/tool-chip.ts +0 -34
- package/src/channels/slack/types.ts +0 -787
- package/src/channels/slack/upload.ts +0 -137
- package/src/channels.ts +0 -543
- package/src/connections.ts +0 -153
- package/src/dashboard-session-url.ts +0 -30
- package/src/evals/assertions.ts +0 -688
- package/src/evals/expect.ts +0 -250
- package/src/evals/judge.ts +0 -329
- package/src/evals/loaders.ts +0 -111
- package/src/evals/matchers.ts +0 -223
- package/src/evals/reporters.ts +0 -257
- package/src/evals/results.ts +0 -130
- package/src/evals/run-facts.ts +0 -306
- package/src/evals.ts +0 -709
- package/src/extensions/cursor-cloud-agents/extension.ts +0 -131
- package/src/extensions/cursor-cloud-agents/lib/backend.ts +0 -386
- package/src/extensions/cursor-cloud-agents/lib/channels.ts +0 -11
- package/src/extensions/cursor-cloud-agents/lib/fleet.ts +0 -98
- package/src/extensions/cursor-cloud-agents/lib/inputs.ts +0 -5
- package/src/extensions/cursor-cloud-agents/lib/repos.ts +0 -80
- package/src/extensions/cursor-cloud-agents/lib/transcript.ts +0 -19
- package/src/extensions/cursor-cloud-agents/skills/handoff.md +0 -37
- package/src/extensions/cursor-cloud-agents/tools/cancel.ts +0 -21
- package/src/extensions/cursor-cloud-agents/tools/dump.ts +0 -47
- package/src/extensions/cursor-cloud-agents/tools/get.ts +0 -18
- package/src/extensions/cursor-cloud-agents/tools/launch.ts +0 -62
- package/src/extensions/cursor-cloud-agents/tools/list.ts +0 -31
- package/src/extensions/cursor-cloud-agents/tools/reply.ts +0 -36
- package/src/extensions/cursor-grokbot-agents/extension.ts +0 -132
- package/src/extensions/cursor-grokbot-agents/lib/agents.ts +0 -42
- package/src/extensions/cursor-grokbot-agents/lib/backend.ts +0 -208
- package/src/extensions/cursor-grokbot-agents/lib/contacts.ts +0 -74
- package/src/extensions/cursor-grokbot-agents/lib/conversation.ts +0 -260
- package/src/extensions/cursor-grokbot-agents/lib/inputs.ts +0 -21
- package/src/extensions/cursor-grokbot-agents/lib/lock.ts +0 -26
- package/src/extensions/cursor-grokbot-agents/skills/consult.md +0 -40
- package/src/extensions/cursor-grokbot-agents/tools/ask.ts +0 -32
- package/src/extensions/cursor-grokbot-agents/tools/check.ts +0 -25
- package/src/extensions/cursor-grokbot-agents/tools/interrupt.ts +0 -17
- package/src/extensions/cursor-grokbot-agents/tools/list.ts +0 -26
- package/src/extensions/improve/extension.ts +0 -69
- package/src/extensions/improve/skills/yourself.ts +0 -50
- package/src/extensions/jev/extension.ts +0 -95
- package/src/extensions/jev/lib/evaluate.ts +0 -266
- package/src/extensions/jev/skills/gated-write.md +0 -25
- package/src/extensions/jev/skills/questions.md +0 -33
- package/src/extensions/jev/tools/evaluate.ts +0 -82
- package/src/extensions/slack-communication/evals/harness.ts +0 -705
- package/src/extensions/slack-communication/evals/slack-communication.eval.ts +0 -830
- package/src/extensions/slack-communication/evals/slack-placeholder.eval.ts +0 -172
- package/src/extensions/slack-communication/extension.ts +0 -44
- package/src/extensions/slack-communication/skills/slack-voice.ts +0 -56
- package/src/extensions/slack-communication/tools/delete-message.ts +0 -33
- package/src/extensions/slack-communication/tools/edit-message.ts +0 -42
- package/src/extensions/slack-communication/tools/post-card.ts +0 -28
- package/src/extensions/slack-communication/tools/post-file.ts +0 -82
- package/src/extensions/slack-communication/tools/post-update.ts +0 -40
- package/src/extensions/slack-communication/tools/react.ts +0 -30
- package/src/extensions/slack-communication/tools/set-status.ts +0 -21
- package/src/extensions.ts +0 -179
- package/src/files-backends/agent-store-presigned-url.ts +0 -11
- package/src/files-backends/cursor-hosted.ts +0 -1212
- package/src/files-backends/local-fs.ts +0 -163
- package/src/files.ts +0 -293
- package/src/filesystem.ts +0 -2005
- package/src/hooks.ts +0 -30
- package/src/index.ts +0 -259
- package/src/internal/advertise-tools.ts +0 -370
- package/src/internal/approval-gate.ts +0 -103
- package/src/internal/artifacts-store.ts +0 -836
- package/src/internal/as-of.ts +0 -257
- package/src/internal/auth.ts +0 -46
- package/src/internal/authored-alias-hooks.ts +0 -138
- package/src/internal/authored-loaders.ts +0 -188
- package/src/internal/bounded-int.ts +0 -24
- package/src/internal/bounded.ts +0 -25
- package/src/internal/brand.ts +0 -28
- package/src/internal/browser-origin-guard.ts +0 -67
- package/src/internal/builtin-tools/artifacts.ts +0 -62
- package/src/internal/builtin-tools/index.ts +0 -53
- package/src/internal/builtin-tools/reminders.ts +0 -145
- package/src/internal/channel-dispatch.ts +0 -129
- package/src/internal/channel-route-dispatch.ts +0 -58
- package/src/internal/channel-state.ts +0 -83
- package/src/internal/chat-client.ts +0 -594
- package/src/internal/cli-ax.ts +0 -2318
- package/src/internal/cli-bitbucket.ts +0 -438
- package/src/internal/cli-convert-automation.ts +0 -335
- package/src/internal/cli-cursor.ts +0 -282
- package/src/internal/cli-deploy.ts +0 -2519
- package/src/internal/cli-docs.ts +0 -192
- package/src/internal/cli-github.ts +0 -806
- package/src/internal/cli-gitlab.ts +0 -452
- package/src/internal/cli-images.ts +0 -672
- package/src/internal/cli-manifest.ts +0 -56
- package/src/internal/cli-mcp-oauth.ts +0 -396
- package/src/internal/cli-mcp.ts +0 -808
- package/src/internal/cli-skills.ts +0 -98
- package/src/internal/cli-slack-manual.ts +0 -418
- package/src/internal/cli-slack.ts +0 -874
- package/src/internal/cloud-merge.ts +0 -51
- package/src/internal/cloud-turn-cost.ts +0 -159
- package/src/internal/connection-env.ts +0 -106
- package/src/internal/continuation-channel.ts +0 -233
- package/src/internal/continuation-identity.ts +0 -935
- package/src/internal/conversation-mirror.ts +0 -423
- package/src/internal/convert-automation/convert-workflow.ts +0 -1377
- package/src/internal/convert-automation/slug.ts +0 -29
- package/src/internal/convert-automation/types.ts +0 -212
- package/src/internal/cron.ts +0 -76
- package/src/internal/cursor/account-mcp.ts +0 -692
- package/src/internal/cursor/backend-client.ts +0 -984
- package/src/internal/cursor/bound-secret-file.ts +0 -101
- package/src/internal/cursor/credentials.ts +0 -560
- package/src/internal/cursor/cursor-api-transport.ts +0 -65
- package/src/internal/cursor/github-credentials.ts +0 -228
- package/src/internal/cursor/hosted-bound-secrets.ts +0 -71
- package/src/internal/cursor/hosted-deployment-secrets.ts +0 -100
- package/src/internal/cursor/hosted-store-secrets.ts +0 -152
- package/src/internal/cursor/session-token.ts +0 -111
- package/src/internal/cursor/store-api-client.ts +0 -323
- package/src/internal/cursor-account-mcp-auth.ts +0 -303
- package/src/internal/cursor-agent-template.ts +0 -50
- package/src/internal/cursor-deployment-relay.ts +0 -315
- package/src/internal/cursor-event-relay.ts +0 -675
- package/src/internal/cursor-relay-core.ts +0 -563
- package/src/internal/deferred-channel-session.ts +0 -61
- package/src/internal/deploy-client.ts +0 -1574
- package/src/internal/deploy-manifest.ts +0 -361
- package/src/internal/deploy-source.ts +0 -144
- package/src/internal/describe-error.ts +0 -32
- package/src/internal/dev-mode.ts +0 -20
- package/src/internal/discovery/agent-config.ts +0 -288
- package/src/internal/discovery/agent.ts +0 -381
- package/src/internal/discovery/channels.ts +0 -100
- package/src/internal/discovery/connections.ts +0 -516
- package/src/internal/discovery/context.ts +0 -38
- package/src/internal/discovery/cursor-plugin.ts +0 -628
- package/src/internal/discovery/extension-overlay.ts +0 -247
- package/src/internal/discovery/extensions.ts +0 -490
- package/src/internal/discovery/fs.ts +0 -103
- package/src/internal/discovery/hooks.ts +0 -63
- package/src/internal/discovery/info.ts +0 -174
- package/src/internal/discovery/instructions.ts +0 -98
- package/src/internal/discovery/modules.ts +0 -107
- package/src/internal/discovery/names.ts +0 -45
- package/src/internal/discovery/project.ts +0 -319
- package/src/internal/discovery/reminders.ts +0 -65
- package/src/internal/discovery/runtime.ts +0 -158
- package/src/internal/discovery/schedules.ts +0 -120
- package/src/internal/discovery/seed-files.ts +0 -34
- package/src/internal/discovery/services.ts +0 -151
- package/src/internal/discovery/skills.ts +0 -174
- package/src/internal/discovery/subagent.ts +0 -138
- package/src/internal/discovery/tools.ts +0 -170
- package/src/internal/discovery.ts +0 -27
- package/src/internal/distribution.ts +0 -126
- package/src/internal/docs-site.ts +0 -248
- package/src/internal/duration.ts +0 -37
- package/src/internal/env-file.ts +0 -83
- package/src/internal/eval-judge-model.ts +0 -142
- package/src/internal/eval-run-store.ts +0 -585
- package/src/internal/eval-runner.ts +0 -823
- package/src/internal/evals-client.ts +0 -475
- package/src/internal/event-log.ts +0 -342
- package/src/internal/event-mapper.ts +0 -811
- package/src/internal/expected-delivery-failure.ts +0 -34
- package/src/internal/factory-resource-channel.ts +0 -103
- package/src/internal/filesystem/errors.ts +0 -207
- package/src/internal/filesystem/format.ts +0 -253
- package/src/internal/filesystem/merge.ts +0 -192
- package/src/internal/filesystem/nearest.ts +0 -112
- package/src/internal/filesystem/scratch.ts +0 -239
- package/src/internal/filesystem/sdk-schemas.ts +0 -204
- package/src/internal/filesystem/tools.ts +0 -804
- package/src/internal/filesystem/walk.ts +0 -366
- package/src/internal/fixtures/units-server.ts +0 -52
- package/src/internal/framework-file-storage.ts +0 -357
- package/src/internal/framework-storage-selection.ts +0 -156
- package/src/internal/frontmatter.ts +0 -108
- package/src/internal/github-fanout.ts +0 -144
- package/src/internal/guest-network.ts +0 -391
- package/src/internal/handleAgentServeTrigger.ts +0 -286
- package/src/internal/host-files.ts +0 -341
- package/src/internal/host-kv.ts +0 -81
- package/src/internal/host-otel.ts +0 -231
- package/src/internal/host-platforms.ts +0 -170
- package/src/internal/hosted-admission-adapter.ts +0 -47
- package/src/internal/hosted-admission-context.ts +0 -37
- package/src/internal/hosted-catch-protocol.ts +0 -112
- package/src/internal/hosted-catch.ts +0 -179
- package/src/internal/hosted-delivery-protocol.ts +0 -824
- package/src/internal/hosted-delivery.ts +0 -1410
- package/src/internal/hosted-execution-diag.ts +0 -291
- package/src/internal/hosted-execution-flush.ts +0 -136
- package/src/internal/hosted-execution-latency.ts +0 -301
- package/src/internal/hosted-managed-automation.ts +0 -116
- package/src/internal/hosting.ts +0 -114
- package/src/internal/http-channel-define.ts +0 -25
- package/src/internal/http-channel.ts +0 -669
- package/src/internal/http-control-plane-session.ts +0 -110
- package/src/internal/ids.ts +0 -39
- package/src/internal/incoming-headers-to-fetch.ts +0 -45
- package/src/internal/init-interview.ts +0 -360
- package/src/internal/init-project.ts +0 -711
- package/src/internal/init-scaffold.ts +0 -182
- package/src/internal/inline-stdio-define-stub.ts +0 -4
- package/src/internal/inline-stdio-mcp.ts +0 -230
- package/src/internal/install-cursor-skills.ts +0 -604
- package/src/internal/is-record.ts +0 -3
- package/src/internal/json-schema.ts +0 -95
- package/src/internal/legacy-command-guard.ts +0 -66
- package/src/internal/listen-port.ts +0 -85
- package/src/internal/local-control-plane.ts +0 -442
- package/src/internal/local-env.ts +0 -59
- package/src/internal/local-ingress.ts +0 -90
- package/src/internal/log-ring.ts +0 -59
- package/src/internal/logs-client.ts +0 -477
- package/src/internal/map-pool.ts +0 -39
- package/src/internal/mcp-endpoint.ts +0 -747
- package/src/internal/mcp-host.ts +0 -509
- package/src/internal/mcp-oauth-on-demand.ts +0 -337
- package/src/internal/mcp-oauth-persist.ts +0 -118
- package/src/internal/mcp-oauth.ts +0 -549
- package/src/internal/net.ts +0 -29
- package/src/internal/open-browser.ts +0 -41
- package/src/internal/otel/attrs.ts +0 -16
- package/src/internal/otel/collector.ts +0 -937
- package/src/internal/otel/config.ts +0 -287
- package/src/internal/otel/http.ts +0 -122
- package/src/internal/otel/mcp.ts +0 -56
- package/src/internal/otel/propagation.ts +0 -17
- package/src/internal/otel/runtime.ts +0 -441
- package/src/internal/package-inline-stdio.ts +0 -114
- package/src/internal/peer-connections.ts +0 -96
- package/src/internal/platform-schedule-sync.ts +0 -75
- package/src/internal/platform-timers.ts +0 -365
- package/src/internal/playground/static.ts +0 -278
- package/src/internal/playground/toolchain.ts +0 -270
- package/src/internal/playground-proxy.ts +0 -564
- package/src/internal/process-memory-telemetry.ts +0 -334
- package/src/internal/project-layout.ts +0 -31
- package/src/internal/prompt-context.ts +0 -116
- package/src/internal/reminder-control-plane-protocol.ts +0 -482
- package/src/internal/reminder-runner.ts +0 -1559
- package/src/internal/reminder-schedule.ts +0 -104
- package/src/internal/reminder-store.ts +0 -176
- package/src/internal/request-error-status.ts +0 -95
- package/src/internal/request-headers.ts +0 -21
- package/src/internal/resolve-prod-target.ts +0 -334
- package/src/internal/resolved-connections.ts +0 -190
- package/src/internal/router.ts +0 -143
- package/src/internal/run-client.ts +0 -354
- package/src/internal/runtime-dispatch-runner.ts +0 -50
- package/src/internal/sanitize-mcp-tool-name.ts +0 -31
- package/src/internal/schedule-runner.ts +0 -154
- package/src/internal/scm/pr-url.ts +0 -245
- package/src/internal/sdk-runner.ts +0 -959
- package/src/internal/serve-restart.ts +0 -113
- package/src/internal/server.ts +0 -3147
- package/src/internal/session-cost.ts +0 -208
- package/src/internal/session-engine.ts +0 -5622
- package/src/internal/session-links.ts +0 -84
- package/src/internal/session-run-log.ts +0 -535
- package/src/internal/session-store.ts +0 -307
- package/src/internal/session-urls.ts +0 -32
- package/src/internal/sessions-client.ts +0 -239
- package/src/internal/skill-catalog.ts +0 -66
- package/src/internal/skills-sync.ts +0 -55
- package/src/internal/slack-provision-client.ts +0 -544
- package/src/internal/slack-thread-key.ts +0 -11
- package/src/internal/sleep.ts +0 -3
- package/src/internal/start-log-store.ts +0 -164
- package/src/internal/steering.ts +0 -17
- package/src/internal/storage-coordinator.ts +0 -800
- package/src/internal/storage-roles.ts +0 -86
- package/src/internal/storage.ts +0 -1
- package/src/internal/store-api-protocol.ts +0 -205
- package/src/internal/store-mirror.ts +0 -73
- package/src/internal/stream-progress.ts +0 -294
- package/src/internal/terminal-style.ts +0 -133
- package/src/internal/testing/factory-resource-fixtures.ts +0 -84
- package/src/internal/testing/scm-continuation-fixtures.ts +0 -285
- package/src/internal/tool-catalog.ts +0 -104
- package/src/internal/tool-policy.ts +0 -222
- package/src/internal/tool-result.ts +0 -50
- package/src/internal/trajectory.ts +0 -418
- package/src/internal/turn-cost.ts +0 -136
- package/src/internal/turn-governor.ts +0 -145
- package/src/internal/turn-lease-store.ts +0 -144
- package/src/internal/turn-outbox.ts +0 -77
- package/src/internal/update-check.ts +0 -517
- package/src/internal/v2-hosting.ts +0 -52
- package/src/internal/workspace-sync.ts +0 -114
- package/src/internal/workspace.ts +0 -505
- package/src/kv/memory-kv.ts +0 -94
- package/src/kv.ts +0 -18
- package/src/memory.ts +0 -487
- package/src/otel-public.ts +0 -24
- package/src/otel.ts +0 -320
- package/src/prompt.ts +0 -80
- package/src/reminders.ts +0 -65
- package/src/schedules.ts +0 -31
- package/src/skills.ts +0 -27
- package/src/storage-backends/cursor-hosted-v2.ts +0 -204
- package/src/storage-backends/cursor-hosted.ts +0 -388
- package/src/storage-backends/file-kv.ts +0 -276
- package/src/storage-protocol.ts +0 -261
- package/src/storage.ts +0 -408
- package/src/tools.ts +0 -166
- package/src/types.ts +0 -3776
- /package/dist/docs/assets/{reference_agent-config.md.DzGI777n.lean.js → reference_agent-config.md.Cj5uBKp4.lean.js} +0 -0
|
@@ -1,672 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* `agent-sdk images push|list|rm`: a team's container images for
|
|
3
|
-
* `persistent: true` agents. `push` first checks the image locally for
|
|
4
|
-
* what the hosted install needs (linux/amd64, bash, git, node, npm) by
|
|
5
|
-
* inspecting it and running one probe container, then streams
|
|
6
|
-
* `docker save <image>` through gzip into a temp file (hashing as it
|
|
7
|
-
* goes), reserves a slot under the team cap, uploads the parts to the
|
|
8
|
-
* presigned URLs the backend handed back, and finalizes. Bytes never pass
|
|
9
|
-
* through the Cursor backend.
|
|
10
|
-
*/
|
|
11
|
-
|
|
12
|
-
import { spawn } from "node:child_process";
|
|
13
|
-
import { createHash } from "node:crypto";
|
|
14
|
-
import { createWriteStream } from "node:fs";
|
|
15
|
-
import { mkdtemp, open, rm, stat } from "node:fs/promises";
|
|
16
|
-
import { tmpdir } from "node:os";
|
|
17
|
-
import { join } from "node:path";
|
|
18
|
-
import { Readable } from "node:stream";
|
|
19
|
-
import { pipeline } from "node:stream/promises";
|
|
20
|
-
import { createGzip } from "node:zlib";
|
|
21
|
-
import { type DeployCliOptions, prepare, renderApiError, renderTable } from "./cli-deploy.js";
|
|
22
|
-
import { type ContainerImageInfo, DeployApiError } from "./deploy-client.js";
|
|
23
|
-
import { CLI_COMMAND_NAME as CLI } from "./distribution.js";
|
|
24
|
-
import { MAX_CONTAINER_IMAGE_BYTES, validateContainerImageName } from "./hosting.js";
|
|
25
|
-
|
|
26
|
-
/** Persistent VMs are x86_64; an arm64 image (Apple Silicon default) will not start there. */
|
|
27
|
-
const REQUIRED_PLATFORM = "linux/amd64";
|
|
28
|
-
/** Same floor as `engines.node` in this package: the image runs `agent-sdk serve`. */
|
|
29
|
-
const MIN_NODE_VERSION: readonly [number, number] = [22, 13];
|
|
30
|
-
/** glibc Debian-family bases are what the hosted install is exercised on. */
|
|
31
|
-
const KNOWN_GOOD_OS_IDS: ReadonlySet<string> = new Set(["debian", "ubuntu"]);
|
|
32
|
-
const UPLOAD_CONCURRENCY = 4;
|
|
33
|
-
const UPLOAD_ATTEMPTS = 3;
|
|
34
|
-
/** Same anchor the backend's cap error points at. */
|
|
35
|
-
const IMAGES_DASHBOARD_URL = "https://cursor.com/dashboard/deployed-agents#images";
|
|
36
|
-
|
|
37
|
-
/**
|
|
38
|
-
* What a container reports about itself when asked; every key may be
|
|
39
|
-
* missing or empty when the tool is absent. `os` / `osLike` come from
|
|
40
|
-
* `/etc/os-release` `ID` / `ID_LIKE`.
|
|
41
|
-
*/
|
|
42
|
-
export type ImageProbe = Partial<
|
|
43
|
-
Record<"bash" | "git" | "node" | "npm" | "user" | "os" | "osLike", string>
|
|
44
|
-
>;
|
|
45
|
-
|
|
46
|
-
/**
|
|
47
|
-
* POSIX `sh` body run inside the image (host shell never sees it). Prints
|
|
48
|
-
* one `key=value` per line; a missing tool prints an empty value.
|
|
49
|
-
*/
|
|
50
|
-
const PROBE_SCRIPT = [
|
|
51
|
-
'echo "bash=$(command -v bash 2>/dev/null || true)"',
|
|
52
|
-
'echo "git=$(command -v git 2>/dev/null || true)"',
|
|
53
|
-
'echo "node=$(node --version 2>/dev/null || true)"',
|
|
54
|
-
'echo "npm=$(npm --version 2>/dev/null || true)"',
|
|
55
|
-
'echo "user=$(id -un 2>/dev/null || id -u 2>/dev/null || true)"',
|
|
56
|
-
'if [ -r /etc/os-release ]; then . /etc/os-release; echo "os=${ID:-}"; echo "osLike=${ID_LIKE:-}"; fi',
|
|
57
|
-
].join("; ");
|
|
58
|
-
|
|
59
|
-
/** What `push` needs from the local Docker daemon; injectable for tests. */
|
|
60
|
-
export interface DockerImageSource {
|
|
61
|
-
/** `docker image inspect`: id, os/arch and uncompressed size, or undefined when the image is not local. */
|
|
62
|
-
inspect(image: string): Promise<{ id: string; platform: string; sizeBytes: number } | undefined>;
|
|
63
|
-
/**
|
|
64
|
-
* `docker run --rm --entrypoint sh <image> -c <probe>`: what the image
|
|
65
|
-
* has on PATH and who it runs as, or undefined when no container could
|
|
66
|
-
* run at all (no `sh`, or the daemon refused).
|
|
67
|
-
*/
|
|
68
|
-
probe(image: string): Promise<ImageProbe | undefined>;
|
|
69
|
-
/** `docker save`: the image as a tar stream. */
|
|
70
|
-
save(image: string): Readable;
|
|
71
|
-
}
|
|
72
|
-
|
|
73
|
-
function parseProbe(stdout: string): ImageProbe {
|
|
74
|
-
const probe: ImageProbe = {};
|
|
75
|
-
for (const line of stdout.split("\n")) {
|
|
76
|
-
const eq = line.indexOf("=");
|
|
77
|
-
if (eq <= 0) {
|
|
78
|
-
continue;
|
|
79
|
-
}
|
|
80
|
-
const key = line.slice(0, eq) as keyof ImageProbe;
|
|
81
|
-
if (
|
|
82
|
-
key === "bash" ||
|
|
83
|
-
key === "git" ||
|
|
84
|
-
key === "node" ||
|
|
85
|
-
key === "npm" ||
|
|
86
|
-
key === "user" ||
|
|
87
|
-
key === "os" ||
|
|
88
|
-
key === "osLike"
|
|
89
|
-
) {
|
|
90
|
-
probe[key] = line.slice(eq + 1).trim();
|
|
91
|
-
}
|
|
92
|
-
}
|
|
93
|
-
return probe;
|
|
94
|
-
}
|
|
95
|
-
|
|
96
|
-
/** `v22.14.0` → `[22, 14]`; undefined for anything else. */
|
|
97
|
-
function parseNodeVersion(raw: string): [number, number] | undefined {
|
|
98
|
-
const match = /^v?(\d+)\.(\d+)(?:\.\d+)?/.exec(raw.trim());
|
|
99
|
-
if (match === null) {
|
|
100
|
-
return undefined;
|
|
101
|
-
}
|
|
102
|
-
return [Number(match[1]), Number(match[2])];
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
function nodeMeetsFloor(version: [number, number]): boolean {
|
|
106
|
-
return (
|
|
107
|
-
version[0] > MIN_NODE_VERSION[0] ||
|
|
108
|
-
(version[0] === MIN_NODE_VERSION[0] && version[1] >= MIN_NODE_VERSION[1])
|
|
109
|
-
);
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
type ImageCheck = {
|
|
113
|
-
label: string;
|
|
114
|
-
value: string;
|
|
115
|
-
status: "ok" | "warning" | "failed";
|
|
116
|
-
/** Shown under the row for warnings and failures. */
|
|
117
|
-
detail?: string;
|
|
118
|
-
};
|
|
119
|
-
|
|
120
|
-
/**
|
|
121
|
-
* What the hosted install needs from the image, decided from `inspect` and
|
|
122
|
-
* `probe`. Failures stop the push; warnings print and continue.
|
|
123
|
-
*/
|
|
124
|
-
export function checkImage(
|
|
125
|
-
inspected: { platform: string },
|
|
126
|
-
probe: ImageProbe | undefined,
|
|
127
|
-
): ImageCheck[] {
|
|
128
|
-
const checks: ImageCheck[] = [];
|
|
129
|
-
if (inspected.platform === REQUIRED_PLATFORM) {
|
|
130
|
-
checks.push({ label: "platform", value: inspected.platform, status: "ok" });
|
|
131
|
-
} else {
|
|
132
|
-
checks.push({
|
|
133
|
-
label: "platform",
|
|
134
|
-
value: inspected.platform,
|
|
135
|
-
status: "failed",
|
|
136
|
-
detail: `Hosted agents run on ${REQUIRED_PLATFORM}. Rebuild with \`docker buildx build --platform ${REQUIRED_PLATFORM} …\`.`,
|
|
137
|
-
});
|
|
138
|
-
}
|
|
139
|
-
if (probe === undefined) {
|
|
140
|
-
checks.push({
|
|
141
|
-
label: "shell",
|
|
142
|
-
value: "no sh",
|
|
143
|
-
status: "failed",
|
|
144
|
-
detail:
|
|
145
|
-
"The image could not run `sh`. Start from a standard Debian or Ubuntu base such as node:22-bookworm-slim.",
|
|
146
|
-
});
|
|
147
|
-
return checks;
|
|
148
|
-
}
|
|
149
|
-
for (const tool of ["bash", "git"] as const) {
|
|
150
|
-
const path = probe[tool] ?? "";
|
|
151
|
-
checks.push(
|
|
152
|
-
path === ""
|
|
153
|
-
? {
|
|
154
|
-
label: tool,
|
|
155
|
-
value: "missing",
|
|
156
|
-
status: "failed",
|
|
157
|
-
detail: `Install ${tool} in the image (\`apt-get install -y ${tool}\`).`,
|
|
158
|
-
}
|
|
159
|
-
: { label: tool, value: path, status: "ok" },
|
|
160
|
-
);
|
|
161
|
-
}
|
|
162
|
-
const nodeRaw = probe.node ?? "";
|
|
163
|
-
const nodeVersion = parseNodeVersion(nodeRaw);
|
|
164
|
-
const floor = `${MIN_NODE_VERSION[0]}.${MIN_NODE_VERSION[1]}`;
|
|
165
|
-
if (nodeVersion === undefined) {
|
|
166
|
-
checks.push({
|
|
167
|
-
label: "node",
|
|
168
|
-
value: nodeRaw === "" ? "missing" : nodeRaw,
|
|
169
|
-
status: "failed",
|
|
170
|
-
detail: `Node.js ${floor} or newer must be on PATH; the image runs \`${CLI} serve\`.`,
|
|
171
|
-
});
|
|
172
|
-
} else if (!nodeMeetsFloor(nodeVersion)) {
|
|
173
|
-
checks.push({
|
|
174
|
-
label: "node",
|
|
175
|
-
value: nodeRaw,
|
|
176
|
-
status: "failed",
|
|
177
|
-
detail: `Node.js ${floor} or newer is required.`,
|
|
178
|
-
});
|
|
179
|
-
} else {
|
|
180
|
-
checks.push({ label: "node", value: nodeRaw, status: "ok" });
|
|
181
|
-
}
|
|
182
|
-
const npm = probe.npm ?? "";
|
|
183
|
-
checks.push(
|
|
184
|
-
npm === ""
|
|
185
|
-
? {
|
|
186
|
-
label: "npm",
|
|
187
|
-
value: "missing",
|
|
188
|
-
status: "failed",
|
|
189
|
-
detail: "npm must be on PATH; the hosted install runs it.",
|
|
190
|
-
}
|
|
191
|
-
: { label: "npm", value: npm, status: "ok" },
|
|
192
|
-
);
|
|
193
|
-
const user = probe.user ?? "";
|
|
194
|
-
checks.push(
|
|
195
|
-
user === "" || user === "root" || user === "0"
|
|
196
|
-
? { label: "user", value: user === "" ? "root" : user, status: "ok" }
|
|
197
|
-
: {
|
|
198
|
-
label: "user",
|
|
199
|
-
value: user,
|
|
200
|
-
status: "warning",
|
|
201
|
-
detail:
|
|
202
|
-
"The image runs as a non-root user. The hosted state directory is mounted root-owned, so installs may fail to write it; prefer no USER instruction or USER root.",
|
|
203
|
-
},
|
|
204
|
-
);
|
|
205
|
-
const osIds = [probe.os ?? "", ...(probe.osLike ?? "").split(/\s+/)]
|
|
206
|
-
.map(id => id.trim().toLowerCase())
|
|
207
|
-
.filter(id => id !== "");
|
|
208
|
-
const osValue = probe.os === undefined || probe.os === "" ? "unknown" : probe.os;
|
|
209
|
-
if (osIds.some(id => KNOWN_GOOD_OS_IDS.has(id))) {
|
|
210
|
-
checks.push({ label: "base", value: osValue, status: "ok" });
|
|
211
|
-
} else if (osIds.includes("alpine")) {
|
|
212
|
-
checks.push({
|
|
213
|
-
label: "base",
|
|
214
|
-
value: osValue,
|
|
215
|
-
status: "warning",
|
|
216
|
-
detail:
|
|
217
|
-
"Alpine is musl-based; native Node modules without musl builds fail at install. Debian or Ubuntu bases are known to work.",
|
|
218
|
-
});
|
|
219
|
-
} else {
|
|
220
|
-
checks.push({
|
|
221
|
-
label: "base",
|
|
222
|
-
value: osValue,
|
|
223
|
-
status: "warning",
|
|
224
|
-
detail:
|
|
225
|
-
"Could not identify a Debian or Ubuntu base. Other distributions may fail when the VM starts; node:22-bookworm-slim is a known-good starting point.",
|
|
226
|
-
});
|
|
227
|
-
}
|
|
228
|
-
return checks;
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
function renderChecks(image: string, checks: ImageCheck[]): string {
|
|
232
|
-
const width = Math.max(...checks.map(check => check.label.length));
|
|
233
|
-
const valueWidth = Math.max(...checks.map(check => check.value.length));
|
|
234
|
-
const lines = [`Checking ${image}…`];
|
|
235
|
-
for (const check of checks) {
|
|
236
|
-
lines.push(
|
|
237
|
-
` ${check.label.padEnd(width)} ${check.value.padEnd(valueWidth)} ${check.status}`,
|
|
238
|
-
);
|
|
239
|
-
if (check.detail !== undefined && check.status !== "ok") {
|
|
240
|
-
lines.push(` ${check.detail}`);
|
|
241
|
-
}
|
|
242
|
-
}
|
|
243
|
-
return `${lines.join("\n")}\n`;
|
|
244
|
-
}
|
|
245
|
-
|
|
246
|
-
export interface ImagesCliOptions extends DeployCliOptions {
|
|
247
|
-
docker?: DockerImageSource;
|
|
248
|
-
}
|
|
249
|
-
|
|
250
|
-
function runDocker(
|
|
251
|
-
args: string[],
|
|
252
|
-
): Promise<{ code: number | null; stdout: string; stderr: string }> {
|
|
253
|
-
return new Promise(resolvePromise => {
|
|
254
|
-
const child = spawn("docker", args, { stdio: ["ignore", "pipe", "pipe"] });
|
|
255
|
-
let stdout = "";
|
|
256
|
-
let stderr = "";
|
|
257
|
-
child.stdout.on("data", chunk => {
|
|
258
|
-
stdout += String(chunk);
|
|
259
|
-
});
|
|
260
|
-
child.stderr.on("data", chunk => {
|
|
261
|
-
stderr += String(chunk);
|
|
262
|
-
});
|
|
263
|
-
child.on("error", error => resolvePromise({ code: 1, stdout: "", stderr: error.message }));
|
|
264
|
-
child.on("close", code => resolvePromise({ code, stdout, stderr }));
|
|
265
|
-
});
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
/**
|
|
269
|
-
* Real Docker. A multi-platform image (an arm64 laptop pulling
|
|
270
|
-
* `--platform linux/amd64`) reports no os/arch at the top level, so inspect
|
|
271
|
-
* and save ask for the target platform explicitly where the daemon supports
|
|
272
|
-
* it (Docker 28+); older daemons fall back to the single-platform fields.
|
|
273
|
-
*/
|
|
274
|
-
function shellDocker(): DockerImageSource {
|
|
275
|
-
let savePlatform = false;
|
|
276
|
-
const format = "{{.Id}} {{.Os}}/{{.Architecture}} {{.Size}}";
|
|
277
|
-
const parse = (stdout: string) => {
|
|
278
|
-
const [id, platform, size] = stdout.trim().split(" ");
|
|
279
|
-
if (id === undefined || platform === undefined || size === undefined) {
|
|
280
|
-
return undefined;
|
|
281
|
-
}
|
|
282
|
-
return { id, platform, sizeBytes: Number(size) };
|
|
283
|
-
};
|
|
284
|
-
return {
|
|
285
|
-
async inspect(image) {
|
|
286
|
-
const scoped = await runDocker([
|
|
287
|
-
"image",
|
|
288
|
-
"inspect",
|
|
289
|
-
"--platform",
|
|
290
|
-
REQUIRED_PLATFORM,
|
|
291
|
-
image,
|
|
292
|
-
"--format",
|
|
293
|
-
format,
|
|
294
|
-
]);
|
|
295
|
-
const variant = scoped.code === 0 ? parse(scoped.stdout) : undefined;
|
|
296
|
-
// An image with no linux/amd64 variant answers the scoped inspect
|
|
297
|
-
// with the manifest list itself: no os/arch. Fall through so the
|
|
298
|
-
// plain inspect names the platform it does have.
|
|
299
|
-
if (variant !== undefined && variant.platform !== "/") {
|
|
300
|
-
savePlatform = true;
|
|
301
|
-
return variant;
|
|
302
|
-
}
|
|
303
|
-
// Older daemon, a missing image, or one with no linux/amd64 variant:
|
|
304
|
-
// the plain inspect tells those apart (absent vs. the wrong platform).
|
|
305
|
-
const plain = await runDocker(["image", "inspect", image, "--format", format]);
|
|
306
|
-
return plain.code === 0 ? parse(plain.stdout) : undefined;
|
|
307
|
-
},
|
|
308
|
-
async probe(image) {
|
|
309
|
-
// Same platform selection as save: on an arm64 host Docker runs the
|
|
310
|
-
// amd64 variant under emulation, which is enough for `command -v`.
|
|
311
|
-
const run = await runDocker([
|
|
312
|
-
"run",
|
|
313
|
-
"--rm",
|
|
314
|
-
"--pull=never",
|
|
315
|
-
...(savePlatform ? ["--platform", REQUIRED_PLATFORM] : []),
|
|
316
|
-
"--entrypoint",
|
|
317
|
-
"sh",
|
|
318
|
-
image,
|
|
319
|
-
"-c",
|
|
320
|
-
PROBE_SCRIPT,
|
|
321
|
-
]);
|
|
322
|
-
return run.code === 0 ? parseProbe(run.stdout) : undefined;
|
|
323
|
-
},
|
|
324
|
-
save(image) {
|
|
325
|
-
const child = spawn(
|
|
326
|
-
"docker",
|
|
327
|
-
savePlatform ? ["save", "--platform", REQUIRED_PLATFORM, image] : ["save", image],
|
|
328
|
-
{ stdio: ["ignore", "pipe", "inherit"] },
|
|
329
|
-
);
|
|
330
|
-
const stream = child.stdout;
|
|
331
|
-
child.on("close", code => {
|
|
332
|
-
if (code !== 0) {
|
|
333
|
-
stream.destroy(new Error(`docker save exited with ${code}`));
|
|
334
|
-
}
|
|
335
|
-
});
|
|
336
|
-
return stream;
|
|
337
|
-
},
|
|
338
|
-
};
|
|
339
|
-
}
|
|
340
|
-
|
|
341
|
-
function formatBytes(bytes: number): string {
|
|
342
|
-
if (bytes >= 1024 ** 3) {
|
|
343
|
-
return `${(bytes / 1024 ** 3).toFixed(2)} GiB`;
|
|
344
|
-
}
|
|
345
|
-
if (bytes >= 1024 ** 2) {
|
|
346
|
-
return `${(bytes / 1024 ** 2).toFixed(1)} MiB`;
|
|
347
|
-
}
|
|
348
|
-
return `${Math.ceil(bytes / 1024)} KiB`;
|
|
349
|
-
}
|
|
350
|
-
|
|
351
|
-
async function saveCompressed(
|
|
352
|
-
docker: DockerImageSource,
|
|
353
|
-
image: string,
|
|
354
|
-
path: string,
|
|
355
|
-
): Promise<{ sha256: string; sizeBytes: number }> {
|
|
356
|
-
const hash = createHash("sha256");
|
|
357
|
-
await pipeline(
|
|
358
|
-
docker.save(image),
|
|
359
|
-
createGzip(),
|
|
360
|
-
async function* (source) {
|
|
361
|
-
for await (const chunk of source) {
|
|
362
|
-
hash.update(chunk as Buffer);
|
|
363
|
-
yield chunk;
|
|
364
|
-
}
|
|
365
|
-
},
|
|
366
|
-
createWriteStream(path),
|
|
367
|
-
);
|
|
368
|
-
return {
|
|
369
|
-
sha256: hash.digest("hex"),
|
|
370
|
-
sizeBytes: (await stat(path)).size,
|
|
371
|
-
};
|
|
372
|
-
}
|
|
373
|
-
|
|
374
|
-
async function uploadPart(
|
|
375
|
-
fetchImpl: typeof fetch,
|
|
376
|
-
path: string,
|
|
377
|
-
part: { partNumber: number; url: string },
|
|
378
|
-
range: { start: number; end: number },
|
|
379
|
-
): Promise<string> {
|
|
380
|
-
const handle = await open(path, "r");
|
|
381
|
-
try {
|
|
382
|
-
const length = range.end - range.start;
|
|
383
|
-
const buffer = Buffer.alloc(length);
|
|
384
|
-
await handle.read(buffer, 0, length, range.start);
|
|
385
|
-
let lastError: unknown;
|
|
386
|
-
for (let attempt = 1; attempt <= UPLOAD_ATTEMPTS; attempt++) {
|
|
387
|
-
try {
|
|
388
|
-
const response = await fetchImpl(part.url, {
|
|
389
|
-
method: "PUT",
|
|
390
|
-
body: buffer,
|
|
391
|
-
headers: { "content-length": String(length) },
|
|
392
|
-
});
|
|
393
|
-
if (!response.ok) {
|
|
394
|
-
throw new Error(
|
|
395
|
-
`part ${part.partNumber}: HTTP ${response.status} ${await response.text()}`,
|
|
396
|
-
);
|
|
397
|
-
}
|
|
398
|
-
const etag = response.headers.get("etag");
|
|
399
|
-
if (etag === null || etag === "") {
|
|
400
|
-
throw new Error(`part ${part.partNumber}: S3 returned no ETag`);
|
|
401
|
-
}
|
|
402
|
-
return etag;
|
|
403
|
-
} catch (error) {
|
|
404
|
-
lastError = error;
|
|
405
|
-
}
|
|
406
|
-
}
|
|
407
|
-
throw lastError;
|
|
408
|
-
} finally {
|
|
409
|
-
await handle.close();
|
|
410
|
-
}
|
|
411
|
-
}
|
|
412
|
-
|
|
413
|
-
async function uploadParts(
|
|
414
|
-
fetchImpl: typeof fetch,
|
|
415
|
-
path: string,
|
|
416
|
-
sizeBytes: number,
|
|
417
|
-
upload: {
|
|
418
|
-
partSizeBytes: number;
|
|
419
|
-
parts: Array<{ partNumber: number; url: string }>;
|
|
420
|
-
},
|
|
421
|
-
onPart: (done: number, total: number) => void,
|
|
422
|
-
): Promise<Array<{ partNumber: number; etag: string }>> {
|
|
423
|
-
const queue = [...upload.parts];
|
|
424
|
-
const results: Array<{ partNumber: number; etag: string }> = [];
|
|
425
|
-
let done = 0;
|
|
426
|
-
const worker = async (): Promise<void> => {
|
|
427
|
-
for (;;) {
|
|
428
|
-
const part = queue.shift();
|
|
429
|
-
if (part === undefined) {
|
|
430
|
-
return;
|
|
431
|
-
}
|
|
432
|
-
const start = (part.partNumber - 1) * upload.partSizeBytes;
|
|
433
|
-
const end = Math.min(start + upload.partSizeBytes, sizeBytes);
|
|
434
|
-
const etag = await uploadPart(fetchImpl, path, part, { start, end });
|
|
435
|
-
results.push({ partNumber: part.partNumber, etag });
|
|
436
|
-
done++;
|
|
437
|
-
onPart(done, upload.parts.length);
|
|
438
|
-
}
|
|
439
|
-
};
|
|
440
|
-
await Promise.all(Array.from({ length: Math.min(UPLOAD_CONCURRENCY, queue.length) }, worker));
|
|
441
|
-
return results.sort((a, b) => a.partNumber - b.partNumber);
|
|
442
|
-
}
|
|
443
|
-
|
|
444
|
-
export async function cmdImagesPush(
|
|
445
|
-
args: { image: string | undefined; name: string | undefined },
|
|
446
|
-
options: ImagesCliOptions,
|
|
447
|
-
): Promise<number> {
|
|
448
|
-
const err = options.err ?? ((text: string) => void process.stderr.write(text));
|
|
449
|
-
if (args.image === undefined || args.image === "") {
|
|
450
|
-
err(`Usage: ${CLI} images push <local-image> --name <name> [--team <id>]\n`);
|
|
451
|
-
return 1;
|
|
452
|
-
}
|
|
453
|
-
if (args.name === undefined || args.name === "") {
|
|
454
|
-
err(`--name is required: ${CLI} images push ${args.image} --name <name>\n`);
|
|
455
|
-
return 1;
|
|
456
|
-
}
|
|
457
|
-
const nameError = validateContainerImageName(args.name);
|
|
458
|
-
if (nameError !== undefined) {
|
|
459
|
-
err(`${nameError}\n`);
|
|
460
|
-
return 1;
|
|
461
|
-
}
|
|
462
|
-
const out = options.out ?? ((text: string) => void process.stdout.write(text));
|
|
463
|
-
const docker = options.docker ?? shellDocker();
|
|
464
|
-
const inspected = await docker.inspect(args.image);
|
|
465
|
-
if (inspected === undefined) {
|
|
466
|
-
err(
|
|
467
|
-
`No local image named ${args.image}. Build or pull it first (\`docker image ls\` shows what is available).\n`,
|
|
468
|
-
);
|
|
469
|
-
return 1;
|
|
470
|
-
}
|
|
471
|
-
// Everything the hosted install needs is knowable locally; decide it
|
|
472
|
-
// before signing in or moving any bytes. The platform check gates the
|
|
473
|
-
// probe: a wrong-arch container cannot run here to be probed.
|
|
474
|
-
const checks = checkImage(
|
|
475
|
-
inspected,
|
|
476
|
-
inspected.platform === REQUIRED_PLATFORM ? await docker.probe(args.image) : undefined,
|
|
477
|
-
).filter(check => inspected.platform === REQUIRED_PLATFORM || check.label === "platform");
|
|
478
|
-
if (options.json !== true) {
|
|
479
|
-
out(renderChecks(args.image, checks));
|
|
480
|
-
}
|
|
481
|
-
const failed = checks.filter(check => check.status === "failed");
|
|
482
|
-
if (failed.length > 0) {
|
|
483
|
-
err(
|
|
484
|
-
`${args.image} cannot run as a hosted agent image:\n${failed
|
|
485
|
-
.map(check => ` ${check.label}: ${check.value}. ${check.detail ?? ""}`)
|
|
486
|
-
.join("\n")}\n`,
|
|
487
|
-
);
|
|
488
|
-
return 1;
|
|
489
|
-
}
|
|
490
|
-
|
|
491
|
-
const ctx = await prepare(options);
|
|
492
|
-
if (typeof ctx === "number") {
|
|
493
|
-
return ctx;
|
|
494
|
-
}
|
|
495
|
-
const fetchImpl = options.fetchImpl ?? fetch;
|
|
496
|
-
// `docker save` of a real image takes minutes; learn about a full team
|
|
497
|
-
// before paying for it. The backend re-checks at begin.
|
|
498
|
-
let listed: { images: ContainerImageInfo[]; limit: number };
|
|
499
|
-
try {
|
|
500
|
-
listed = await ctx.client.listContainerImages({ teamId: ctx.teamId });
|
|
501
|
-
} catch (error) {
|
|
502
|
-
return renderApiError(error, ctx.err);
|
|
503
|
-
}
|
|
504
|
-
if (
|
|
505
|
-
listed.images.length >= listed.limit &&
|
|
506
|
-
!listed.images.some(image => image.name === args.name)
|
|
507
|
-
) {
|
|
508
|
-
ctx.err(
|
|
509
|
-
`${listed.images.length} of ${listed.limit} images used; delete some at ${IMAGES_DASHBOARD_URL} or with \`${CLI} images rm <name>\`.\n`,
|
|
510
|
-
);
|
|
511
|
-
return 1;
|
|
512
|
-
}
|
|
513
|
-
const dir = await mkdtemp(join(tmpdir(), "agent-sdk-image-"));
|
|
514
|
-
const tarball = join(dir, "image.tar.gz");
|
|
515
|
-
try {
|
|
516
|
-
if (!ctx.json) {
|
|
517
|
-
ctx.out(`Saving ${args.image} (${formatBytes(inspected.sizeBytes)} uncompressed)…\n`);
|
|
518
|
-
}
|
|
519
|
-
const saved = await saveCompressed(docker, args.image, tarball);
|
|
520
|
-
if (saved.sizeBytes > MAX_CONTAINER_IMAGE_BYTES) {
|
|
521
|
-
err(
|
|
522
|
-
`Compressed image is ${formatBytes(saved.sizeBytes)}; the limit is ${formatBytes(MAX_CONTAINER_IMAGE_BYTES)}.\n`,
|
|
523
|
-
);
|
|
524
|
-
return 1;
|
|
525
|
-
}
|
|
526
|
-
|
|
527
|
-
const upload = await ctx.client.beginContainerImageUpload({
|
|
528
|
-
teamId: ctx.teamId,
|
|
529
|
-
name: args.name,
|
|
530
|
-
sizeBytes: saved.sizeBytes,
|
|
531
|
-
sha256: saved.sha256,
|
|
532
|
-
dockerImageId: inspected.id,
|
|
533
|
-
platform: inspected.platform,
|
|
534
|
-
});
|
|
535
|
-
if (!ctx.json) {
|
|
536
|
-
ctx.out(
|
|
537
|
-
`Uploading ${formatBytes(saved.sizeBytes)} in ${upload.parts.length} part${upload.parts.length === 1 ? "" : "s"}…\n`,
|
|
538
|
-
);
|
|
539
|
-
}
|
|
540
|
-
const parts = await uploadParts(fetchImpl, tarball, saved.sizeBytes, upload, (done, total) => {
|
|
541
|
-
if (!ctx.json && total > 1) {
|
|
542
|
-
ctx.out(` ${done}/${total}\n`);
|
|
543
|
-
}
|
|
544
|
-
});
|
|
545
|
-
const image = await ctx.client.finalizeContainerImage({
|
|
546
|
-
teamId: ctx.teamId,
|
|
547
|
-
name: args.name,
|
|
548
|
-
uploadId: upload.uploadId,
|
|
549
|
-
parts,
|
|
550
|
-
});
|
|
551
|
-
if (ctx.json) {
|
|
552
|
-
ctx.out(`${JSON.stringify({ image }, null, 2)}\n`);
|
|
553
|
-
} else {
|
|
554
|
-
ctx.out(
|
|
555
|
-
`Pushed ${image.name} (${formatBytes(image.sizeBytes)}, sha256 ${saved.sha256.slice(0, 12)}).\n` +
|
|
556
|
-
`Use it from a persistent agent: defineAgent({ persistent: true, hosting: { image: "${image.name}" } }).\n`,
|
|
557
|
-
);
|
|
558
|
-
}
|
|
559
|
-
return 0;
|
|
560
|
-
} catch (error) {
|
|
561
|
-
if (error instanceof DeployApiError) {
|
|
562
|
-
return renderApiError(error, ctx.err);
|
|
563
|
-
}
|
|
564
|
-
ctx.err(
|
|
565
|
-
`Push failed: ${error instanceof Error ? error.message : String(error)}\nRun the same command again to retry.\n`,
|
|
566
|
-
);
|
|
567
|
-
return 1;
|
|
568
|
-
} finally {
|
|
569
|
-
await rm(dir, { recursive: true, force: true });
|
|
570
|
-
}
|
|
571
|
-
}
|
|
572
|
-
|
|
573
|
-
export async function cmdImagesList(options: DeployCliOptions): Promise<number> {
|
|
574
|
-
const ctx = await prepare(options);
|
|
575
|
-
if (typeof ctx === "number") {
|
|
576
|
-
return ctx;
|
|
577
|
-
}
|
|
578
|
-
let listed: { images: ContainerImageInfo[]; limit: number };
|
|
579
|
-
try {
|
|
580
|
-
listed = await ctx.client.listContainerImages({ teamId: ctx.teamId });
|
|
581
|
-
} catch (error) {
|
|
582
|
-
return renderApiError(error, ctx.err);
|
|
583
|
-
}
|
|
584
|
-
if (ctx.json) {
|
|
585
|
-
ctx.out(`${JSON.stringify(listed, null, 2)}\n`);
|
|
586
|
-
return 0;
|
|
587
|
-
}
|
|
588
|
-
if (listed.images.length === 0) {
|
|
589
|
-
ctx.out(
|
|
590
|
-
`No images pushed yet. Push one with \`${CLI} images push <local-image> --name <name>\`.\n`,
|
|
591
|
-
);
|
|
592
|
-
return 0;
|
|
593
|
-
}
|
|
594
|
-
ctx.out(
|
|
595
|
-
`${renderTable(
|
|
596
|
-
["NAME", "SIZE", "PLATFORM", "SHA256", "PUSHED"],
|
|
597
|
-
listed.images.map(image => [
|
|
598
|
-
image.name,
|
|
599
|
-
formatBytes(image.sizeBytes),
|
|
600
|
-
image.platform ?? "",
|
|
601
|
-
image.sha256?.slice(0, 12) ?? "",
|
|
602
|
-
image.pushedAt,
|
|
603
|
-
]),
|
|
604
|
-
)}\n${listed.images.length} of ${listed.limit} images.\n`,
|
|
605
|
-
);
|
|
606
|
-
return 0;
|
|
607
|
-
}
|
|
608
|
-
|
|
609
|
-
export async function cmdImagesRm(
|
|
610
|
-
name: string | undefined,
|
|
611
|
-
options: DeployCliOptions,
|
|
612
|
-
): Promise<number> {
|
|
613
|
-
if (name === undefined || name === "") {
|
|
614
|
-
(options.err ?? ((t: string) => void process.stderr.write(t)))(
|
|
615
|
-
`Usage: ${CLI} images rm <name> [--team <id>]\n`,
|
|
616
|
-
);
|
|
617
|
-
return 1;
|
|
618
|
-
}
|
|
619
|
-
const ctx = await prepare(options);
|
|
620
|
-
if (typeof ctx === "number") {
|
|
621
|
-
return ctx;
|
|
622
|
-
}
|
|
623
|
-
try {
|
|
624
|
-
await ctx.client.deleteContainerImage({ teamId: ctx.teamId, name });
|
|
625
|
-
} catch (error) {
|
|
626
|
-
if (error instanceof DeployApiError && error.status === 404) {
|
|
627
|
-
ctx.err(`No image named ${name} — check \`${CLI} images list\`.\n`);
|
|
628
|
-
return 1;
|
|
629
|
-
}
|
|
630
|
-
return renderApiError(error, ctx.err);
|
|
631
|
-
}
|
|
632
|
-
if (ctx.json) {
|
|
633
|
-
ctx.out(`${JSON.stringify({ removed: name }, null, 2)}\n`);
|
|
634
|
-
} else {
|
|
635
|
-
ctx.out(`Removed image ${name}.\n`);
|
|
636
|
-
}
|
|
637
|
-
return 0;
|
|
638
|
-
}
|
|
639
|
-
|
|
640
|
-
/** Test seam: a `DockerImageSource` over in-memory bytes. */
|
|
641
|
-
export function memoryDockerImageSource(
|
|
642
|
-
images: Record<
|
|
643
|
-
string,
|
|
644
|
-
{
|
|
645
|
-
id: string;
|
|
646
|
-
platform: string;
|
|
647
|
-
tar: Buffer;
|
|
648
|
-
/** Omit for an image whose container cannot run `sh`. */
|
|
649
|
-
probe?: ImageProbe;
|
|
650
|
-
}
|
|
651
|
-
>,
|
|
652
|
-
): DockerImageSource {
|
|
653
|
-
return {
|
|
654
|
-
async inspect(image) {
|
|
655
|
-
const found = images[image];
|
|
656
|
-
return found === undefined
|
|
657
|
-
? undefined
|
|
658
|
-
: {
|
|
659
|
-
id: found.id,
|
|
660
|
-
platform: found.platform,
|
|
661
|
-
sizeBytes: found.tar.length,
|
|
662
|
-
};
|
|
663
|
-
},
|
|
664
|
-
async probe(image) {
|
|
665
|
-
return images[image]?.probe;
|
|
666
|
-
},
|
|
667
|
-
save(image) {
|
|
668
|
-
const found = images[image];
|
|
669
|
-
return Readable.from(found === undefined ? [] : [found.tar]);
|
|
670
|
-
},
|
|
671
|
-
};
|
|
672
|
-
}
|