Repository navigation
Conversation
…io's origins
The framework bindings (@decocms/tanstack, @decocms/nextjs) need the same
draft names and Studio origin list; sites repeat them by hand today.
- DRAFT_PARAM ("__draft"), DRAFT_COOKIE ("__deco_draft"), DRAFT_HEADER ("x-deco-draft")
- draftResponseHeaders(pointer): no-store/private, Vary: Cookie, noindex for a draft; {} otherwise
- STUDIO_ORIGINS, STUDIO_FRAME_ANCESTORS, isStudioOrigin()
No change to how createCMS decides which hosts may preview: cms.draftPointer
stays the only reader of the parameter and cookie. The v7 host allowlist goes
into the bindings.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01WNwbSEePYNcY5YCgqZURig
…io's origins out of @decocms/blocks Product owner review: these belong to the framework bindings, not to the framework layer. @decocms/tanstack and @decocms/nextjs carry them; blocks keeps what main already had (parseDraftPointer, cms.draftPointer, cms.draftCookie). This reverts 7ff9fb6. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WNwbSEePYNcY5YCgqZURig
tlgimenes
added a commit
that referenced
this pull request
Oct 14, 2026
…ponse headers and Studio's origins Moved from @decocms/blocks, unchanged values (PO review of #693): a new browser-safe root export with DRAFT_PARAM, DRAFT_COOKIE, DRAFT_HEADER, draftResponseHeaders (src/draft.ts) and STUDIO_ORIGINS, STUDIO_FRAME_ANCESTORS, isStudioOrigin (src/studio.ts). The worker, /server and the frame-ancestors use them; DecoDocument passes STUDIO_ORIGINS to StudioBridge's now required trustedOrigins, the list the bridge answered before. Tests moved with them, plus one that the bridge gets Studio's origins and one that the package depends on no @decocms/apps-* package. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WNwbSEePYNcY5YCgqZURig
tlgimenes
added a commit
that referenced
this pull request
Oct 14, 2026
…draft names and Studio's origins Brings in the PO review: @decocms/blocks no longer exports the draft names, draftResponseHeaders or Studio's origins (#693), @decocms/blocks/image is platform-neutral with the VTEX and Shopify helpers in @decocms/apps-vtex/image and @decocms/apps-shopify/image (#694), StudioBridge takes its trusted origins from the binding (#695), and @decocms/tanstack owns its own copy (#696). CLAUDE.md conflict: tests/ (helper guardrails) and examples/ lines combined. @decocms/nextjs, in the same commit so every package type-checks: - src/draft.ts (DRAFT_PARAM/COOKIE/HEADER, draftResponseHeaders) and src/studio.ts (STUDIO_ORIGINS, STUDIO_FRAME_ANCESTORS, isStudioOrigin): the package's own copy, same values as @decocms/tanstack's, never imported from it. The proxy, drafts.ts, /server and config.test.ts use it; the root exports it. - StudioBridge (src/StudioBridge.ts): blocks' bridge with trustedOrigins set to STUDIO_ORIGINS, so the layout still passes only the site. - /image-loader stays platform-neutral; its next/image golden comparison moves to tests/nextjs-image-loader.golden.test.ts, which composes @decocms/apps-vtex/image with decoCdn as a Next storefront does: 1,212 cases from blocks' and apps-vtex's fixtures, none changed. exports.test.ts pins that the package depends on no @decocms/tanstack or @decocms/apps-*. - nextjs-binding-smoke: decoCdn({ fit: "contain" }) (blocks' default fit is now cover) and a check of the origins the bridge answers. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WNwbSEePYNcY5YCgqZURig
tlgimenes
added a commit
that referenced
this pull request
Oct 14, 2026
Brings in the PO review down the stack: blocks without the draft names or Studio's origins (#693), the platform-neutral @decocms/blocks/image with the @decocms/apps-vtex/image and @decocms/apps-shopify/image helper subpaths (#694), StudioBridge's required trustedOrigins (#695), and each binding's own copy of the draft names and Studio's origins (#696, #697). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WNwbSEePYNcY5YCgqZURig
…ys an override The SDK's one environment read: without `dev`, createCMS keeps local files (no hosted release swaps in) when process.env.NODE_ENV is "development". Read guarded (typeof process, process.env), so a Worker or a browser without `process` counts as production, and spelled process.env.NODE_ENV so a bundler's define replaces it. An explicit `dev` (shipped in 8.0-8.2) overrides it both ways. remoteLoader itself still reads no environment. Conformance: H-5 default, override, production/unset and no-process cases. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
The resolver resolved every variant's rule before the built-in multivariate ran, so a matcher after the winner still ran: a random rule there drew and recorded a cohort. The built-in multivariate (marked like lazy) now gets its variants' rules resolved in order, one at a time, up to the first true one; later variants are left out and their matchers never run. A multivariate in the site's block map replaces the built-in and still gets every rule. builtin-03/mv-02 now claims the first-match order (the docs claim changes). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
…t of date For CI: generates the schema in memory, writes nothing, and exits 1 when the committed file is missing or differs from what `deco schema` would write, listing what moved (blocks new in code or gone, changed definitions, the generating version, or formatting only) and how to fix it. Schema errors also exit 1. --check can't be combined with --watch. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
tlgimenes
added a commit
that referenced
this pull request
Oct 15, 2026
Brings in #693's PO decisions 1-3 and afe430c (stripAssetHosts defaults to "leading"). Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
The draft changes body is now `{ set, delete, edits? }`. `edits` is the site
editor's record of who changed each name and when (`{ <name>: { userId, at }
}`, written by Studio); parseDraftChanges requires it to be an object when
present and returns only `set` and `delete`, so nothing of it reaches the
snapshot, layerDraft or a rendered page (PO: no v8 site is deployed yet, so
the shape can change).
Conformance: DP-11 now claims `{ set, delete, edits? }` (a non-object
`edits` is refused); DP-11b proves a draft's edits resolve to nothing: the
draft's blocks are as without them, no block is named `edits`, and no
resolved value or list carries a user id. The docs site's draft-previews
section needs the same wording.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
… drops it" This reverts commit 0012550. The PO moved the who/when record onto each block (a reserved `__meta` key), so the draft stays exactly { set, delete }. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
PO: "just add, on the block a metadata … something that tells last edited
by. but on the same json". A saved block may carry one reserved key next to
`__resolveType`: `__meta: { lastEditedBy: <Studio user id>, lastEditedAt:
<ISO 8601> }`, which the site editor stamps on every save (drafts, Localhost,
releases alike).
The resolver drops it wherever it walks (META_KEY): a saved entry is read
without it, and no object's `__meta` is copied into a resolved value, so no
block function, loader, list, `{ run: false }` read or rendered page sees
it, whether the block comes from a release, a bundled snapshot or a draft
layered on one. Snapshots and drafts keep the stored JSON as is; the
resolver is the one place content leaves. `deco check` already accepts it
(keys starting with `_` are never fields); the content protocol stores and
lists it as written; `deco schema` reads no content.
Tests: resolve.test (a stamped snapshot resolves, expands and lists exactly
as the plain one; no block function's props carry it, through references,
overrides and nesting), delivery DP-2b (a release's and a draft's stamped
block: nothing resolved carries it), deco check (accepted on any saved block
and a referenced one), protocol apply (passed through).
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
This was referenced Oct 16, 2026
This reverts commits b1cd9a1 and 36fb75f. PO: "only have metadata and changed by on v8 hosted": who edited a draft lives in the hosted draft object's storage metadata (Studio), never in block JSON, so the resolver has no reserved `__meta` key to drop. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What this PR does
Three product-owner decisions (2026-10-14/15) in
@decocms/blocks. The rest of the stack (#694 and up) merges this branch.1.
createCMSreadsNODE_ENVagain to decide dev mode (d03448c)devoption, acreateCMSwithsitestays on local files whenprocess.env.NODE_ENV === "development". Hosted releases are never swapped in, and drafts still load.typeof process !== "undefined" && process.env != null && …), so a Worker or browser withoutprocesscounts as production. It is spelledprocess.env.NODE_ENVso a bundler'sdefinecan replace it.devoption, which shipped in 8.0–8.2, stays as an override in both directions (dev: falseforces swaps even whenNODE_ENV=development).noEnv.test.tsallows exactly that one line.remoteLoaderitself still reads no environment.process). Each was mutation-checked.isNextDevfrom@decocms/nextjs, the migrator, the skill and the smoke apps happens in feat: @decocms/nextjs for v8: draft proxy and pages helpers, its own draft names and Studio origins, withDeco() and a platform-neutral image loader #697 and feat: the v7-to-v8 migrator and skill use @decocms/tanstack and @decocms/nextjs #700, not here.2.
deco schema --check(fa83481)For CI: generates the schema in memory, writes nothing, and exits 1 when
.deco/schema.gen.jsonis missing or differs from whatdeco schemawould write. The message says what moved:It ends with: Run
deco schemaand commit .deco/schema.gen.json.Schema errors exit 1 with the errors.
--checkand--watchcan't be combined, and there is no dev watch.Usage line:
deco schema [--root <dir>] [--watch | --check]. Seven tests incli/run.test.ts, including one through the bin under plain Node.dd-06follows the new usage line.The migrator adds it to each site's CI workflow in feat: the v7-to-v8 migrator and skill use @decocms/tanstack and @decocms/nextjs #700.
3.
multivariatestops at the first matching rule, as v7 did (ac23a70)multivariateran. A matcher after the winner still ran, so a random rule there drew a number and recorded a cohort.multivariate(marked the waylazyis) gets its rules resolved in order, one at a time, up to the firsttrueone. Later variants are left out and their matchers are never called.multivariatethat the site declares in its block map replaces the built-in and still gets every rule resolved, like any other block.website/flags/multivariate.ts, …) go through the same path.builtin-03/mv-02now claims first-match order. That test changed because the docs claim changes. New tests cover in-order evaluation, a random rule after the winner never drawing, legacy types, and the block-map override. Mutation-checked: 4 fail without the change.lazyand the built-inmultivariateare the resolver's special cases.Docs site follow-up (deco-sites/docs-tanstack,
/next/*)devdefaults toNODE_ENV === "development"(guarded;falsewithoutprocess). Passdevto override it, e.g.dev: import.meta.env.DEVon a Worker. Remove "the SDK reads no environment variable" wherever it refers todev.deco schema --check(usage line, exit codes, the message) and a CI snippet that runsdeco schema --check.trueone, as in v7: a later rule's matcher never runs, so a random rule after the winner draws nothing and sets no cookie. Amultivariateyou declare in your block map gets every rule."lazyis no longer the only special case. Add the built-inmultivariate's in-order rules.Gates
bun run checkpasses.bun run buildpasses.skills:checkandskills:readme:checkpass.deco --help.bun run test(2 GB): 2092 pass, 3 fail, 95 skipped.mainsince fix(protocol): discard also unstages the discarded blocks #689.schema.test.tstests hit the 5 s timeout under full-suite load. They pass alone (116/116 with noEnv, guides.cli and telemetry).Draft shape and block JSON: unchanged (2026-10-16)
Two who-edited-what experiments came and went on this branch, and the net change is none:
editsfield on the draft (00125500), reverted ina886d720.__metakey on saved blocks that the resolver dropped (b1cd9a13,36fb75f1), reverted in the commit on top. Both reverts are merged up the stack.PO: "only have metadata and changed by on v8 hosted". Studio keeps who and when in the hosted draft object's storage metadata, so the draft stays exactly
{ set, delete }and blocks has no reserved metadata key. The tree at M2 equals its state before these commits.https://claude.ai/code/session_016ZsmzpZ2zahRBoATBb2tBu
🤖 Generated with Claude Code