net.autobuilder.core.ParaParameter Maven / Gradle / Ivy
package net.autobuilder.core;
import com.squareup.javapoet.ClassName;
import com.squareup.javapoet.CodeBlock;
import com.squareup.javapoet.FieldSpec;
import com.squareup.javapoet.ParameterSpec;
import com.squareup.javapoet.ParameterizedTypeName;
import com.squareup.javapoet.TypeSpec;
import java.util.List;
import java.util.Optional;
import java.util.function.BiConsumer;
import java.util.function.BiFunction;
import java.util.function.Function;
import static java.util.Arrays.asList;
import static java.util.Collections.singletonList;
abstract class ParaParameter {
static abstract class Cases {
abstract R parameter(Parameter parameter, P p);
abstract R collectionish(Collectionish collectionish, P p);
abstract R optionalish(Optionalish optionalish, P p);
}
private static Function asFunction(Cases cases) {
return parameter -> parameter.accept(cases, null);
}
private static BiConsumer asConsumer(Cases cases) {
return (parameter, p) -> parameter.accept(cases, p);
}
private static BiFunction biFunction(Cases cases) {
return (parameter, p) -> parameter.accept(cases, p);
}
abstract R accept(Cases cases, P p);
static final Function GET_PARAMETER =
asFunction(new ParaParameter.Cases() {
@Override
Parameter parameter(Parameter parameter, Void _null) {
return parameter;
}
@Override
Parameter collectionish(Collectionish collectionish, Void _null) {
return collectionish.parameter;
}
@Override
Parameter optionalish(Optionalish optionalish, Void _null) {
return optionalish.parameter;
}
});
static final Function> METHOD_NAMES =
asFunction(new ParaParameter.Cases, Void>() {
@Override
List parameter(Parameter parameter, Void _null) {
return singletonList(parameter.setterName);
}
@Override
List collectionish(Collectionish collectionish, Void _null) {
return asList(collectionish.parameter.setterName, collectionish.accumulatorName());
}
@Override
List optionalish(Optionalish optionalish, Void _null) {
return singletonList(optionalish.parameter.setterName);
}
});
static final Function> FIELD_NAMES =
asFunction(new ParaParameter.Cases, Void>() {
@Override
List parameter(Parameter parameter, Void _null) {
return singletonList(parameter.setterName);
}
@Override
List collectionish(Collectionish collectionish, Void _null) {
return asList(collectionish.parameter.setterName,
collectionish.builderFieldName());
}
@Override
List optionalish(Optionalish optionalish, Void _null) {
return singletonList(optionalish.parameter.setterName);
}
});
static final Function NO_ACCUMULATOR =
asFunction(new ParaParameter.Cases() {
@Override
ParaParameter parameter(Parameter parameter, Void _null) {
return parameter;
}
@Override
ParaParameter collectionish(Collectionish collectionish, Void _null) {
return collectionish.parameter;
}
@Override
ParaParameter optionalish(Optionalish optionalish, Void _null) {
return optionalish;
}
});
static final Function ORIGINAL_SETTER =
asFunction(new ParaParameter.Cases() {
@Override
ParaParameter parameter(Parameter parameter, Void _null) {
return parameter.originalSetter();
}
@Override
ParaParameter collectionish(Collectionish collectionish, Void _null) {
return collectionish.withParameter(collectionish.parameter.originalSetter());
}
@Override
ParaParameter optionalish(Optionalish optionalish, Void _null) {
return optionalish.withParameter(optionalish.parameter.originalSetter());
}
});
static final Function AS_SETTER_PARAMETER =
asFunction(new ParaParameter.Cases() {
@Override
ParameterSpec parameter(Parameter parameter, Void _null) {
return ParameterSpec.builder(parameter.type, parameter.setterName).build();
}
@Override
ParameterSpec collectionish(Collectionish collectionish, Void _null) {
return collectionish.asSetterParameter();
}
@Override
ParameterSpec optionalish(Optionalish optionalish, Void _null) {
return ParameterSpec.builder(optionalish.parameter.type,
optionalish.parameter.setterName).build();
}
});
static final Function SETTER_ASSIGNMENT =
asFunction(new ParaParameter.Cases() {
@Override
CodeBlock parameter(Parameter parameter, Void _null) {
FieldSpec field = parameter.asField();
ParameterSpec p = AS_SETTER_PARAMETER.apply(parameter);
return CodeBlock.builder()
.addStatement("this.$N = $N", field, p).build();
}
@Override
CodeBlock collectionish(Collectionish collectionish, Void _null) {
return collectionish.setterAssignment();
}
@Override
CodeBlock optionalish(Optionalish optionalish, Void _null) {
FieldSpec field = optionalish.parameter.asField();
ParameterSpec p = AS_SETTER_PARAMETER.apply(optionalish);
return CodeBlock.builder()
.addStatement("this.$N = $N", field, p).build();
}
});
static final BiFunction GET_FIELD_VALUE =
biFunction(new ParaParameter.Cases() {
@Override
CodeBlock parameter(Parameter parameter, ParameterSpec builder) {
return Collectionish.emptyBlock(parameter, builder)
.orElse(Optionalish.emptyBlock(parameter, builder)
.orElse(CodeBlock.of("$N.$N", builder, parameter.asField())));
}
@Override
CodeBlock collectionish(Collectionish collectionish, ParameterSpec builder) {
return collectionish.getFieldValue(builder);
}
@Override
CodeBlock optionalish(Optionalish optionalish, ParameterSpec builder) {
return optionalish.getFieldValue(builder);
}
});
static final BiConsumer CLEAR_ACCUMULATOR =
asConsumer(new ParaParameter.Cases() {
@Override
Void parameter(Parameter parameter, CodeBlock.Builder builder) {
return null;
}
@Override
Void collectionish(Collectionish collectionish, CodeBlock.Builder builder) {
builder.addStatement("this.$N = null",
collectionish.asBuilderField());
return null;
}
@Override
Void optionalish(Optionalish optionalish, CodeBlock.Builder builder) {
return null;
}
});
static final BiConsumer ADD_OPTIONALISH_OVERLOAD =
asConsumer(new ParaParameter.Cases() {
@Override
Void parameter(Parameter parameter, TypeSpec.Builder builder) {
return null;
}
@Override
Void collectionish(Collectionish collectionish, TypeSpec.Builder block) {
return null;
}
@Override
Void optionalish(Optionalish optionalish, TypeSpec.Builder builder) {
builder.addMethod(optionalish.convenienceOverloadMethod());
return null;
}
});
static final BiConsumer ADD_ACCUMULATOR_FIELD =
asConsumer(new ParaParameter.Cases() {
@Override
Void parameter(Parameter parameter, TypeSpec.Builder builder) {
return null;
}
@Override
Void collectionish(Collectionish collectionish, TypeSpec.Builder builder) {
builder.addField(collectionish.asBuilderField());
return null;
}
@Override
Void optionalish(Optionalish optionalish, TypeSpec.Builder builder) {
return null;
}
});
static final BiConsumer ADD_ACCUMULATOR_METHOD =
asConsumer(new ParaParameter.Cases() {
@Override
Void parameter(Parameter parameter, TypeSpec.Builder builder) {
return null;
}
@Override
Void collectionish(Collectionish collectionish, TypeSpec.Builder builder) {
builder.addMethod(collectionish.accumulatorMethod());
return null;
}
@Override
Void optionalish(Optionalish optionalish, TypeSpec.Builder builder) {
return null;
}
});
static final BiConsumer ADD_ACCUMULATOR_OVERLOAD =
asConsumer(new ParaParameter.Cases() {
@Override
Void parameter(Parameter parameter, TypeSpec.Builder builder) {
return null;
}
@Override
Void collectionish(Collectionish collectionish, TypeSpec.Builder builder) {
builder.addMethod(collectionish.accumulatorMethodOverload());
return null;
}
@Override
Void optionalish(Optionalish optionalish, TypeSpec.Builder builder) {
return null;
}
});
static final BiFunction> CLEANUP_CODE =
biFunction(new ParaParameter.Cases, ParameterSpec>() {
@Override
Optional parameter(Parameter parameter, ParameterSpec builder) {
if (parameter.type instanceof ClassName ||
parameter.type instanceof ParameterizedTypeName) {
return Optional.of(CodeBlock.builder().addStatement("$N.$L(null)",
builder, parameter.setterName).build());
}
return Optional.empty();
}
@Override
Optional collectionish(Collectionish collectionish, ParameterSpec builder) {
return this.parameter(collectionish.parameter, builder);
}
@Override
Optional optionalish(Optionalish optionalish, ParameterSpec builder) {
return Optional.of(CodeBlock.builder().addStatement("$N.$L(($T) null)",
builder, optionalish.parameter.setterName,
optionalish.parameter.type).build());
}
});
}