supabase_typegen 0.1.2
supabase_typegen: ^0.1.2 copied to clipboard
Command-line code generator that turns a Supabase database schema into typed Dart table definitions.
supabase_typegen #
Generates typed Supabase table definitions from your database schema, so
query results never expose raw Map<String, dynamic> data.
For every table the generator emits:
- a zero-cost row extension type over the decoded JSON map with typed getters,
InsertandUpdatevalue types that enforce required columns at the construction site,- a
PostgrestTabledefinition andTableColumntokens for compile-time checked filters, - Dart enums for Postgres enums, with wire-name mapping.
Usage #
The easiest way is through the Supabase CLI, which handles the database
connection and runs this package for you. Add supabase_typegen as a dev
dependency of your project (until the package is published to
pub.dev, depend on it with a git source pointing at
packages/supabase_typegen in this repository), then:
supabase gen types --lang dart --local > lib/supabase_schema.g.dart
Any of the CLI's connection flags work (--local, --linked, --db-url,
--project-id).
Under the hood the CLI runs the introspection of
@supabase/postgrest-typegen
in-process against the database (the same GeneratorMetadata intermediate
representation its TypeScript, Go, Swift, and Python generators consume,
ordered with sortGeneratorMetadata) and hands the document to this tool
over stdin. The types reflect the current state of the selected database:
with --local the SQL in your supabase/ directory stays the single source
of truth, since the CLI applies your migrations to the local database and
generates from the result, while --linked, --project-id, and --db-url
generate from whatever that database currently contains.
Use --schema to generate for a schema other than public, and --import
to change which library the generated file imports PostgrestTable and
TableColumn from.
The metadata comes from the database catalog, so nullability, database
defaults, and identity columns are exact: a NOT NULL column with a default
reads as non-nullable but stays optional on insert, and GENERATED ALWAYS
columns appear in the row type but not in the insert and update types.
Generated code in action #
final books = await client.table(Books.table)
.select()
.where(Books.mood.eq(Mood.happy))
.order(Books.createdAt, ascending: false); // List<BooksRow>
await client.table(Books.table).insert(
BooksInsert(title: 'A typed row', tags: ['dart']),
);
Known limitations #
- Passing
nullto anInsert/Updateparameter omits the column. To write SQL NULL explicitly, use the generatedset…ToNullmethods, for exampleBooksUpdate(inPrint: false).setPriceToNull(); they only exist for nullable columns, so nulling aNOT NULLcolumn is a compile error. - Array elements are assumed non-null (
text[]maps toList<String>), matching the supabase-js type generator; arrays containing SQL NULL elements throw when the element is read. Enum, date, and timestamp array elements stay in their wire representation (List<String>); the Dart enum for enum array elements is still generated for manual conversion. timestamptzvalues are written back in UTC, naivetimestampvalues as local wall time, anddatevalues date-only, so calendar dates never shift with the client timezone.- Foreign key relationship getters and typed functions (rpc) are not generated yet.