Repository navigation
Description
repo:cloud#3 · hotlong · session_01Q4EjjRhUZjdy8VXs6Kkur2
Blocked-by: #30871
Filing gate: ③ a task on the maintainer's word. Epic objectstack-ai/cloud#3652, coordinator session 2026-11-06, verbatim: 「我觉得先把受管软件包的开发循环走顺了」, 「同意,然后第一步先解决我本地开发的软件包怎么能够方便地发布到云端」, then 「还有一个场景,我如果是私有部署的企业版或者社区版,这个发布的流程怎么走?」 / 「docker部署」. On the deploy command (#30871 amendment), verbatim: 「开发人员也记不住啊」, then 「同意」. Rulings on cloud#3652 (2026-11-06T08:33Z), verbatim: Q1 「a 本地 os dev(推荐)」; Q3 「默认拒绝,需显式映射(推荐)」. Q3 reaches self-hosted through install-local (01a).
Carrier: objectstack. The CLI and the self-hosted install door (install-local) are platform code. No cloud part: an unbound self-hosted runtime never calls the control plane.
维护者速读
第一期的部署命令只认云端环境。私有部署(Docker 企业版或社区版)现在要手敲 os package install ./dist/objectstack.json -u <地址> -t <令牌>,每次都要带地址和令牌,默认地址还是 localhost:3000,而官方镜像监听 8080。这张卡让同一个部署命令和 os dev 里的 d 键也能部署到私有部署的运行时:记住目标地址和令牌,底层走现有的 install-local。升级预览和 Q3 的拒绝也一样生效。
Today (objectstack origin/main c50e0dfa)
os package installremembers nothing. (measured)- The target is
-u/--url(envOS_RUNTIME_URL, defaulthttp://localhost:3000). The credential is-t/--token(OS_RUNTIME_TOKEN) or--email/--password(packages/cli/src/commands/package/install.ts:113-136). - No stored target or credential is read: no
cloud-config,active-environmentor home-file read in the command. - Other flags:
--version(catalog, defaultlatest,:124-127),--timeout,--install-mode(:156),--confirm-global-uniques,--confirm-access-upgrade <token>(:174).
- The target is
- The default URL does not match the official image. The image sets
OS_PORT=8080andEXPOSE 8080(docker/Dockerfile:117-119), while the install default is port 3000. (measured; whether a typical Compose maps 8080 → 3000 is not read) - Install-local is synchronous. The runtime registers the package in its live kernel and answers
hotLoaded(packages/cloud-connection/src/marketplace-install-local-plugin.ts:41-47); the CLI prints a not-hot-loaded answer (install.ts:449). So "wait until live" is the answer itself, and no served-version poll is needed. (measured) - A dev version is not needed for an inline artifact. Install-local takes the artifact inline, and a managed re-install over an installed package is the supported upgrade path (
marketplace-install-local-plugin.ts:85-97). There is no catalog version row to collide with. (inferred from the door's contract; not run) - Install-local on the Community image. The image runs
os start(docker/Dockerfile:129), which spawnsserve.servemountsMarketplaceInstallLocalPluginin both the cloud-connected arm and the cloud-off arm (packages/cli/src/commands/serve.ts:4052,:4093), unless the host kernel is a runtime host. (inferred from code, not run; the epic recorded it as "not verified") Enterprise mounts it, or declines it in composed-artifact mode (cloudapps/objectos-ee/objectstack.config.ts:1397,:1658). (measured) - The deploy command (
os deploy, working name) and thedkey are being added by os package publish: one command from a local checkout to the org's environment — pick the only environment, keep it across login, fail loudly without one, and publish dev builds without hand-bumping the version #30871, cloud target only. (measured on the issue)
Expected
- A self-hosted target the CLI remembers. One command records a runtime URL and a credential, for example a token the runtime issued. The lane names the command beside
os environments switch. It is stored like the cloud target, with the credential in the same protected file the cloud token uses. The deploy command and thedkey use whichever target is active.os package installfalls back to it when-u/-tare not given. - Deploy to self-hosted = compile →
POST /api/v1/marketplace/install-localwith the inline artifact → print thehotLoadedanswer. No catalog publish and no dev-version suffix. A runtime bound to cloud may instead go through the catalog; the lane decides whether that is in scope or a follow-up. - The same plan and refusals. The deploy command asks install-local's dry run (01a) and prints the plan exactly as 01d prints cloud's. Declared
renamedFromrenames (07, 01b) are printed. Q3's--confirm-upgradeand the existing--confirm-access-upgradepass through. There is no--rename(decision D3: the mapping lives in the package). - A refused door is named. A runtime that declines install-local (composed-artifact mode) or predates the dry run answers in a sentence naming what to do, and the exit is non-zero.
- The default URL question (3000 vs the image's 8080) is settled by the remembered target. The lane says whether the default also changes.
Acceptance
- Tests with a stubbed runtime: remember a target, then the deploy command with no flags installs into it; the
dkey path does the same;os package installwithout-uuses the remembered target; a declined install-local (the EE composed-mode refusal) exits non-zero with its sentence; a Q3 refusal from the dry run stops the deploy. - Manual on the official Community image (
ghcr.io/objectstack-ai/objectstack,os start): from a fresh scaffold, remember the container's URL and an API key it issued, pressdtwice with an edit between, and the runtime serves the second build. This also settles the epic's "not verified" row.
Serial: after #30871, which creates the deploy command, the d key and the stored-target plumbing this card extends. The preview half needs 01a; the cloud preview (01c) is not needed. Can run in parallel with 01d, but both edit the deploy command, so the later one merges origin/main.
Dedupe (2026-11-06), run as gh api -X GET search/issues -f q=…:
repo:objectstack-ai/objectstack "os package install" self-hosted remembered is:issue→ 2 hits, both seat posts ([PM seat] director(项目总监) — ⏳ vacant · 第 47 场(os-bill)已收班 · 第 43 场续场 5(os-zhuang)、第 44 场(os-project-manager)与第 46 场(huangyiirene)无收班简报 · 台账在评论 #12708, [PM seat] triage (objectstack-wide) — 🟢 Routine · session_01AavokzJ5DndAwitDXvKy4U · trig_01NcnCtMS2tH46nUg1a5TaMJ (hourly) · state = body + the round records newer than it #6015).repo:objectstack-ai/objectstack install-local deploy runtime target is:issue is:open→ 12 hits, all QA runs and seat posts.
Suggested-grade: p3 · the maintainer named the self-hosted scenario; it follows the cloud loop and reuses everything Phase 1 builds.
Clause-②: no · CLI commands, flags and a local config file. The install-local door is used as is (its dry run comes from 01a).
🤖 Generated with Claude Code
Activity
objectstack-fleet commentedon Nov 6, 2026
triage#1 · os-zhuang · session_01AavokzJ5DndAwitDXvKy4U
Path: none
Triage: audit · grade kept ·
domain:server·pm:blocked· 2026-11-06T10:01Z⛔ Not a claim.
domain:server, andrepo:cloud#3follows it. The grade the filer set is kept.Blocked-byholds.Generated by Claude Code
objectstack-fleet commentedon Nov 6, 2026
domain:server#3 · os-elon-musk · session_016WV4cytQjG9X1CrCgytUM5
Unblocked · 2026-11-06T14:48Z ·
Blocked-by: #30871is cleared: #30871 closed as completed at 2026-11-06T14:34Z. Movedpm:blocked→pm:queueby the server seats' unblock scan; the card keeps its triage audit and grade, and is picked through the live server split. ⛔ Not a claim.objectstack-fleet commentedon Nov 7, 2026
domain:server#4 · marchtian · session_017ihL2dLQEXWGsE2SZ3Qn5F
Claim: PM loop round 1
Session:
session_017ihL2dLQEXWGsE2SZ3Qn5FAccount:
marchtianBranch:
claude/issue-30888-deploy-self-hostedWorktree:
objectstack-issue-30888Domain:
domain:serverSeat:
domain:server#4File surface:
packages/cli/src/commands/deploy.ts,packages/cli/src/commands/package/install.ts,packages/cli/src/commands/dev.ts(thedkey),packages/cli/src/commands/environments/**, the CLI stored-target/config helpers #30871 added, CLI tests,.changeset/(stop on breach; explain in the report)Container & model:
M/L,mode:subagent(in-seat background subagent, the project's standing dev form),model: default(dispatch-gates --tier: no path-derived mandate; PM judgment, default tier),effort: highClause-②: no
Metadata-protocol: none
Responsibility: n/a — not a defect card
Thread-read: 6687641434
Premise: holds
Serial constraints cleared: #30871 closed completed 2026-11-06; sibling #30889 (seat 4) reuses the same target resolution in parallel, later lander merges origin/main
objectstack-fleet commentedon Nov 7, 2026
domain:server#4 · marchtian · session_017ihL2dLQEXWGsE2SZ3Qn5F
os-dev-report
{ "pr": { "number": 31137, "url": "https://github.com/objectstack-ai/objectstack/pull/31137", "head": "b57c03aa03ab30e9502660953d02fc93accf3d4c", "draft": true, "assignees": [ "marchtian" ], "reviewers": [] }, "premise_still_valid": true, "gates": { "head": "b57c03aa", "merge_base": "5f003744", "origin_main_merged": "once, before pr_create: already up to date at 5f003744 (main has since moved 2 commits, neither touching a file this diff edits)", "local": [ "pnpm --filter @objectstack/cli exec vitest run --project unit --maxWorkers=2 :: exit 0 (397 files / 5603 tests)", "pnpm --filter @objectstack/cli exec vitest run --project unit test/deploy.test.ts test/dev-deploy-key.test.ts test/environments-use-runtime.test.ts test/package-install-url-token-flags.test.ts :: exit 0 (4 files / 63 tests)", "pnpm --filter @objectstack/cli typecheck :: exit 0 (NODE_OPTIONS=--max-old-space-size=8192, the CLI's measured OOM at the default heap)", "eslint packages/cli --no-inline-config :: exit 0", "node scripts/pm/dispatch-gates.mjs --commands --repo objectstack-ai/objectstack :: exit 0 (62 families)", "node scripts/check-adr-0087-registration.mjs --base origin/main :: exit 0", "node scripts/check-adr-0087-registration.mjs --self-test :: exit 0", "node scripts/check-changeset-no-major.mjs --base origin/main :: exit 0", "node scripts/check-closing-keyword-parity.mjs :: exit 0", "node scripts/check-closing-keyword-parity.mjs --self-test :: exit 0", "node scripts/check-comment-mask-adoption.mjs :: exit 0", "node scripts/check-comment-mask-adoption.mjs --self-test :: exit 0", "node scripts/check-comment-mask-corpus.mjs :: exit 0", "node scripts/check-dts-emitted.mjs --self-test :: exit 0", "node scripts/check-empty-changeset.mjs --base origin/main :: exit 0", "node scripts/check-empty-changeset.mjs --self-test :: exit 0", "node scripts/check-issue-citations.mjs :: exit 0", "node scripts/check-plugin-teardown-shape.mjs :: exit 0", "node scripts/check-plugin-teardown-shape.mjs --self-test :: exit 0", "node scripts/ci/assert-turbo-remote-cache.mjs --self-test :: exit 0", "node scripts/ci/plan-test-core-shards.mjs --self-test :: exit 0", "node scripts/ci/prune-turbo-cache.mjs --self-test :: exit 0", "node scripts/ci/snapshot-next.mjs --self-test :: exit 0", "node scripts/docs-audit/check-affected-docs.mjs :: exit 0", "node scripts/docs-audit/check-drift-comment.mjs :: exit 0", "node scripts/pm/release-rehearsal-clone.mjs --self-test :: exit 0", "node scripts/release-pending-publish.mjs --self-test :: exit 0", "pnpm --filter @objectstack/spec run check:duration-unit-keys :: exit 0", "pnpm check:changeset-gate-self-tests :: exit 0", "pnpm check:ci-filter-parity :: exit 0", "pnpm check:cli-test-child-env :: exit 0", "pnpm check:closed-ceremony-text :: exit 0", "pnpm check:cross-package-test-inputs :: exit 0", "pnpm check:doc-authoring :: exit 0", "pnpm check:driver-memory-census :: exit 0", "pnpm check:dts-closure :: exit 0", "pnpm check:dual-build-cjs-loads :: exit 0", "pnpm check:engine-double-contract :: exit 0", "pnpm check:gitlink-declared :: exit 0", "pnpm check:i18n :: exit 0", "pnpm check:i18n-coverage :: exit 0", "pnpm check:i18n-walk-parity :: exit 0", "pnpm check:issue-citations :: exit 0", "pnpm check:keyed-text-bounds :: exit 0", "pnpm check:lean-entry-closure :: exit 0", "pnpm check:logger-receiver-detach :: exit 0", "pnpm check:nul-bytes :: exit 0", "pnpm check:objectql-double-limit :: exit 0", "pnpm check:org-identifier :: exit 0", "pnpm check:page-declaration-shape :: exit 0", "pnpm check:platform-object-tenancy-census :: exit 0", "pnpm check:published-files :: exit 0", "pnpm check:query-options-erasure :: exit 0", "pnpm check:refd-timer-probe :: exit 0", "pnpm check:registry-log-declared :: exit 0", "pnpm check:rest-log-spy-declared :: exit 0", "pnpm check:slot-lookup :: exit 0", "pnpm check:sourcemap-no-sources-content :: exit 0", "pnpm check:system-context-census :: exit 0", "pnpm check:test-source-alias :: exit 0", "pnpm check:tier-file-adoption :: exit 0", "pnpm check:type-check-coverage :: exit 0", "pnpm check:type-check-debt :: exit 0", "pnpm check:undeclared-dep-imports :: exit 0", "pnpm check:vouch-for-reference-callers :: exit 0", "pnpm check:watch-hint-literal :: exit 0", "pnpm check:where-matcher :: exit 0", "node scripts/pm/dispatch-gates.mjs --repo objectstack-ai/objectstack --ran ran.list :: exit 0 (62 derived, 62 run, 0 NOT-MEASURED)" ], "first_pass_exit_3_rebuilt_and_rerun": [ "node scripts/check-plugin-teardown-shape.mjs --self-test (shallow clone: fetched pinned control 621a4876)", "pnpm check:dual-build-cjs-loads", "pnpm check:i18n", "pnpm check:i18n-coverage", "pnpm check:i18n-walk-parity", "pnpm check:type-check-debt (lock queue-timeout, rerun with slot)" ], "ablation": "runtime-target.ts isSameControlPlane(stored.url, url) -> true: test '-u naming another server never receives the remembered key' red (1 failed / 13 passed); restored, blob 900b6fe7 == HEAD", "ci": "in_progress at report time (PR just opened); not re-run locally", "integration_tier": "declared to CI: no spawn entry or integration-tier file touched" }, "line_budget": { "changed_lines": 1148, "additions": 1103, "deletions": 45, "files": 12, "human_merge_threshold": 3000, "src": 617, "tests": 472, "changeset": 14, "skills_touched": false }, "files_changed": [ ".changeset/30888-deploy-self-hosted.md", "packages/cli/src/commands/deploy.ts", "packages/cli/src/commands/environments/switch.ts", "packages/cli/src/commands/environments/use-runtime.ts (new)", "packages/cli/src/commands/package/install.ts", "packages/cli/src/utils/cloud-config.ts", "packages/cli/src/utils/dev-deploy-key.ts", "packages/cli/src/utils/runtime-target.ts (new)", "packages/cli/test/deploy.test.ts", "packages/cli/test/dev-deploy-key.test.ts", "packages/cli/test/environments-use-runtime.test.ts (new)", "packages/cli/test/package-install-url-token-flags.test.ts" ], "deviations": [ "Manual Community-image check NOT RUN: docker is not available in this container. Steps: docker run -p 8080:8080 ghcr.io/objectstack-ai/objectstack (os start); create an API key in Setup, API Keys; in a fresh scaffold: os environments use-runtime http://localhost:8080 --token KEY; os dev; press d; edit an object label; press d again; GET http://localhost:8080/api/v1/meta/object/NAME serves the second label. The epic's 'not verified' row (install-local on the Community image) stays NOT MEASURED.", "Q3 --confirm-upgrade pass-through NOT implemented: install-local on origin/main has the dry run (#30884 PR 1) but no Q3 refusal, no confirmSchemaUpgrade body key and no os package install --confirm-upgrade (#30884 PR 2, unclaimed, handoff 6688284693). The deploy prints the plan and stops on any refusal the door answers (dry run or install); no client-side copy of the verdict was added. Acceptance 'a Q3 refusal from the dry run stops the deploy' is pinned generically (a dry-run refusal stops before any install).", "The composed-artifact (EE) refusal shape is inferred from the card, not measured: objectstack-ai/cloud is not readable from this session (gh 403). A 404 is named with the composed-artifact sentence; any other refusal prints its code and message, exit 1.", "File surface: docs (content/docs/deployment/cli.mdx: os deploy section, environments table, os package install) and skills/objectstack-platform/references/operations.md are NOT updated: outside the claim's file surface. cloud/login.ts and cloud/logout.ts were NOT touched: the cloud.json write/delete helpers carry the runtime half instead.", "Ran pnpm install --frozen-lockfile and builds in the worktree; two lock queue-timeouts (exit 99) re-queued under the same slot." ], "open_questions": [ { "question": "When #30884 PR 2 lands (Q3 refusal + confirmSchemaUpgrade), who forwards --confirm-upgrade through os deploy?", "options": [ "A: #30884 PR 2 adds the one forwarded flag to os deploy beside --confirm-access-upgrade", "B: a follow-up card on this lane after PR 2 lands" ], "recommendation": "A, because PR 2 already edits os package install's flags and the deploy forwards them by the same in-process call; one line plus a test" }, { "question": "Should os environments create --activate also flip the deploy target back to the cloud (only switch does today)?", "options": [ "A: leave as is (switch and use-runtime are the pair)", "B: flip it too" ], "recommendation": "A, because create is provisioning; the deploy line names the runtime it targets" }, { "question": "Who updates the docs and the platform skill row for use-runtime / self-hosted deploy?", "options": [ "A: a docs follow-up card (cli.mdx + operations.md)", "B: amend this PR after the seat widens the file surface" ], "recommendation": "A, because skills/** carries its own budget and review" } ], "out_of_scope_findings": [ "carrier: #30884 (PR 2) · Q3 refusal on install-local not on main; until it lands, a self-hosted deploy whose plan lists a suspected rename installs it (plan printed first), the same as os package install today · noted, not filed", "carrier: seat · card item 2 second half (a cloud-bound runtime deploying through the catalog) not done; follow-up · noted, not filed", "carrier: seat · docs/skills rows for os environments use-runtime and the self-hosted os deploy (content/docs/deployment/cli.mdx, skills/objectstack-platform/references/operations.md) · noted, not filed" ], "mcp_calls": "0", "api_writes": "2: POST /repos/objectstack-ai/objectstack/dispatches (fleet-write pr_create with assignees marchtian -> PR 31137); POST /repos/objectstack-ai/objectstack/issues/30888/comments via post-stamped (this report). git push is not a REST write." }objectstack-fleet commentedon Nov 7, 2026
domain:server#4 · marchtian · session_017ihL2dLQEXWGsE2SZ3Qn5F
Landed · PR #31137 merged by the merge queue as
d5fd948efce2f8cc3f3032773fbba9f2c69f8f43.merged_atfrom the pulls APIcompletedbyFixes #30888pm:dispatchedremoved with this record. Follow-ups: docs + skill card #31143; Q3--confirm-upgradeforward rides #30884 PR 2 (noted on PR #31137's ACCEPT 6708196796).