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

br.com.objectos.code.pojo.CollectionAttributeMethod Maven / Gradle / Ivy

The newest version!
/*
 * Copyright 2015 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.code.pojo;

import java.util.List;
import java.util.stream.Stream;

import javax.lang.model.element.Modifier;

import br.com.objectos.code.Code;
import br.com.objectos.code.MethodInfo;
import br.com.objectos.code.SimpleTypeInfo;
import br.com.objectos.core.auto.AutoPojo;

import com.google.common.collect.ImmutableList;
import com.squareup.javapoet.ArrayTypeName;
import com.squareup.javapoet.CodeBlock;
import com.squareup.javapoet.MethodSpec;
import com.squareup.javapoet.MethodSpec.Builder;
import com.squareup.javapoet.TypeName;

/**
 * @author [email protected] (Marcio Endo)
 */
@AutoPojo
abstract class CollectionAttributeMethod extends AttributeMethod {

  abstract CollectionNaming collectionNaming();

  CollectionAttributeMethod() {
  }

  public static CollectionAttributeMethodBuilder builder() {
    return new CollectionAttributeMethodBuilderPojo();
  }

  public static AttributeMethod of(Naming naming, MethodInfo methodInfo, SimpleTypeInfo returnTypeInfo) {
    CollectionNaming collectionNaming = CollectionNaming.of(returnTypeInfo);
    return collectionNaming != null
        ? CollectionAttributeMethod.builder()
            .naming(naming)
            .accessInfo(methodInfo.accessInfo())
            .name(methodInfo.name())
            .fieldName(methodInfo.fieldName())
            .returnTypeName(returnTypeInfo.typeName())
            .collectionNaming(collectionNaming)
            .build()
        : SimpleAttributeMethod.of(naming, methodInfo, returnTypeInfo);
  }

  @Override
  Stream builderClassSetter() {
    TypeName returns = naming().builderInnerTypeName(this);
    return Stream.of(
        builderClassSetterVarargs(returns),
        builderClassSetterStandard(returns)
        );
  }

  @Override
  List builderInterfaceMiddle() {
    TypeName returns = naming().builderInnerTypeName(this);
    return ImmutableList. builder()
        .add(builderInterfaceMiddleVarargs(returns))
        .add(builderInterfaceMiddleStandard(returns))
        .build();
  }

  private MethodSpec builderClassSetterStandard(TypeName returns) {
    Builder method = builderClassMethod(returns);
    standard(method);
    return method
        .addCode(builderClassSetterBody())
        .build();
  }

  private MethodSpec builderClassSetterVarargs(TypeName returns) {
    Builder method = builderClassMethod(returns);
    varargs(method);
    method.addCode(Code.nullCheck("elements"));
    method.addCode("\n");
    method.addStatement("$T $L = new $T<>(elements.length)",
        collectionNaming().collectionTypeNameBound(), fieldName(), collectionNaming().collectionTypeName());
    method.addCode("\n");
    method.addCode(CodeBlock.builder()
        .beginControlFlow("for (int i = 0; i < elements.length; i++)")
        .addStatement("$T e = elements[i]", collectionNaming().elementTypeName())
        .add(Code.nullCheck("e"))
        .addStatement("$L.add(e)", fieldName())
        .endControlFlow()
        .build());
    return method
        .addCode("\n")
        .addStatement("this.$L = $L", fieldName(), fieldName())
        .addStatement("return this")
        .build();
  }

  private MethodSpec builderInterfaceMiddleStandard(TypeName returns) {
    Builder method = builderIfaceMethod(returns);
    standard(method);
    return method.build();
  }

  private MethodSpec builderInterfaceMiddleVarargs(TypeName returns) {
    Builder method = builderIfaceMethod(returns);
    varargs(method);
    return method.build();
  }

  private MethodSpec.Builder builderIfaceMethod(TypeName returns) {
    return MethodSpec.methodBuilder(fieldName())
        .addModifiers(Modifier.PUBLIC, Modifier.ABSTRACT)
        .returns(returns);
  }

  private MethodSpec.Builder builderClassMethod(TypeName returns) {
    return MethodSpec.methodBuilder(fieldName())
        .addAnnotation(Override.class)
        .addModifiers(Modifier.PUBLIC)
        .returns(returns);
  }

  private void standard(MethodSpec.Builder method) {
    method.addParameter(returnTypeName(), fieldName());
  }

  private void varargs(MethodSpec.Builder method) {
    TypeName elementTypeName = collectionNaming().elementTypeName();
    method.addParameter(ArrayTypeName.of(elementTypeName), "elements");
    method.varargs();
  }

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy