All Downloads are FREE. Search and download functionalities are using the official Maven repository.

br.com.objectos.way.flat.ListFlatContainerProperty Maven / Gradle / Ivy

There is a newer version: 0.6.0
Show newest version
/*
 * Copyright 2016 Objectos, Fábrica de Software LTDA.
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may not
 * use this file except in compliance with the License. You may obtain a copy of
 * the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
 * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
 * License for the specific language governing permissions and limitations under
 * the License.
 */
package br.com.objectos.way.flat;

import java.util.ArrayList;
import java.util.List;
import java.util.Optional;

import br.com.objectos.way.code.AnnotationInfo;
import br.com.objectos.way.code.SimpleTypeInfo;
import br.com.objectos.way.code.TypeInfo;
import br.com.objectos.way.code.TypeParameterInfo;
import br.com.objectos.way.flat.FlatImplementations;
import br.com.objectos.way.pojo.plugin.Property;

import com.squareup.javapoet.FieldSpec.Builder;
import com.squareup.javapoet.MethodSpec;
import com.squareup.javapoet.TypeName;

/**
 * @author [email protected] (Marcio Endo)
 */
abstract class ListFlatContainerProperty extends FlatContainerProperty {

  public ListFlatContainerProperty(Property property) {
    super(property);
  }

  public static FlatContainerProperty of(Property property, SimpleTypeInfo returnTypeInfo) {
    SimpleTypeInfo elementTypeInfo = returnTypeInfo.getTypeParameterInfoStream()
        .findFirst()
        .map(TypeParameterInfo::simpleTypeInfo)
        .get();

    Optional maybeTypeInfo = elementTypeInfo.typeInfo();
    if (!maybeTypeInfo.isPresent()) {
      return new Single(property, FlatRecordInfo.of(elementTypeInfo));
    }

    TypeInfo typeInfo = maybeTypeInfo.get();
    Optional maybeFlatImplementations = typeInfo.annotationInfo(FlatImplementations.class);
    return maybeFlatImplementations.isPresent()
        ? Multi.of(property, typeInfo, maybeFlatImplementations.get())
        : of0(property, typeInfo);
  }

  private static FlatContainerProperty of0(Property property, TypeInfo typeInfo) {
    Optional maybeFlatImplementations = property.annotationInfo(FlatImplementations.class);
    return maybeFlatImplementations.isPresent()
        ? Multi.of(property, typeInfo, maybeFlatImplementations.get())
        : Single.of(property, FlatRecordInfo.of(typeInfo));
  }

  @Override
  public void writeTo(MethodSpec.Builder method) {
    method.beginControlFlow("for ($T e : $L)", recordTypeName(), propertyName())
        .addStatement("e.writeTo(writer)")
        .endControlFlow();
  }

  @Override
  Builder flatReaderVisitorFieldSpec() {
    return super.flatReaderVisitorFieldSpec().initializer("new $T<>()", ArrayList.class);
  }

  abstract TypeName recordTypeName();

  private static class Multi extends ListFlatContainerProperty {

    private final List recordInfoList;
    private final TypeName recordTypeName;
    private final PrefixInfo prefixInfo;

    public Multi(Property property,
                 List recordInfoList,
                 TypeName recordTypeName,
                 PrefixInfo prefixInfo) {
      super(property);
      this.recordInfoList = recordInfoList;
      this.recordTypeName = recordTypeName;
      this.prefixInfo = prefixInfo;
    }

    public static FlatContainerProperty of(Property property, TypeInfo typeInfo, AnnotationInfo annotationInfo) {
      List recordInfoList = new ArrayList<>();
      List prefixInfoList = new ArrayList<>();
      annotationInfo.simpleTypeInfoArrayValue("value")
          .get()
          .stream()
          .map(FlatRecordInfo::of)
          .forEach(recordInfo -> {
            recordInfoList.add(recordInfo);
            prefixInfoList.add(recordInfo.prefixInfo());
          });
      return new Multi(property, recordInfoList, typeInfo.typeName(), prefixInfoList.get(0));
    }

    @Override
    public void visitLineMethod(MethodSpec.Builder method) {
      for (FlatRecordInfo recordInfo : recordInfoList) {
        recordInfo.visitLineMethod(method);
        method.addStatement("$L.add(new $T(reader))", propertyName(), recordInfo.pojoTypeName());
        method.addStatement("break");
      }
    }

    @Override
    PrefixInfo prefixInfo() {
      return prefixInfo;
    }

    @Override
    TypeName recordTypeName() {
      return recordTypeName;
    }

  }

  private static class Single extends ListFlatContainerProperty {

    private final FlatRecordInfo recordInfo;

    public Single(Property property, FlatRecordInfo recordInfo) {
      super(property);
      this.recordInfo = recordInfo;
    }

    public static FlatContainerProperty of(Property property, FlatRecordInfo recordInfo) {
      return new Single(property, recordInfo);
    }

    @Override
    public void visitLineMethod(MethodSpec.Builder method) {
      recordInfo.visitLineMethod(method);
      method.addStatement("$L.add(new $T(reader))", propertyName(), recordInfo.pojoTypeName());
      method.addStatement("break");
    }

    @Override
    PrefixInfo prefixInfo() {
      return recordInfo.prefixInfo();
    }

    @Override
    TypeName recordTypeName() {
      return recordInfo.typeName();
    }

  }

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy