feat: apso import supabase — generate .apsorc from a Supabase/Postgres database#68
Open
cultron wants to merge 1 commit into
Open
feat: apso import supabase — generate .apsorc from a Supabase/Postgres database#68cultron wants to merge 1 commit into
cultron wants to merge 1 commit into
Conversation
…s database Phase 1 of migrating off Supabase: introspect an existing Postgres database (read-only) and write a local .apsorc, after which the normal apso generate/deploy flow rebuilds it on Apso. Mirrors the existing 'apso schema pull' shape (introspect -> ApsorcOutput -> write with backup). - src/lib/import/introspect.ts: read-only PgIntrospector over information_schema/pg_catalog (lazy pg import, SSL on, skips Supabase system schemas and views). buildSchema() assembles raw rows and is unit-tested without a DB. - src/lib/import/pg-to-apsorc.ts: pure converter with a reverse type map (inverse of fieldTypeToColumnType, full fidelity), PK detection (uuid/serial/text id; composite/non-id kept as primary fields + warned), created_at/updated_at detection, FK -> ManyToOne (FK column omitted; to_name derived and round-trip-verified against getRelationshipIdField), enum values, default translation, unique/index handling, and an import report of everything lossy/skipped. - src/commands/import/supabase.ts: connection string via flag / SUPABASE_DB_URL / DATABASE_URL / masked prompt; --schema/--out/--dry-run/ --yes; never logs or persists the connection string; backs up an existing .apsorc. - pg + @types/pg added; 'import' topic registered. Verified end-to-end: generated .apsorc passes apso migrate (PGlite sandbox) producing valid DDL. 188 new assertions; full suite 248 tests, lint clean. Co-Authored-By: Claude Fable 5 <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
Phase 1 of migrating off Supabase: a new
apso import supabasecommand that connects to an existing Supabase (Postgres) database via a connection string, introspects its schema read-only, and writes a local.apsorc. From there the existingapso generate/apso deployflow rebuilds the structure on Apso.This is step 1 of the two-step plan agreed up front (schema now, table-data copy later). It mirrors the existing
apso schema pullshape: introspect →ApsorcOutput→ write with backup.How it works
Pipeline:
src/lib/import/introspect.ts) — read-onlySELECTs overinformation_schema/pg_catalog; SSL on by default; skips Supabase-managed schemas (auth,storage, …) and views.pgis lazy-imported.src/lib/import/pg-to-apsorc.ts, pure) — reverse type map (inverse offieldTypeToColumnType, full fidelity: uuid/timestamp/bigint/jsonb preserved; arrays + unknown types → text + warning); PK detection (uuid/serial/textid; composite/non-idPKs kept asprimaryfields + flagged);created_at/updated_atdetection; FK →ManyToOnewith the FK column omitted andto_nameround-trip-verified againstgetRelationshipIdField; enums; default translation; unique/index handling..apsorc; never logs or persists the connection string.Decisions (confirmed during planning)
idPKs imported as-is + warned (never silently rewritten).ManyToOne(lossless).Verification
buildSchemarow assembly (FK grouping, enum detection) — no DB needed. Command helpers tested with a fake introspector..apsorcwas fed toapso migrate(PGlite sandbox) and produced valid DDL (uuid PKs, enum type, unique/FK constraints, array→text).npm testincl. the posttest eslint hook).Notes / follow-ups
introspect.ts's live-DB path is covered only by the purebuildSchematests here; a guarded integration test against a real database is a sensible follow-up.IntrospectedSchemaand the FK graph; theIntrospectorinterface andsrc/lib/import/layout leave room for a sibling data reader without touching the converter.ManyToOnewithcascadeDelete: truerenders asON DELETE NO ACTIONin the sandbox SQL — that's existing relationship/generator behavior, not introduced here; worth a separate look.🤖 Generated with Claude Code