generateForAnnotatedElement method
- Element element,
- ConstantReader annotation,
- BuildStep buildStep
Implement to return source code to generate for element.
This method is invoked based on finding elements annotated with an
instance of T. The annotation is provided as a ConstantReader.
Supported return values include a single String or multiple String instances within an Iterable or Stream. It is also valid to return a Future of String, Iterable, or Stream. When multiple values are returned through an iterable or stream they will be deduplicated. Typically each value will be an independent unit of code and the deduplication prevents re-defining the same member multiple times. For example if multiple annotated elements may need a specific utility method available it can be output for each one, and the single deduplicated definition can be shared.
Implementations should return null when no content is generated. Empty
or whitespace-only String instances are also ignored.
Implementation
@override
FutureOr<String> generateForAnnotatedElement(Element element, ConstantReader annotation, BuildStep buildStep) async {
String code = '';
String className = element.name ?? 'UnnamedClass';
List<Variable> variablesList = List<Variable>.empty(growable: true);
ElementVisitor visitor = ElementVisitor();
element.visitChildren(visitor);
List<Element> fields = element.children.where((child) => child.kind == ElementKind.FIELD).toList();
List<Element> constructors = element.children.where((child) => child.kind == ElementKind.CONSTRUCTOR).toList();
for (var item in fields) {
DartType? selectedVisitorField = visitor.fieldElements[item.name];
// code += selectedVisitorField == null ? '' : Prints.dartTypeInfo(selectedVisitorField);
Variable variable = Variable(
name: item.name ?? Strings.unnamedVariable,
type: selectedVisitorField,
typeString: selectedVisitorField?.toString(),
isCoreType: selectedVisitorField?.isDartCoreList == true ? selectedVisitorField?.isCoreTypeFromList : selectedVisitorField?.isCoreType,
isFinal: item.name.toString().contains('final'),
hasRequired: constructors.first.children.isEmpty ? null : constructors.first.children.firstWhere((e) => e.name == item.name).name.toString().contains('required '),
isNullable: item.name?.toString().split(' ').first.contains('?'),
isEnum: selectedVisitorField?.isEnum,
isList: selectedVisitorField?.isDartCoreList,
);
variablesList.add(variable);
}
code += AddCode.addCommentLine(' This File is Generated by ${PackageAuthorInfo.packageNameDescription}');
code += AddCode.addCommentLine(' [$className] Annotated with [${PackageAuthorInfo.annotationName}] with [${annotation.getName}] mode');
code += AddCode.addCommentLine(' Including:');
code += AddCode.addCommentLine(' Model Class, Entity Class and Mapper Class,');
code += AddCode.addCommentLine(' Model Classes includes [toJson] and [fromJson] functions, and Entity Classes are not!');
code += AddCode.addCommentLine(' Mappers will convert every filed in the class including [SubClasses], they should be annotated as well.');
code += AddCode.addCommentLine(
' [${PackageAuthorInfo.annotationName}] Annotation will generate all these fields for all Classes, so all subclasses should decorated with annotation to generate model, entity and mapper to use them here');
code += AddCode.addCommentLine(' [Enums] also supported and they will be detected and count into account for mappers and also json conversion');
annotation.getFreezed == true ? code += AddCode.addCommentLine(' Classes are decorated with [Freezed], other functions will generate with [Freezed]') : null;
code += AddCode.addSpace();
code += AddCode.addCommentLine(' Details:');
code += AddCode.addCommentLine(' Class: ${annotation.getAs ?? className}');
code += AddCode.addCommentLine(' Constructors Count: ${constructors.length}');
code += AddCode.addCommentLine(' Variables Count: ${variablesList.length}');
code += AddCode.addSpace();
GeneratorData generatorData = GeneratorData(
className: annotation.getAs ?? className,
variablesList: variablesList,
isAbstract: element.name?.toString().contains('abstract'),
isFreezed: annotation.getFreezed,
extended: annotation.getIsExtended,
);
if (annotation.getName == AnnotationTypes.all.name || annotation.getName == AnnotationTypes.model.name) {
code += AddCode.addCommentLine(' ==> Model Class:');
code += AddClass().generate(generatorData.copyWith(annotationType: AnnotationTypes.model));
}
if (annotation.getName == AnnotationTypes.all.name || annotation.getName == AnnotationTypes.entity.name) {
code += AddCode.addCommentLine(' ==> Entity Class:');
code += AddClass().generate(generatorData.copyWith(annotationType: AnnotationTypes.entity));
}
if (annotation.getName == AnnotationTypes.all.name) {
code += AddCode.addCommentLine(' ==> Mapper Classes:');
code += AddMapper().generate(generatorData);
}
return code;
}