feat(cloudflare): credential-free alchemy dev - #1066
Open
sam-goodwin wants to merge 2 commits into
Open
Conversation
Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
alchemy dev now runs with no Cloudflare profile configured when every resource resolves to a local provider. Credentials are demanded lazily, exactly once, in the tty-owning process, only when the plan needs the cloud — and Cloudflare.state() resolves to a local file store in dev. - plan-time demand seam: collectCredentialDemands scans the plan for live-mode nodes, devRemote bindings, and live-stamped deletes; the demand runs loadOrConfigure interactively (with a reason naming the resources) or fails typed (CredentialsRequired) non-interactively with alchemy login guidance. The RPC sidecar never prompts — it reads credentials persisted by the exec process. - accountId is lazy everywhere local: 7 capability *Local layers defer resolution to the never-taken-for-dev HTTP branch; local providers stamp accountId opportunistically via a non-forcing probe and replace on account drift only when BOTH sides are defined (a credential-free session's resources survive the first post-login run); the local worker injects ALCHEMY_CLOUDFLARE_ACCOUNT_ID only when known. - Cloudflare.state() under dev always uses the local file store (.alchemy/state, telemetry id cloudflare-dev-local), skipping the cloud init entirely; dev and deploy states are disjoint for Cloudflare.state() users (documented). - Test.make now applies the dev context override OUTSIDE the state layer, matching the CLI (it previously built state seeing dev: false). - e2e proof: examples/cloudflare-dev/test/credential-free.test.ts runs the real CLI with a scrubbed HOME, no CLOUDFLARE_* env, and no profile — dev boots, the worker serves, state goes local. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Contributor
|
Install the packages built from this commit: alchemy bun add alchemy@https://pkg.ing/alchemy/e5cb2c2@alchemy.run/better-auth bun add @alchemy.run/better-auth@https://pkg.ing/@alchemy.run/better-auth/e5cb2c2@alchemy.run/pr-package bun add @alchemy.run/pr-package@https://pkg.ing/@alchemy.run/pr-package/e5cb2c2 |
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.
alchemy devnow runs with zero Cloudflare configuration when every resource resolves to a local provider — no profile, no env vars, no login. Credentials are demanded lazily, exactly once, and only when the plan actually needs the real cloud.:::caution
Cloudflare.state()now resolves to a local file store (.alchemy/state) wheneveralchemy devruns. Dev and deploy states become disjoint forCloudflare.state()users: a deploy after dev creates fresh resources instead of mode-replacing dev rows (which only ever described machine-local emulator instances). This matches whatAlchemy.localState()users already have.:::
Plan-time credential demand
After plan resolution, the dev path scans for genuine cloud needs — live-mode nodes (
Alchemy.remote()), bindings opted out viadev: { remote: true }, and deletes of live-stamped rows. Only then does it run the existing profile setup flow, interactively, with the reason spelled out:Non-interactive runs fail with a typed
CredentialsRequirednaming the resources and pointing atalchemy login. The RPC sidecar never prompts — it reads the credentials the exec process persisted.Local providers no longer force
accountIdSeven capability
*Locallayers deferred (they only needed the account for an HTTP branch never taken fordev:ids), and local providers now stampaccountIdopportunistically through a non-forcing probe. The replace-on-account-drift rule fires only when both old and new accounts are known — so resources created credential-free are not replaced (and their data not destroyed) on the first run after login.Proof
examples/cloudflare-dev/test/credential-free.test.tsruns the real CLI with a scrubbedHOME, noCLOUDFLARE_*env, and no profile: dev boots, the worker serves, rows land in the local store. Plus 22 new engine tests (demand detector matrix, drift rule, dev-state selection) and the existing local/live suites re-verified green.Also fixes a latent
Test.makebug: the dev context override was applied inside the state layer, soTest.make({ dev: true, state: Cloudflare.state() })built state seeingdev: false.🤖 Generated with Claude Code