supabase-dart-repo-generator-fixed
v1.3.1
Published
A CLI tool to generate Dart repositories and models for Supabase tables with database functions and triggers support
Maintainers
Readme
Supabase Dart Repository Generator
Generate type-safe Dart repositories and models from your Supabase database schema.
Features
- 🚀 Automatically generate Dart models and repositories
- 🔄 Support for real-time subscriptions
- 🔌 Works with local or remote Supabase instances
- 🧩 Generates complete CRUD operations
- 📦 Includes repository provider for dependency injection
- 🎯 Follows Dart naming conventions (camelCase for fields)
- 🔒 Type-safe JSON serialization with json_annotation
- 📝 Comprehensive documentation in generated code
- 🔄 Supports all common PostgreSQL data types
- 🎯 Generates proper Dart types based on PostgreSQL column types
- 📝 Supports nullable fields
- 🎯 Generates JSON serialization code
- 🎯 Generates repository methods for CRUD operations
- 🎯 Supports real-time subscriptions with Supabase stream
- 🎯 Generates a repository provider for easy dependency injection
- 🎯 Supports PostgreSQL enum types with proper Dart enum generation
- 🔄 Includes database functions as callable methods
- 📝 Documents database triggers for context
Installation
# Install globally
npm install -g supabase-dart-repo-generator-fixed
# Or use npx
npx supabase-dart-repo-generator-fixedUsage
Basic Usage
# Using environment variables
supabase-dart-repo-generator-fixed
# Direct PostgreSQL connection (recommended for local development)
supabase-dart-repo-generator-fixed --database postgresql://postgres:[email protected]:54322/postgres
# Supabase API connection
supabase-dart-repo-generator-fixed --url https://your-project.supabase.co --key your-service-key
# Using a schema file (bypasses database connection)
supabase-dart-repo-generator-fixed --schema path/to/schema.jsonDevelopment
# Clone the repository
git clone https://github.com/Albaraazain/supabase-dart-repo-generator.git
cd supabase-dart-repo-generator
# Install dependencies
npm install
# Run tests
npm test
# Clean up the project (removes test files and directories)
npm run cleanupOptions
-u, --url <url>: Supabase URL-k, --key <key>: Supabase service key-d, --database <url>: PostgreSQL connection URL-o, --output <dir>: Output directory (default:lib/generated)-v, --verbose: Enable verbose logging
Environment Variables
You can also set these in a .env file:
# For Supabase API access
SUPABASE_URL=http://localhost:54321
SUPABASE_SERVICE_KEY=your-service-key
# For direct PostgreSQL connection
DATABASE_URL=postgresql://postgres:[email protected]:54322/postgresGenerated Code Structure
lib/generated/
├── enums/
│ ├── status_enum.dart
│ └── index.dart
├── models/
│ ├── index.dart
│ ├── user_model.dart
│ ├── user_model.g.dart (generated by build_runner)
│ └── ...
├── repositories/
│ ├── index.dart
│ ├── user_repository.dart
│ └── ...
└── repository_provider.dartDatabase Functions and Triggers Support
The generator now includes support for PostgreSQL functions and triggers:
Database Functions
- 🔄 Automatically generates Dart wrappers for all database functions
- 🎯 Type-safe parameters and return values
- 📝 Includes documentation from database comments
- 🧩 Accessible through the repository provider
Example usage:
// Access a database function
final result = await repositoryProvider.databaseFunctions.calculateTotal(userId: 123);Database Triggers
- 📝 Generates documentation for all database triggers
- 🔍 Includes trigger definitions for reference
- 📚 Helps understand automatic database behaviors
This feature allows you to:
- Test database functions directly in PostgreSQL first
- Then use those tested functions from your Dart code
- Have documentation about triggers for context
- Reduce runtime errors by ensuring database functions work before using them in code
Model Features
The generated models include:
- 🔄 JSON serialization with
json_annotation - 🎯 Dart naming conventions (camelCase) with original database names preserved
- 📝 Documentation comments for all fields
- 🔄
copyWith()method for immutability - 📝
toString()method for debugging - 🔒 Type-safe field access
Repository Features
The generated repositories include:
- 🧩 Complete CRUD operations
- 🔄 Real-time subscriptions with Supabase
- 🔒 Type-safe query methods
- 📝 Documentation comments
Next Steps After Generation
- Add required dependencies to your
pubspec.yaml:
dependencies:
supabase_flutter: ^1.10.0
json_annotation: ^4.8.1
dev_dependencies:
build_runner: ^2.4.0
json_serializable: ^6.7.1- Run build_runner to generate JSON serialization code:
flutter pub run build_runner build --delete-conflicting-outputs- Initialize the repository provider in your app:
final repositoryProvider = RepositoryProvider(Supabase.instance.client);License
ISC
Changelog
1.1.0
- Added support for database functions with automatic Dart wrapper generation
- Added documentation for database triggers
- Improved repository provider to include database functions
- Enhanced schema fetcher to detect and include database functions and triggers
- Added type-safe parameter and return type handling for database functions
- Organized database functions by related tables in repositories
- Fixed HTML entity encoding issues in generated code
1.0.26
- Fixed issue with PostgreSQL interval type conversion
- Ensured interval fields are properly mapped to String type in Dart models
- Added special conversion methods for interval fields to handle different Dart types (String, int, double)
- Improved interval parsing to handle various interval formats
1.0.25
- Added support for PostgreSQL interval type handling
- Fixed issue with interval type conversion in Dart models
- Added special conversion logic for interval fields to handle int, double, and String types
- Updated documentation with interval type mapping information
1.0.22
- Fixed nullable enum field declarations in model classes
- Fixed type errors in copyWith method parameters for nullable enum types
- Ensured consistent type handling for nullable and non-nullable enum fields
- Fixed "missing_default_value_for_parameter" errors for nullable enum fields
1.0.21
- Fixed JSON serialization in generated models to use _$ClassNameFromJson and _$ClassNameToJson
- Removed duplicate toStringValue() method in enum classes
- Improved compatibility with json_serializable package
- Fixed linter errors that would cause build_runner to fail
1.0.20
- Fixed nullable enum handling in generated models
- Fixed type compatibility issues in copyWith methods for enum parameters
- Improved enum fromString method to always return a non-null value for non-nullable fields
- Fixed double question mark issue in copyWith method for nullable enum types
- Updated toStringValue method in enum classes for better consistency
1.0.19
- Fixed duplicate enum imports in generated model files
- Fixed type compatibility issues in copyWith methods for non-nullable enum parameters
- Improved handling of enum types in generated code to prevent type errors
- Fixed unnecessary null-aware operators on non-nullable types
1.0.18
- Fixed undefined method errors for enum fromString methods
- Added static fromString method directly on enum classes
- Improved type safety for non-nullable enum fields
- Fixed null-aware operator usage on non-nullable types
- Added nullable enum extension methods for better type safety
1.0.17
- Fixed type compatibility issues between enum fields and their JSON conversion functions
- Ensured non-nullable enum fields have proper fallback values
- Improved handling of null values in enum conversions
1.0.16
- Fixed SQL script for enum type detection and conversion
- Improved error handling in enum type conversion
- Added support for handling enum values with spaces
- Enhanced get_enum_types function for better enum detection
- Fixed HTML entity encoding in generated enum files
1.0.15
- Improved enum support with proper PostgreSQL enum type detection
- Added SQL script for converting text columns to enum types
- Enhanced documentation for setting up and using enum types
- Fixed enum detection in text columns that should be enums
1.0.14
- Added enum support with automatic Dart enum generation
- Enhanced schema fetcher to detect enum types in PostgreSQL
- Updated models and repositories to utilize enum types
- Added documentation for enum support
1.0.13
- Added enum support with automatic Dart enum generation
- Enhanced schema fetcher to detect enum types
- Updated models and repositories to utilize enum types
1.0.12
- Fixed stream method in repository template to use primaryKey as a list of strings
- Updated to match the latest Supabase Dart SDK stream API requirements
1.0.11
- Fixed repository template to work with latest Supabase Dart SDK
- Removed references to deprecated response.error and response.data properties
- Updated response handling to match current SDK structure
1.0.10
- Fixed CLI version display to match package version
- Improved error handling for template path resolution
- Enhanced HTML entity handling in generated models
1.0.9
- Fixed template path resolution for global installations
- Updated CLI version number to match package version
- Added better error handling for missing templates
1.0.8
- Added support for generating code for all tables at once
- Improved PostgreSQL type mapping for better type safety
- Enhanced documentation comments for fields and methods
- Fixed issues with HTML entity encoding in generated models
- Optimized repository provider for lazy initialization
1.0.7
- Fixed issue with double question marks in copyWith method for nullable fields
- Improved type handling in generated models
1.0.6
- Fixed repository parameter naming to use camelCase instead of snake_case
- Improved consistency between model and repository naming conventions
1.0.5
- Fixed HTML entity encoding issues in generated models
- Ensured proper handling of nullable parameters in copyWith methods
- Improved toString method formatting
1.0.4
- Added support for camelCase field names in Dart models
- Improved JSON serialization with @JsonKey annotations
- Enhanced repository methods with better error handling
Enum Support
The generator supports PostgreSQL enum types and will automatically generate Dart enum classes for them. When a column in your database uses an enum type, the generator will create a corresponding Dart enum and use it in the generated models and repositories.
Setting Up Enum Types in PostgreSQL
For the best experience with enum types, you should define them properly in your PostgreSQL database. Here's how:
Define the enum type:
CREATE TYPE user_role AS ENUM ('admin', 'user', 'guest');Use the enum type in your table columns:
CREATE TABLE users ( id UUID PRIMARY KEY DEFAULT uuid_generate_v4(), name TEXT NOT NULL, role user_role NOT NULL DEFAULT 'user' );Converting existing text columns to enum types: If you have existing text columns that should be enum types, you can convert them:
-- First, create the enum type CREATE TYPE user_role AS ENUM ('admin', 'user', 'guest'); -- Then, alter the column to use the enum type ALTER TABLE users ALTER COLUMN role TYPE user_role USING role::user_role;
We've provided a SQL script in sql/update_enum_columns.sql that demonstrates how to define enum types and update columns to use them.
Alternative: Using the get_enum_types Function
If you can't modify your database schema to use proper enum types (for example, in a shared database), you can use the get_enum_types() function to tell the generator which text columns should be treated as enums:
CREATE OR REPLACE FUNCTION get_enum_types()
RETURNS TABLE(enum_name text, enum_value text) AS $$
BEGIN
RETURN QUERY
SELECT
t.typname::text as enum_name,
e.enumlabel::text as enum_value
FROM pg_type t
JOIN pg_enum e ON t.oid = e.enumtypid
JOIN pg_catalog.pg_namespace n ON n.oid = t.typnamespace
WHERE n.nspname = 'public'
ORDER BY t.typname, e.enumsortorder;
END;
$$ LANGUAGE plpgsql;Generated Dart Code
For each enum type, the generator will create a Dart enum class with methods for converting between string values and enum values. For example:
/// Represents the possible values for UserRole.
enum UserRole {
admin,
user,
guest;
/// Converts a string value from the database to the enum value
static UserRole fromString(String? value) {
if (value == null) return UserRole.admin;
return UserRole.values.firstWhere(
(e) => e.name == value,
orElse: () => UserRole.admin,
);
}
/// Converts the enum to a string for database storage
String toJson() => name;
}The generated models will use these enum types and include conversion methods for JSON serialization:
@JsonSerializable()
class User {
@JsonKey(name: 'id')
final String id;
@JsonKey(name: 'name')
final String name;
@JsonKey(name: 'role', fromJson: _roleFromJson, toJson: _roleToJson)
final UserRole role;
// ... constructor, fromJson, toJson methods ...
// Enum conversion helpers
static UserRole _roleFromJson(dynamic value) =>
UserRole.fromString(value as String);
static String _roleToJson(UserRole value) =>
value.toJson();
}PostgreSQL Type Mappings
The following PostgreSQL types are mapped to Dart types:
| PostgreSQL Type | Dart Type | |----------------|-----------| | int, integer, serial, bigserial | int | | text, varchar, char, character varying | String | | boolean | bool | | real, double precision, float | double | | numeric, decimal | double | | json, jsonb | Map<String, dynamic> | | timestamp, timestamptz, timestamp with time zone, timestamp without time zone | DateTime | | date | DateTime | | time, timetz | String | | interval | String | | uuid | String | | bytea | List |
Special Type Handling
Interval Type
PostgreSQL's interval type is mapped to String by default. However, the generator includes special conversion logic to handle cases where you want to use int or double in your Dart model:
- If the field type in your model is
String, the interval value is passed as-is. - If the field type is
int, the interval is converted to seconds (hours * 3600 + minutes * 60 + seconds). - If the field type is
double, the interval is converted to seconds with decimal precision.
Example of an interval field in a generated model:
@JsonKey(name: 'total_pause_duration', fromJson: _totalPauseDurationFromJson, toJson: _totalPauseDurationToJson)
final int? totalPauseDuration;
// Conversion methods
static int? _totalPauseDurationFromJson(dynamic value) {
if (value == null) return null;
// Convert PostgreSQL interval to seconds
if (value is String) {
try {
// Parse interval string like "00:17:02.998758"
final parts = value.split(':');
if (parts.length >= 3) {
final hours = int.parse(parts[0]);
final minutes = int.parse(parts[1]);
// Handle seconds with potential decimal part
final secondsPart = parts[2].split('.');
final seconds = int.parse(secondsPart[0]);
// Convert to total seconds
return hours * 3600 + minutes * 60 + seconds;
}
} catch (e) {
print('Error parsing interval: $value, $e');
}
}
return 0; // Default value if parsing fails
}
static dynamic _totalPauseDurationToJson(int? value) {
if (value == null) return null;
return value.toString();
}1.0.1
- Fixed issue with PostgreSQL interval type conversion - now correctly maps to String? in Dart models
- Fixed issue with missing field types in generated Dart models
- Added special conversion methods for interval fields to handle different Dart types (String, int, double)
- Improved interval parsing to handle various formats
1.0.0
- Initial release
