Open
Conversation
Refactors apps/api from a Bun HTTP server into a Workers fetch handler so we can deploy via `wrangler deploy` without waiting on the alchemy-effect infra rewrite. - split DatabaseLive into an abstract Context.Service with D1 and libsql live layers; tests and apps/alerting use the libsql variant - add EdgeCacheService backed by Workers caches.default with an in-memory fallback for Node/test runtimes; QueryEngineService uses it in place of Effect.Cache - add packages/db/client factories, D1 migration bundle, and the scripts/prepare-local-d1.ts dev helper - local WorkerEnvironment Context tag so we don't pull alchemy into the tsc graph (alchemy 2.0.0-beta.3 fails type-check against workspace effect 4.0.0-beta.48) Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
Replaces the one-shot SQL bundle with drizzle's native migration folder, which both wrangler and alchemy read directly. The bundle approach couldn't run incrementally — it would fail on the second apply because tables already existed. - wrangler.jsonc: add migrations_dir pointing at packages/db/drizzle so `wrangler d1 migrations apply` tracks applied migrations in the standard d1_migrations table - alchemy.run.ts: declare the D1Database with migrationsDir and the Worker with D1 binding + env/secret wiring, mirroring the pattern in apps/chat-agent/alchemy.run.ts; domains per stage (api.maple.dev / api-staging.maple.dev) - drop the bundle scripts (create-d1-migration-bundle, export-app-state, render-d1-import-sql) and the .generated SQL artifact - rewrite scripts/prepare-local-d1.ts to delegate to `wrangler d1 migrations apply --local` — idempotent, picks up new migrations without wiping - add alchemy dep (same pkg.pr.new version as web/landing/chat-agent) and deploy:stack / destroy:stack scripts Verified: all 16 drizzle migrations apply cleanly via `wrangler d1 migrations apply MAPLE_DB --local` and re-running is a no-op. Typecheck and tests still pass. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
|
no API key found. Pullfrog requires at least one LLM provider API key. to fix this, add the required secret to your GitHub repository:
configure your model at https://pullfrog.com/console/Makisuo/maple for full setup instructions, see https://docs.pullfrog.com/keys
|
CI deploy-prd failed with `Secret cannot be undefined` because `alchemy.secret(optionalEnv(...))` was invoked for env vars that weren't set in CI (MAPLE_ROOT_PASSWORD, CLERK_*, etc.). The D1 database and migrations did apply successfully before the Worker step died. Introduces `optionalSecret` / `optionalString` helpers that omit the binding entirely when the env var is unset. The Worker runtime already handles missing optional env via `Option` in `services/Env.ts`, so omitting the binding is the right shape. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
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.

Summary
Moves
apps/apifrom a Bun HTTP server to a Cloudflare Worker so it canbe deployed independently, without waiting on the in-progress
alchemy-effect infra rewrite on
cf-migration.apps/apiinto a Workers fetch handler (src/worker.ts+shared
src/app.ts), withDatabaseD1Liveusing the D1 binding and anew
EdgeCacheServicebacked by Workerscaches.default(memoryfallback for tests/Node).
DatabaseLiveinto an abstractDatabaseContext.Service withtwo live implementations:
DatabaseLibsqlLive(tests,apps/alerting)and
DatabaseD1Live(worker).wrangler.jsoncsetsmigrations_dir: "../../packages/db/drizzle"andalchemy.run.tspasses
migrationsDiron theD1Databaseresource. Drops the one-shotSQL bundle approach (couldn't re-run incrementally).
apps/api/alchemy.run.ts(upstreamalchemypackage, mirroringapps/chat-agent) with stage-based naming and domain mapping, plusdeploy:stack/destroy:stackscripts.What this PR does not include
Everything below stays on
cf-migrationuntil it's ready:.context/alchemy-effectsubtree bumpapps/{web,landing,chat-agent,alerting}/alchemy.run.tsupdatespackages/infra/src/railwayrewriteNotes
apps/api/src/services/WorkerEnvironment.tsis a local Effect Contexttag replacing what was originally imported from
alchemy/Cloudflare/Workers. WithcustomConditions: ["bun"], tscresolves
alchemy/*to raw TS source, which fails typecheck againstthe workspace's effect beta version. Keeping a local tag means
src/**has zero alchemy imports and the deploy-time
alchemy.run.ts(outsidesrc/**) doesn't pollute the tsc graph.bun installbun --filter=@maple/api deploy:stack(alchemy provisions D1,applies drizzle migrations via
migrationsDir, deploys Worker)TINYBIRD_TOKEN,MAPLE_INGEST_KEY_ENCRYPTION_KEY,MAPLE_INGEST_KEY_LOOKUP_HMAC_KEY, etc. (seealchemy.run.tsforthe full list)
Test plan
bun --filter=@maple/api typecheckbun --filter=@maple/alerting typecheckbun --filter=@maple/db typecheckcd apps/api && bun test— 160/160 passingwrangler d1 migrations apply MAPLE_DB --localapplies all 16drizzle migrations; re-run is a no-op
bun run dev(wrangler dev+ local D1)bun run deploy:stack/healthon the deployed Worker and verify one authenticatedroute against D1
🤖 Generated with Claude Code