Add constructor-driven @Schemable and typed SchemaProvider<T>#93
Add constructor-driven @Schemable and typed SchemaProvider<T>#93leoafarias wants to merge 9 commits intomainfrom
Conversation
|
To view this pull requests documentation preview, visit the following URL: Documentation is deployed and generated using docs.page. |
There was a problem hiding this comment.
Pull request overview
This PR redesigns Ack’s annotation-driven schema generation around constructor-driven @Schemable() models and typed SchemaProvider<T> registrations, updating the generator plus repo docs/examples/tests to match the new surface.
Changes:
- Introduces
@Schemable+ constructor-parameter annotations (@SchemaConstructor,@SchemaKey,@Description) and typedSchemaProvider<T>. - Refactors
ack_generatoranalysis/resolution to be constructor-driven, adding provider- and prefix-aware type resolution plus case-style key canonicalization. - Migrates tests, examples, and docs from field-based
@AckFieldusage to constructor-parameter metadata (and deprecatesAckField/ keepsAckModelas a compatibility alias).
Reviewed changes
Copilot reviewed 59 out of 59 changed files in this pull request and generated 1 comment.
Show a summary per file
| File | Description |
|---|---|
| packages/ack_generator/test/test_utils/test_assets.dart | Updates in-memory test packages to include new Schemable/provider/constraints APIs. |
| packages/ack_generator/test/src/test_utilities.dart | Extends test mocks to support new FieldInfo fields/copying. |
| packages/ack_generator/test/src/generator_test.dart | Updates constructor shapes in generator fixture sources. |
| packages/ack_generator/test/src/builders/schema_builder_test.dart | Adjusts schema builder tests for new model registration behavior. |
| packages/ack_generator/test/src/builders/field_builder_test.dart | Updates nested-schema tests to register models for resolution. |
| packages/ack_generator/test/src/analyzer/model_analyzer_test.dart | Adds/updates tests for constructor selection, descriptions, providers, discriminator canonicalization. |
| packages/ack_generator/test/src/analyzer/field_analyzer_test.dart | Migrates field analysis tests to constructor-parameter analysis (SchemaKey, constraints, defaults). |
| packages/ack_generator/test/integration/schemable_provider_resolution_test.dart | New integration coverage for provider registration (same-file/imported/prefixed/mixin/base-class). |
| packages/ack_generator/test/integration/schemable_cross_file_resolution_test.dart | New integration coverage for cross-file/prefixed schemable type references. |
| packages/ack_generator/test/integration/nested_model_test.dart | Formatting/expectation updates to align with new generator behavior. |
| packages/ack_generator/test/integration/complex_model_test.dart | Migrates constraints/keys expectations from field-based to parameter-based generation. |
| packages/ack_generator/test/enum_test.dart | Minor formatting updates in enum generation tests. |
| packages/ack_generator/test/enhanced_error_messages_test.dart | Updates legacy-API failure messaging to match removed annotation shape. |
| packages/ack_generator/test/description_generation_test.dart | Replaces extensive legacy description tests with Schemable/parameter-driven description coverage. |
| packages/ack_generator/test/correctness_fixes_test.dart | Updates discriminated examples and description/constraint sources to constructor-param annotations. |
| packages/ack_generator/test/annotation_combination_edge_cases_test.dart | Replaces AckModel/AckField combinations with Schemable constructor-contract edge cases + error logging. |
| packages/ack_generator/test/additional_properties_args_test.dart | Test formatting updates; ensures args getter behavior remains stable. |
| packages/ack_generator/test/ack_field_comprehensive_test.dart | Replaces AckField comprehensive tests with constructor-contract/provider/error scenarios. |
| packages/ack_generator/lib/src/validation/model_validator.dart | Formatting-only change. |
| packages/ack_generator/lib/src/utils/type_resolver.dart | New resolver for primitives/collections/enums/schemables/providers (incl. prefixed type names). |
| packages/ack_generator/lib/src/utils/case_style_utils.dart | New case-style transformation utilities for schema key generation. |
| packages/ack_generator/lib/src/utils/annotation_utils.dart | New shared helpers for finding annotations, schema names, and import-prefix detection. |
| packages/ack_generator/lib/src/models/type_provider_info.dart | New model for provider metadata + stable identity keying for generic targets. |
| packages/ack_generator/lib/src/models/model_info.dart | Adds typeProviders to model metadata and updates docs/comments. |
| packages/ack_generator/lib/src/models/field_info.dart | Adds schemaExpressionOverride and a copyWith helper. |
| packages/ack_generator/lib/src/generator.dart | Switches class discovery/error messaging to @Schemable (with legacy alias support). |
| packages/ack_generator/lib/src/builders/schema_builder.dart | Uses shared schema-variable naming + simplifies discriminated/object schema building. |
| packages/ack_generator/lib/src/builders/field_builder.dart | Replaces ad-hoc type mapping with resolver + supports schema-expression overrides. |
| packages/ack_generator/lib/src/analyzer/model_analyzer.dart | Major refactor: constructor selection, named-parameter enforcement, provider validation, discriminator canonicalization. |
| packages/ack_generator/lib/src/analyzer/field_analyzer.dart | Refactor: analyzes constructor parameters (SchemaKey, Description, typed constraint annotations, caseStyle). |
| packages/ack_generator/README.md | Rewrites docs to describe constructor-driven Schemable + providers and deprecate legacy usage. |
| packages/ack_annotations/pubspec.yaml | Adds a direct dependency on ack for SchemaProvider/AckSchema types. |
| packages/ack_annotations/lib/src/schemable.dart | New Schemable annotation surface + SchemaProvider contract and parameter annotations. |
| packages/ack_annotations/lib/src/constraints.dart | Retargets constraint annotations from fields to constructor parameters. |
| packages/ack_annotations/lib/src/ack_type.dart | Updates docs to reference Schemable instead of AckModel in guidance. |
| packages/ack_annotations/lib/src/ack_model.dart | Deprecates AckModel and makes it extend Schemable as a compatibility alias. |
| packages/ack_annotations/lib/src/ack_field.dart | Deprecates AckField / required-mode enum to reflect removal from generator surface. |
| packages/ack_annotations/lib/ack_annotations.dart | Exports new Schemable + constraints surface. |
| packages/ack_annotations/README.md | Updates docs to constructor contract, parameter annotations, providers, and compatibility notes. |
| example/test/comprehensive_model_test.dart | Updates narrative/comments for schema-first validation phrasing. |
| example/lib/validation_test_model.dart | Migrates commented and active annotations to Schemable. |
| example/lib/test_extension_types.dart | Migrates example models from AckModel to Schemable. |
| example/lib/status_model.dart | Moves EnumString usage from field to constructor parameter and switches to Schemable. |
| example/lib/special_types_model.dart | Migrates to Schemable. |
| example/lib/simple_examples.g.dart | Updates generated schema output to match new constructor-requiredness behavior. |
| example/lib/simple_examples.dart | Migrates examples to Schemable. |
| example/lib/product_model.dart | Moves constraints onto constructor parameters; migrates to Schemable. |
| example/lib/mixed_examples.dart | Migrates examples to Schemable; moves EnumString constraint to parameter. |
| example/lib/edge_case_models.dart | Migrates to Schemable; replaces AckField jsonKey usage with SchemaKey parameters. |
| example/lib/discriminated_example.g.dart | Updates generated output for defaulted parameters now treated as optional. |
| example/lib/discriminated_example.dart | Migrates discriminated hierarchies to sealed + Schemable. |
| example/lib/described_model.dart | Moves descriptions/constraints to constructor parameter annotations. |
| example/lib/anyof_example.g.dart | Updates generated output to use provider schemas for anyOf wrapper types. |
| example/lib/anyof_example.dart | Adds SchemaProvider implementations + registers them via useProviders; migrates to Schemable. |
| docs/core-concepts/typesafe-schemas.mdx | Updates docs to reference Schemable constructor-driven generation. |
| docs/core-concepts/json-serialization.mdx | Updates codegen section for Schemable + constructor-driven behavior. |
| docs/core-concepts/configuration.mdx | Updates configuration guidance for parameter annotations and constructor contract rules. |
| docs/api-reference/index.mdx | Updates API reference to Schemable + adds docs for new annotations/providers. |
Comments suppressed due to low confidence (1)
packages/ack_generator/lib/src/analyzer/model_analyzer.dart:74
additionalPropertiesFieldis validated against a class field name, but the schema-generation skip logic compares it tofieldInfo.name(the selected constructor parameter name). If the extra-properties map is assigned via a differently named constructor parameter (e.g. initializer list) the field will incorrectly be emitted into the schema. Consider validating that the selected constructor has a parameter matchingadditionalPropertiesField(or that it’s an initializing formal for that field), and/or skipping based on the resolved field being assigned rather than only the parameter name.
if (additionalPropertiesField != null &&
fieldInfo.name == additionalPropertiesField) {
continue;
}
| 'enumString': (_, args) { | ||
| final values = args.map((v) => "'$v'").join(', '); | ||
| return 'Ack.enumString([$values])'; | ||
| }, |
There was a problem hiding this comment.
The enumString constraint builder replaces the in-progress schema with Ack.enumString(...), which means any constraints added before it (e.g. @MinLength, @Pattern, @Email) are silently discarded due to the current constraint ordering. Either apply EnumString first (so subsequent constraints can chain), or detect/forbid mixing EnumString with other string constraints and throw a clear error.
Remove dead code, deduplicate helpers, and detect conflicting @EnumString + string constraint combinations that were silently discarded during schema generation.
Summary
@Schemableand typedSchemaProvider<T>AckModel/AckField@EnumStringwas combined with other string constraintsChanges
Annotations (
ack_annotations)@Schemableannotation withuseProviders,caseStyle,discriminatedKey/discriminatedValue, andschemaName@SchemaConstructor,@SchemaKey,@DescriptionSchemaProvider<T>interface for registering custom type schemasAckModel(now extendsSchemable) andAckFieldGenerator (
ack_generator)AckSchema<T>return type, no duplicate targetscamelCase,snake_case,PascalCase,param-case)@EnumString+ string constraint combinationsDocs & Examples
@Schemablewith parameter annotationsValidation