dart-lang / source_gen

Automatic source code generation for Dart
https://pub.dev/packages/source_gen
BSD 3-Clause "New" or "Revised" License
482 stars 104 forks source link

LibraryBuilder should allow more customized build extensions #692

Closed Vildnex closed 7 months ago

Vildnex commented 7 months ago

Current folder project structure after running that command:

├── lib
│   ├── entity_generator.dart
│   └── test_files
│       ├── annotation
│       │   └── annotation.dart
│       ├── classes2.dart
│       ├── classes2.entity.dart
│       ├── classes.dart
│       ├── classes.entity.dart
│       └── gen
├── pubspec.lock
└── pubspec.yaml

Current folder project structure after generating them into the custom folder:

├── lib
│   ├── entity_generator.dart
│   └── test_files
│       ├── annotation
│       │   └── annotation.dart
│       ├── classes2.dart
│       ├── classes.dart
│       └── gen
│           ├── classes.entity.dart
|           └── classes2.entity.dart
├── pubspec.lock
└── pubspec.yaml

entity_generator.dart:

class EntityGenerator extends GeneratorForAnnotation<Entity> {
  @override
  generateForAnnotatedElement(Element element, ConstantReader annotation, BuildStep buildStep) {
    if (element is! ClassElement) {
      throw InvalidGenerationSourceError('`@Entity` can only be used on classes.', element: element);
    }

    final className = element.displayName;
    final buffer = StringBuffer();

    // Generate the class with entity exports
    buffer.writeln('class $className extends Entity {}');
    return buffer.toString();
  }
}

Builder entityBuilder(BuilderOptions options) => LibraryBuilder(EntityGenerator(), generatedExtension: '.entity.dart');

build.yaml:

    targets:
      $default:
        builders:
          test_app|export_locating_builder:
            enabled: true

    builders:
      export_locating_builder:
        import: "package:test_app/entity_generator.dart"
        builder_factories: [ "entityBuilder" ]
        build_extensions: {
          '^lib/test_files/{{}}.dart': ['lib/test_files/gen/{{}}.entity.dart']
        }
        auto_apply: dependents
        build_to: source

For the moment even if I did the part {{}} the files will still be generated next to the original class instead of the gen folder.

Sources that I've checked already:

jakemac53 commented 7 months ago

If you run dart run build_runner doctor I think it will highlight the issue, which is a mismatch in build extensions (the build extension in your build.yaml isn't what the actual builder is declaring, and the latter is what is actually used).

I don't believe that LibraryBuilder allows you to configure the extensions in such a way that you could support this, ~but its worth filing an issue on the source_gen package to ask for it?~ (I just transferred the issue here).

jakemac53 commented 7 months ago

Essentially the core of the issue is that LibraryBuilder only allows you to configure the output extensions part of build extensions, and not the input extension (which is hardcoded to .dart). You would need to configure both.

Vildnex commented 7 months ago

@jakemac53, the output of the dart run build_runner doctor is [WARNING] Builder test_app:export_locating_builder uses input extension .dart which is not specified in the 'build.yaml' but I am not entirely sure how to fix it. So basically because the LibraryBuilder does not have support for this, what other Builder should I use? Or there is no other way to do this except building my own Builder?

jakemac53 commented 7 months ago

Or there is no other way to do this except building my own Builder?

Essentially this, the source_gen package is pretty opinionated today about output extensions. Afaik it does this somewhat in order to simplify some of the things it does (such as checking that the user included the appropriate part file, where relevant).

jakemac53 commented 7 months ago

You can fwiw re-use some of the utilities provided by this package to help create the builder though.

Vildnex commented 7 months ago

I see, alright then thanks for clarify this