{"id":25900454,"url":"https://github.com/khuwn-soulutions/supabase_codegen","last_synced_at":"2025-03-03T02:16:54.785Z","repository":{"id":279601754,"uuid":"939104888","full_name":"Khuwn-Soulutions/supabase_codegen","owner":"Khuwn-Soulutions","description":"A codegen library that grabs and generates classes from Supabase tables and enums in Dart.","archived":false,"fork":false,"pushed_at":"2025-02-28T08:40:40.000Z","size":91,"stargazers_count":2,"open_issues_count":8,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-02-28T12:47:18.037Z","etag":null,"topics":["codegen","dart","database","orm","postgres","supabase"],"latest_commit_sha":null,"homepage":"","language":"Dart","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"gpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Khuwn-Soulutions.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2025-02-26T02:02:11.000Z","updated_at":"2025-02-28T05:55:18.000Z","dependencies_parsed_at":"2025-02-28T12:47:26.931Z","dependency_job_id":null,"html_url":"https://github.com/Khuwn-Soulutions/supabase_codegen","commit_stats":null,"previous_names":["jwelmac/supabase_codegen","khuwn-soulutions/supabase_codegen"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Khuwn-Soulutions%2Fsupabase_codegen","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Khuwn-Soulutions%2Fsupabase_codegen/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Khuwn-Soulutions%2Fsupabase_codegen/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Khuwn-Soulutions%2Fsupabase_codegen/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Khuwn-Soulutions","download_url":"https://codeload.github.com/Khuwn-Soulutions/supabase_codegen/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":241596277,"owners_count":19988044,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["codegen","dart","database","orm","postgres","supabase"],"created_at":"2025-03-03T02:16:53.602Z","updated_at":"2025-03-03T02:16:54.764Z","avatar_url":"https://github.com/Khuwn-Soulutions.png","language":"Dart","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Supabase Codegen\n\n[![style: very good analysis][very_good_analysis_badge]][very_good_analysis_link]\n[![Powered by Mason](https://img.shields.io/endpoint?url=https%3A%2F%2Ftinyurl.com%2Fmason-badge)](https://github.com/felangel/mason)\n[![License: MIT][license_badge]][license_link]\n\nSupabase Codegen generates type-safe Dart models from your Supabase tables automatically!\n\n## Installation 💻\n\n**❗ In order to start using Supabase Codegen you must have the [Dart SDK][dart_install_link] installed on your machine.**\n\nAdd the following to your pubspec.yaml\n\n```yaml\ndependencies:\n  supabase_codegen:\n    git:\n      url: https://github.com/jwelmac/supabase_codegen.git\n      ref: main\n```\n\n---\n\n## Continuous Integration 🤖\n\nSupabase Codegen comes with a built-in [GitHub Actions workflow][github_actions_link] powered by [Very Good Workflows][very_good_workflows_link] but you can also add your preferred CI/CD solution.\n\nOut of the box, on each pull request and push, the CI `formats`, `lints`, and `tests` the code. This ensures the code remains consistent and behaves correctly as you add functionality or make changes. The project uses [Very Good Analysis][very_good_analysis_link] for a strict set of analysis options used by our team. Code coverage is enforced using the [Very Good Workflows][very_good_coverage_link].\n\n---\n\n## ✨ Features\n\n- Automatically generates Dart classes from Supabase tables\n- Creates type-safe models with full IDE support\n- Supports complex relationships and nested structures\n- Generates getters and setters for all fields\n\n## 📋 Prerequisites\n\n- Supabase project with tables\n- Dart/Flutter development environment\n- Environment configuration file (`.env`)\n\n## 🛠️ Setup\n\n1. Install the package. See [Installation](#installation-)\n2. Create a `.env` file at the root of your project with your Supabase credentials. See [example.env](example.env).\n3. Create SQL functions in Supabase.  \n   Options:\n   - Copy and run the sql from [get_schema_info](bin/sql/get_schema_info.dart) and [get_enum_types](bin/sql/get_enum_types.dart) in your Supabase project.\n   - Create migration to apply to your local or remote database with `dart run supabase_codegen:add_codegen_functions` and apply the migration with [`supabase migration up`](https://supabase.com/docs/reference/cli/supabase-migration-up).  \n   Note: this requires [Supabase CLI](https://supabase.com/docs/reference/cli/introduction) with linked project\n\n4. Run the generation script: `dart run supabase_codegen:generate_types`  \nOptions:  \n\n- `--output` or `-o`: Folder to output generated files relative to project root. (Default: `supabase/types`)\n- `--env` or `-e`: Path to env file to read Supabase credentials. (Default: `.env`)\n\nExample:\n\n```bash\ndart run supabase_codegen:generate_types --output lib/types -e .env.production\n```\n\n## 📦 Generated Types\n\nThe generator will create strongly-typed models like this:\n\n```dart\nenum UserRole {\n  admin,\n  user,\n}\n\n/// Users Table\nclass UsersTable extends SupabaseTable\u003cUsersRow\u003e {\n  /// Table Name\n  @override\n  String get tableName =\u003e 'users';\n\n  /// Create a [UsersRow] from the [data] provided\n  @override\n  UsersRow createRow(Map\u003cString, dynamic\u003e data) =\u003e UsersRow(data);\n}\n\n/// Users Row\nclass UsersRow extends SupabaseDataRow {\n  /// Users Row\n  const UsersRow(super.data);\n\n  /// Construct Users Row using fields\n  factory UsersRow.withFields({\n    required String email,\n    required UserRole role,\n    String? accName,\n    String? phoneNumber,\n    List\u003cString\u003e? contacts,\n    DateTime? createdAt,\n  }) =\u003e\n      UsersRow({\n        'email': email,\n        'role': role.name,\n        if (accName != null) 'acc_name': accName,\n        if (phoneNumber != null) 'phone_number': phoneNumber,\n        if (contacts != null) 'contacts': contacts,\n        if (createdAt != null) 'created_at': createdAt,\n      });\n\n  /// Get the [SupabaseTable] for this row\n  @override\n  SupabaseTable get table =\u003e UsersTable();\n\n  /// Email field name\n  static const String emailField = 'email';\n\n  /// Email\n  String get email =\u003e getField\u003cString\u003e(emailField)!;\n  set email(String value) =\u003e setField\u003cString\u003e(emailField, value);\n\n  /// Acc Name field name\n  static const String accNameField = 'acc_name';\n\n  /// Acc Name\n  String? get accName =\u003e getField\u003cString\u003e(accNameField);\n  set accName(String? value) =\u003e setField\u003cString\u003e(accNameField, value);\n\n  /// Phone Number field name\n  static const String phoneNumberField = 'phone_number';\n\n  /// Phone Number\n  String? get phoneNumber =\u003e getField\u003cString\u003e(phoneNumberField);\n  set phoneNumber(String? value) =\u003e setField\u003cString\u003e(phoneNumberField, value);\n\n  /// Contacts field name\n  static const String contactsField = 'contacts';\n\n  /// Contacts\n  List\u003cString\u003e get contacts =\u003e getListField\u003cString\u003e(contactsField);\n  set contacts(List\u003cString\u003e? value) =\u003e\n      setListField\u003cString\u003e(contactsField, value);\n\n  /// Created At field name\n  static const String createdAtField = 'created_at';\n\n  /// Created At\n  DateTime get createdAt =\u003e\n      getField\u003cDateTime\u003e(createdAtField, defaultValue: DateTime.now())!;\n  set createdAt(DateTime value) =\u003e setField\u003cDateTime\u003e(createdAtField, value);\n\n  /// Role field name\n  static const String roleField = 'role';\n\n  /// Role\n  UserRole get role =\u003e\n      getField\u003cUserRole\u003e(roleField, enumValues: UserRole.values)!;\n  set role(UserRole value) =\u003e setField\u003cUserRole\u003e(roleField, value);\n}\n\n```\n\n## 🚀 Usage Examples\n\n### Reading Data\n\n```dart\nfinal usersTable = UsersTable();\n\n// Fetch a single user\nfinal user = await usersTable.querySingleRow(\n  queryFn: (q) =\u003e q.eq(UsersRow.idField, 123),\n);\n\n// Access typed properties\nprint(user.email);\nprint(user.accName);\nprint(user.phoneNumber);\nprint(user.createdAt);\n\n// Fetch multiple users\nfinal adminUsers = await usersTable.queryRows(\n  queryFn: (q) =\u003e q\n  .eq(UsersRow.roleField, UserRole.admin.name)\n  .order(UserRow.emailField),\n);\n\n// Work with typed objects\nfor (final user in adminUsers) {\n  print('User ${user.id}:');\n  print('- Email: ${user.email}');\n  print('- Name: ${user.accName ?? \"No name set\"}');\n  print('- Phone: ${user.phoneNumber ?? \"No phone set\"}');\n  print('- Created: ${user.createdAt}');\n}\n\n// Query with complex conditions\nfinal recentUsers = await usersTable.queryRows(\n  queryFn: (q) =\u003e q\n  .gte(UsersRow.createdAtField, DateTime.now().subtract(Duration(days: 7)))\n  .ilike(UsersRow.emailField, '%@gmail.com')\n  .order(UsersRow.createdAtField, ascending: false),\n);\n```\n\n### Creating Records\n\n```dart\nfinal usersTable = UsersTable();\n\n// Create new record\nfinal adminUser = await usersTable.insert({\n  UsersRow.emailField: 'john@example.com',\n  UsersRow.roleField: UserRole.user.name,\n  UsersRow.accNameField: 'John Doe',\n  UsersRow.phoneNumberField: '+1234567890',\n});\n\n// The returned object is already typed\nprint(adminUser.email);\nprint(adminUser.accName);\n```\n\n### Updating Records\n\n```dart\nfinal usersTable = UsersTable();\n\n// Update by query\nawait usersTable.update(\n  data: {'acc_name': 'Jane Doe'},\n  matchingRows: (q) =\u003e q.eq('id', 123),\n);\n\n// Update with return value\nfinal updatedUsers = await usersTable.update(\n  data: {'role': UserRole.admin.name},\n  matchingRows: (q) =\u003e q.in_(UsersRow.idField, [1, 2, 3]),\n  returnRows: true,\n);\n```\n\n### Deleting Records\n\n```dart\nfinal usersTable = UsersTable();\n\n// Delete single record\n  await usersTable.delete(\n  matchingRows: (q) =\u003e q.eq(UsersRow.idField, 123),\n);\n\n// Delete with return value\nfinal deletedUsers = await usersTable.delete(\n  matchingRows: (q) =\u003e q.eq(UsersRow.roleField, UserRole.user.name),\n  returnRows: true,\n);\n```\n\n### Working with Related Data\n\n```dart\n// Get a pilot and their documents\nfinal pilotsTable = PilotsTable();\nfinal documentsTable = DocumentsTable();\n\n// Get pilot\nfinal pilots = await pilotsTable.queryRows(\n  queryFn: (q) =\u003e q.eq('id', pilotId),\n);\nfinal pilot = pilots.firstOrNull;\n\n// Get related documents\nif (pilot != null) {\n  final documents = await documentsTable.queryRows(\n    queryFn: (q) =\u003e q.eq('pilot_id', pilot.id),\n  );\n}\n```\n\n## 📝 Notes\n\n- Ensure your Supabase tables have proper primary keys defined\n- All generated models are null-safe\n- Custom column types are supported through type converters\n\n## 🤝 Contributing\n\nContributions are welcome! Please feel free to submit a Pull Request.\n\n## 📄 License\n\nThis project is licensed under the GPL-3.0 license - see the [LICENSE](LICENSE) file for details.\n\n---\n\n[dart_install_link]: https://dart.dev/get-dart\n[github_actions_link]: https://docs.github.com/en/actions/learn-github-actions\n[license_badge]: https://img.shields.io/badge/license-MIT-blue.svg\n[license_link]: https://opensource.org/licenses/MIT\n[very_good_analysis_badge]: https://img.shields.io/badge/style-very_good_analysis-B22C89.svg\n[very_good_analysis_link]: https://pub.dev/packages/very_good_analysis\n[very_good_coverage_link]: https://github.com/marketplace/actions/very-good-coverage\n[very_good_workflows_link]: https://github.com/VeryGoodOpenSource/very_good_workflows\n\n## Attributions\n\nBuilt using the great work by [Kennerd](https://github.com/Kemerd) at [Supabase Flutter Codegen](https://github.com/Kemerd/supabase-flutter-codegen)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fkhuwn-soulutions%2Fsupabase_codegen","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fkhuwn-soulutions%2Fsupabase_codegen","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fkhuwn-soulutions%2Fsupabase_codegen/lists"}