Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
20 commits
Select commit Hold shift + click to select a range
1885110
docs(drive): slice spec for Postgres and bucket instances
wmadden-electric Oct 13, 2026
a5baa23
feat(dev-emulators): key Postgres databases by ids the emulator gener…
wmadden-electric Oct 13, 2026
b8508a4
feat(dev-emulators): key buckets by ids the emulator generates, with …
wmadden-electric Oct 13, 2026
11bc339
feat(local-target): record every app's services, databases and bucket…
wmadden-electric Oct 13, 2026
785489c
docs(design): extend ADR-0052 to databases, buckets, stop on exit and…
wmadden-electric Oct 13, 2026
4f516d1
docs(guides): each directory runs its own databases and buckets; dev …
wmadden-electric Oct 13, 2026
5bc22bd
docs(drive): record deferred items from the data-instances slice
wmadden-electric Oct 13, 2026
bcfc2da
refactor: name the session stop, record kinds and client types after …
wmadden-electric Oct 13, 2026
7f9cf3f
fix(local-target): stop what a failed dev start started, and delete d…
wmadden-electric Oct 13, 2026
962a59e
docs: show the database port-change line, the record's service kind, …
wmadden-electric Oct 13, 2026
91b3288
docs: match the slice spec to the shipped record, and say a failed st…
wmadden-electric Oct 13, 2026
1cf1093
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 14, 2026
ae00e8e
Merge remote-tracking branch 'bot/feat/emulator-instances' into feat/…
wmadden-electric Oct 14, 2026
a65e1fa
test(integration): look for bucket objects under the app's directory
wmadden-electric Oct 14, 2026
f60802f
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
83b6ed1
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
9743e40
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
9ea57c1
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
d3eaa1a
Merge feat/emulator-instances into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
b68f53a
Merge main into feat/emulator-data-instances
wmadden-electric Oct 15, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .drive/projects/emulator-commands/deferred.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,3 +4,5 @@
- **What a previous app's databases and buckets become when another app runs from the same directory.** Compute instances are deleted (S1a). Databases and buckets hold data; decide in S1b.
- **`[dev]` notices bypass the CLI engine's output.** The emulators hook writes `[dev] compute emulator ready`, the port-change line and the app-switch line with `console.log` to stdout, so a piped `prisma dev` mixes them into the JSON frames. Fixing it needs a channel for the local target's hooks to report through the engine.
- **A deployment that arrives while its instance is being deleted can start a process the emulator no longer tracks.** Same race as #353's app delete.
- **`env.json` and `secrets.json` in `.prisma-composer/dev/` are shared by every app run from a directory, and `--fresh` wipes them.** One app's `--fresh` can drop rows another app in the same directory needs on its next redeploy. Pre-existing. Making them per app, like bucket objects (S1b moved those to `buckets/<app>/<bucket>/`), would fix it.
- **A service that never listens fails `prisma dev` under prisma/composer#353** (the cron scheduler; `examples/store`). Raised with Will; the fix belongs in #353.
Original file line number Diff line number Diff line change
@@ -0,0 +1,76 @@
# S1b — The Postgres and bucket emulators know nothing about Composer

Repo: prisma/composer. Branch `feat/emulator-data-instances`, stacked on S1a (`feat/emulator-instances`, prisma/composer#354). PR base: that branch until it merges.

## At a glance

After S1a, only the Compute emulator follows ADR-0052. This slice moves the Postgres and bucket emulators to the same model, makes `prisma dev` stop its Postgres servers when it ends, and lets one directory keep the local data of more than one app.

```text
~/work/shop/.prisma-composer/dev/emulator-instances.json
{ "current": "shop",
"apps": {
"shop": { "nodes": {
"quotes": { "kind": "service", "id": "svc_k3f9…", "port": 3000 },
"catalog": { "kind": "database", "id": "db_02c4…" },
"uploads": { "kind": "bucket", "id": "bkt-77e1…" } } },
"shop-v2": { "nodes": { … } } } }
```

Comment thread
wmadden-electric marked this conversation as resolved.
Two checkouts of one app no longer share a local database or a bucket.

## Chosen design

**Postgres emulator.**
- A database is an instance with an emulator-generated id and labels, hosted on a `@prisma/dev` server named after that id. Every operation takes the id.
- A route lists all instances.
- New: **stop** shuts the instance's server down and keeps its data; **start** brings it back on the same port with the same data. Delete removes the server and its data. A stopped database keeps its port, by the same reasoning as Compute: its connection URL is in its dependents' environments.
- Old app-keyed servers and state are discarded on load. If `@prisma/dev` keeps data for them outside the emulator's own directory, remove it there too, or document exactly what is left behind.

**Bucket emulator.**
- A bucket is an instance with an emulator-generated id and labels. Its name on the S3 wire is that id, replacing `<app>--<bucket>`.
- Its data root is the in-project directory Composer registers, `.prisma-composer/dev/buckets/<app>/<bucket>/` (the app is in the path so two apps in one directory don't share a bucket's files). The emulator stores that path verbatim and never interprets it.
- Credentials are registered per instance. A route lists all instances.
- A bucket has no process, so stop and start don't apply.

**The record holds every app run from the directory.** This changes S1a's rule that switching apps deletes the previous app's Compute instances.
- `current` names the app `prisma dev` last ran here. `prisma dev url` (S3) resolves addresses in it.
- Switching apps stops the previous app's instances and keeps them, with their data and ports. Switching back resumes them warm.
- `--fresh` deletes the current app's instances and its entry.
- This follows Will's statement that the mapping is keyed by directory, app and topology. It also avoids deleting a database because a root module was renamed or run with a different `--name`.

**`prisma dev` ends.** On Ctrl-C, SIGTERM or a failure, `prisma dev` stops the current app's service processes, as today, and also its Postgres servers. The next start brings them back with their data.

**Everything else reaches databases and buckets through the record.** That includes the providers (`Database`, `Connection`, `Bucket`, `BucketKey`), attach, teardown, and `PgWarm`/`OrmMigration`, which already use the provider's URL. The emulators hook ensures them, as it does for Compute. Every instance gets the three `composer.*` labels.

**Docs.**
- ADR-0052 is extended in place, since it is unreleased, to cover databases, buckets, stop and the multi-app record. ADR-0041's amendment note is adjusted if needed.
- `local-dev.md`, the running-locally guide and the core-concepts skill are updated, removing every "Postgres and buckets are still keyed by the app" caveat.
- The guide's note that `PRISMA_COMPOSER_EMULATORS_DIR` doesn't isolate Postgres goes, because generated ids make checkouts independent.

## Scope

In: the Postgres and bucket emulators and their clients; the record's multi-app shape and the switch rule for all kinds; stopping Postgres servers on exit; the data providers, attach and teardown; tests; docs.

Out: `dev url`, `dev stop` and `emulator list` (S3); removing instances left by deleted directories.

## Pre-investigated edge cases

| Case | Expected |
| --- | --- |
| Warm start after Ctrl-C | Same database, same port, data intact, migrations no-op |
| A recorded database missing from the emulator | Re-created, requesting the remembered port; empty data, so migrations replay as on a fresh start |
| Switch app A → B → A | A's services, databases and buckets resume with their data and ports |
| Two checkouts of one app, each writes a row | Each reads only its own row; each lists only its own bucket objects |

## Slice-specific done conditions

- [ ] Two directories running one app with a database and a bucket each see only their own rows and objects (real emulators, temporary emulators directory).
- [ ] After `prisma dev` ends, no Postgres server of that app is running; the next start has the data.

## Dispatch plan

1. **Postgres emulator and client:** instances, labels, list, stop and start keeping data, delete. *Hands to 2.*
2. **Bucket emulator and client:** instances, labels, list, per-instance credentials. *Hands to 3.*
3. **Composer side:** the multi-app record, the data providers, attach and stop-on-exit, teardown, the two-directory data test. *Hands to 4.*
4. **Docs.** *Hands to:* the PR.
Loading
Loading