generateForAnnotatedElement method

  1. @override
FutureOr<String> generateForAnnotatedElement(
  1. Element element,
  2. ConstantReader annotation,
  3. 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.

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) {
  if (element.kind != ElementKind.CLASS) {
    throw 'ERROR: @Entity can only be used on a class, found on $element';
  }
  var inspector = EntityInspector();
  element.visitChildren(inspector);
  inspector.visitClassElement(element as ClassElement);
  final typeName = element.name;
  final serializedName = _nameOf(element);
  var deserializer = '$typeName.fromJson(map)';
  if (inspector.deserializer == null) {
    deserializer = _generateDeserializer(inspector, typeName);
  }
  var serializer = 'entity.toJson()';
  if (inspector.serializer == null) {
    serializer = _generateSerializer(inspector);
  }
  return '''
  class $typeName\$BoxSupport extends EntitySupport<$typeName> {
    $typeName\$BoxSupport() : super(
      name: '$serializedName',
      keyAccessor: ${_buildKeyAccessor(inspector)},
      fieldAccessors: ${_buildFieldAccessors(inspector)},
      keyFields: [${inspector.keys.map((key) => "'${key.name}'").join(',')}],
      fieldTypes: {${_buildFieldTypes(inspector)}},
      indexes: [${_buildIndexes(inspector)}],
    );

    @override
    $typeName deserialize(Map<String, dynamic> map) => $deserializer;

    @override
    Map<String, dynamic> serialize($typeName entity) => $serializer;
  }
  ''';
}