deepspace 0.27.1 → 0.28.1

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/CHANGELOG.md CHANGED
@@ -1,5 +1,61 @@
1
1
  # deepspace
2
2
 
3
+ ## 0.28.1
4
+
5
+ ### Patch Changes
6
+
7
+ - Let apps share one authenticated tool set between their in-app assistant and local assistants through stateless `deepspace agent` commands.
8
+
9
+ ## 0.28.0
10
+
11
+ ### Minor Changes
12
+
13
+ - Every confirmed finding from the v0.27.0 AX round-1 pass. Records: `records.update` (and the action-tools `tools.update` built on it) is an UPDATE, never an upsert — a typo'd or stringified-undefined recordId used to silently create a phantom record and report success; it now refuses naming `records.create` as the spelling that creates. Source: it now LATCHES at the app's first release, permanently — the first `deepspace push` claims DeepSpace at the pack POST, the first deploy latches GitHub or DeepSpace from the checkout's selected remote, and every later check is one registry field. No flag and no consent gate; the latch is announced on stderr at the moment it happens, and a wrong latch is escaped like every wrong-source state, with `deepspace app init --new-id`. `pull` on an empty cloud repo refuses `no_cloud_repo` before writing the `space` remote or git identity (it used to mutate, then say `branch_not_found`/"push first" — and now matches `clone`'s code for the same state), and `pull` gains `--env`. Collaboration: `app collaborators list` names the OWNER (`owner: {userId, emailDisplay}` + an `OWNER:` line) — five refusals say "ask the owner" and no surface said who that was; the raw `Failed: <upstream>` family from `test accounts` maps to real refusals (`test_account_cap` with the freeing commands; a dead session says re-login instead of "Unauthorized"). Install healing: a zombie installer pid (containers whose PID 1 does not reap) no longer holds `install_in_progress` for 30 minutes — the sentinel age bound is 6 minutes, just past the install's own 5-minute timeout; if `npx deepspace` ITSELF fails `not found` after an interrupted install, run the package manager's `install` directly (npx cannot resolve a half-installed tree — documented in the contract). First deploy's unborn-HEAD commit says what it does ("Initial commit (DeepSpace scaffold + working tree)", with the file count on stderr) instead of silently labeling the user's own code "scaffold". `app_not_found` appends its staging paragraph only when DEEPSPACE_DEPLOY_URL is actually overridden. Scaffolder: `--no-register` prints a one-line deprecation note instead of silence. Docs: `computeHmacHex`/`timingSafeEqualHex` documented for webhook authors; `test run`'s `skippedSpecs` semantics (suite-level file selection, not runner-level test.skip) stated in the contract; developer deletion documented as auth-side only (registered apps are retained — undeploy first).
14
+ - Every confirmed finding from the v0.27.0 AX round-2 pass (workspaces, operations, testing lanes). Agent-loop killers: `stale_base` ships NO action — its old `deepspace pull` action looped forever after a workspace-branch release (pull answered `up_to_date`; the live commit sits on a ws/\* ref trunk can never fast-forward to; two lanes hit it independently) — the refusal now names the real choices (integrate, land, or `--ignore-stale`); `port_in_use`'s action always says `dev kill --port <n>` explicitly, because bare `dev kill` resolves through dev's own port precedence and could free a different port than the one that refused (`dev kill --help` now describes that precedence honestly). `workspace land` (and the sync recovery path) detect an unresolved merge and refuse with the merge-aware code instead of `dirty_worktree` advice that would commit `<<<<<<<` markers. `workspace attach`'s failed re-materialization hands back `git worktree prune` as the action (the verified one-step fix for a stale registration). `activity`'s human line names WHICH workspace synced (the JSON always did). Consent and honesty: `test accounts recover` is now a RETRIEVAL (the platform stores the credential for these synthetic QA identities), so `--all` from a second machine no longer invalidates the first machine's pool and needs no confirmation; only a pre-storage account rotates, once, reported via `rotated`. The rename prompt defaults to No (Enter must not move a live URL). `undeploy`'s consent text says app files survive too. Storage/billing truth: reported `usedBytes` re-measures when the summary is dirty, so deletes show up in the number users see (admission always self-healed at the refusal boundary; reporting lied at a 26 MB high-water mark indefinitely); a failed integration invoke's 502 says what happened to the money (`billing: 'released' | 'retained'` — retained means the upstream outcome is unknown and the worst-case pre-charge stands). Testing: `test run tests/<file>.spec.ts` with no such file refuses `spec_not_found` instead of `tests_failed`; `test screenshot --wait-for-selector` is wall-bounded (`screenshot_timeout` names the selector that never matched); duplicate test-account emails refuse `test_account_email_taken` stating the GLOBAL namespace; `secrets set/upload --json` carries `devRestartRequired` (the dev-restart fact only the human path stated). Scaffolder: the page `<title>` is the app's name, not "DeepSpace App"; `docs/migrations/` ships a README so `app update`'s `guidanceUrl` stops 404ing on the public mirror.
15
+ - Structural complexity reductions across five surfaces:
16
+ - One destructive-consent gate (`cli/lib/consent.ts` `requireConsent`) replaces
17
+ the six hand-rolled copies in `app undeploy`, `secrets configs delete`,
18
+ `domain buy`/`detach`, `test accounts clear`, and (before its deletion) the
19
+ `recover --all` gate; `domain`'s bespoke raw-stdin prompt is deleted, and an
20
+ interactive decline now uniformly refuses (exit 1) — `domain buy`/`detach`
21
+ and `test accounts clear` previously exited 0 with `cancelled: true`.
22
+ - The `install.pid` sentinel and its liveness check are gone: "still
23
+ installing" is `install.started` with no terminal sentinel and younger
24
+ than 6 minutes; the scaffolder's installer (which has no hard timeout)
25
+ keeps the sentinel's mtime fresh while it runs, bounded at 30 minutes so
26
+ a hung-but-alive package manager cannot hold `install_in_progress`
27
+ forever. The pid check's own-pid, recycled-pid, and zombie-pid bugs go
28
+ with it; a crashed install heals after the age bound instead of
29
+ immediately. The test harness's pid-ledger cleanup guard (which watched
30
+ for a detached installer that no longer exists) is deleted too.
31
+ - Test-account credentials are stored server-side (synthetic QA identities,
32
+ on purpose), so `test accounts recover` is a retrieval: other machines'
33
+ credentials stay valid, `--all` needs no confirmation and loses its
34
+ `--yes`. Pre-storage accounts rotate once (reported via `rotated`), then
35
+ are stored.
36
+ - The auth-worker's test-account endpoints return machine `code` fields
37
+ (`test_account_cap`, `test_account_email_taken`, `not_authenticated`, …);
38
+ the CLI keys remedies on the code alone.
39
+ - One dev-server port precedence (`resolveDevServerPort` in `cli/lib/port.ts`)
40
+ shared by `dev start`, `test run`, and `dev kill`, replacing `kill`'s
41
+ duplicated `pickKillPort`.
42
+ - Source LATCHES at the app's FIRST release, permanently — either DeepSpace
43
+ or GitHub, decided once, server-side, then one registry field forever:
44
+ the first `deepspace push` claims DeepSpace at the pack POST; the first
45
+ deploy latches from the checkout's selected GitHub remote (present ⇒
46
+ GitHub with the repository recorded, absent ⇒ DeepSpace) at the deploy
47
+ commit route, announced on stderr at the moment it happens. `push`'s
48
+ `--claim-source` flag and its pre-push refusal are deleted, and so is the
49
+ whole evidence-inference apparatus: no verb consults the release ledger
50
+ anymore — `pull`/`clone`/`workspace new` refusals on a GitHub app are the
51
+ server's field check (`source_managed_by_github`), which raw `git pull`
52
+ against a leftover remote gets too. Admin pushes
53
+ stay refused on every unclaimed app, and admin on-behalf deploys never
54
+ latch. A first release that latched from an accidental remote is escaped
55
+ the same way as every wrong-source state: `deepspace app init --new-id`.
56
+ Apps that deployed from GitHub before this release and never pushed are
57
+ simply still unclaimed — their next deploy latches GitHub.
58
+
3
59
  ## 0.27.1
4
60
 
5
61
  ### Patch Changes
package/README.md CHANGED
@@ -97,8 +97,16 @@ The package ships a `deepspace` binary for local dev and deployment:
97
97
  npx deepspace auth login # authenticate
98
98
  npx deepspace dev start # run locally
99
99
  npx deepspace deploy # deploy to *.app.space
100
+ npx deepspace agent tools my-app # discover an app's local-assistant tools
100
101
  ```
101
102
 
103
+ Apps that register assistant tools can expose the same tool factory to their
104
+ website AI and to a user's local assistant. The stateless
105
+ `deepspace agent tools` and `deepspace agent invoke` commands reuse the CLI
106
+ session to mint a five-minute credential for the exact target app. The
107
+ ordinary platform token is never sent to the app, and no separate connection
108
+ or browser approval is required.
109
+
102
110
  When updating an existing app, run the target CLI rather than the app's old
103
111
  installed binary:
104
112
 
@@ -118,10 +126,11 @@ The hierarchy shown by `deepspace --help` keeps durable app lifecycle under
118
126
  operations stay top-level. The historical `deepspace app migrate` command was
119
127
  removed in 0.15.0; it is not an upgrade or recovery path.
120
128
 
121
- Every app has one authoritative Git repository, and which one it is follows
122
- from what you do rather than from anything you declare. DeepSpace source is the
123
- packaged default: on a checkout with no GitHub remote, the first
124
- `deepspace push` — or the source sync inside the first normal deploy — claims
129
+ Every app has one authoritative Git repository — DeepSpace's packaged repo or
130
+ GitHub — fixed permanently at the app's FIRST release, and which one it is
131
+ follows from what you do rather than from anything you declare. DeepSpace
132
+ source is the packaged default: on a checkout with no GitHub remote, the first
133
+ `deepspace push` — or the first normal deploy — claims
125
134
  it and publishes automatically. `deepspace push` publishes the current branch
126
135
  and `deepspace clone <app>` checks it out; both configure a `space` remote and
127
136
  credential helper, so normal `git fetch space` and `git push space` work
@@ -136,10 +145,11 @@ npx deepspace deploy
136
145
  ```
137
146
 
138
147
  Nothing to declare: a checkout with a GitHub remote deploys as GitHub
139
- automatically — DeepSpace never reads or writes the GitHub repository, and
140
- each release records which repository the checkout pointed at (and whether
141
- the tree was dirty). The first `deepspace push` instead claims DeepSpace
142
- source, permanently — using it is choosing it; there are no transfers.
148
+ automatically, and the first deploy fixes GitHub source permanently —
149
+ DeepSpace never reads or writes the GitHub repository, and each release
150
+ records which repository the checkout pointed at (and whether the tree was
151
+ dirty). The first `deepspace push` instead claims DeepSpace source,
152
+ permanently — using it is choosing it; there are no transfers.
143
153
  Inspect with `deepspace app source` (read-only). Commands support `--json`
144
154
  for agents. Use `deepspace --help`, command-specific `--help`, and the
145
155
  [public manual](https://docs.deep.space) for workspaces, releases, and
@@ -164,3 +174,12 @@ env binding on your Worker to emit per-connection `[DO Perf]` timing logs.
164
174
  ## License
165
175
 
166
176
  Apache-2.0
177
+
178
+ ## Verifying a signed webhook
179
+
180
+ `deepspace/server` exports the two halves of HMAC verification so apps never
181
+ hand-roll them: `computeHmacHex(secret, payload)` and
182
+ `timingSafeEqualHex(a, b)` (constant-time compare). Verify the raw request
183
+ body against the signature header before parsing, and reject stale
184
+ timestamps yourself — the r1 AX pass built exactly this and could not
185
+ discover either export from the docs.
@@ -1274,7 +1274,7 @@ function renderInlineMarkdown(value) {
1274
1274
  import { useEffect as useEffect6, useRef as useRef5, useState as useState5 } from "react";
1275
1275
 
1276
1276
  // package.json
1277
- var version = "0.27.1";
1277
+ var version = "0.28.1";
1278
1278
 
1279
1279
  // src/documentation/runtime/navigation.tsx
1280
1280
  import { Fragment as Fragment4, jsx as jsx6, jsxs as jsxs6 } from "react/jsx-runtime";
@@ -1954,4 +1954,4 @@ export {
1954
1954
  DefaultDocumentation,
1955
1955
  DocumentationContent
1956
1956
  };
1957
- //# sourceMappingURL=chunk-CRIG6LPA.js.map
1957
+ //# sourceMappingURL=chunk-PVEUIQN4.js.map