use of com.squareup.javapoet.ParameterizedTypeName in project LoganSquare by bluelinelabs.
the class ObjectMapperInjector method getTypeSpec.
private TypeSpec getTypeSpec() {
TypeSpec.Builder builder = TypeSpec.classBuilder(mJsonObjectHolder.injectedClassName).addModifiers(Modifier.PUBLIC, Modifier.FINAL);
builder.addAnnotation(AnnotationSpec.builder(SuppressWarnings.class).addMember("value", "\"unsafe,unchecked\"").build());
builder.superclass(ParameterizedTypeName.get(ClassName.get(JsonMapper.class), mJsonObjectHolder.objectTypeName));
for (TypeParameterElement typeParameterElement : mJsonObjectHolder.typeParameters) {
builder.addTypeVariable(TypeVariableName.get((TypeVariable) typeParameterElement.asType()));
}
if (mJsonObjectHolder.hasParentClass()) {
FieldSpec.Builder parentMapperBuilder;
if (mJsonObjectHolder.parentTypeParameters.size() == 0) {
parentMapperBuilder = FieldSpec.builder(ParameterizedTypeName.get(ClassName.get(JsonMapper.class), mJsonObjectHolder.parentTypeName), PARENT_OBJECT_MAPPER_VARIABLE_NAME).addModifiers(Modifier.PRIVATE, Modifier.STATIC, Modifier.FINAL).initializer("$T.mapperFor($T.class)", LoganSquare.class, mJsonObjectHolder.parentTypeName);
} else {
parentMapperBuilder = FieldSpec.builder(ParameterizedTypeName.get(ClassName.get(JsonMapper.class), mJsonObjectHolder.getParameterizedParentTypeName()), PARENT_OBJECT_MAPPER_VARIABLE_NAME).addModifiers(Modifier.PRIVATE);
if (mJsonObjectHolder.typeParameters.size() == 0) {
parentMapperBuilder.initializer("$T.mapperFor(new $T<$T>() { })", LoganSquare.class, ParameterizedType.class, mJsonObjectHolder.getParameterizedParentTypeName());
}
}
builder.addField(parentMapperBuilder.build());
}
// TypeConverters could be expensive to create, so just use one per class
Set<ClassName> typeConvertersUsed = new HashSet<>();
for (JsonFieldHolder fieldHolder : mJsonObjectHolder.fieldMap.values()) {
if (fieldHolder.type instanceof TypeConverterFieldType) {
typeConvertersUsed.add(((TypeConverterFieldType) fieldHolder.type).getTypeConverterClassName());
}
}
for (ClassName typeConverter : typeConvertersUsed) {
builder.addField(FieldSpec.builder(typeConverter, getStaticFinalTypeConverterVariableName(typeConverter)).addModifiers(Modifier.PROTECTED, Modifier.STATIC, Modifier.FINAL).initializer("new $T()", typeConverter).build());
}
MethodSpec.Builder constructorBuilder = MethodSpec.constructorBuilder().addModifiers(Modifier.PUBLIC);
List<String> createdJsonMappers = new ArrayList<>();
if (mJsonObjectHolder.typeParameters.size() > 0) {
constructorBuilder.addParameter(ClassName.get(ParameterizedType.class), "type");
constructorBuilder.addStatement("partialMappers.put(type, this)");
for (TypeParameterElement typeParameterElement : mJsonObjectHolder.typeParameters) {
final String typeName = typeParameterElement.getSimpleName().toString();
final String typeArgumentName = typeName + "Type";
final String jsonMapperVariableName = getJsonMapperVariableNameForTypeParameter(typeName);
if (!createdJsonMappers.contains(jsonMapperVariableName)) {
createdJsonMappers.add(jsonMapperVariableName);
// Add a JsonMapper reference
builder.addField(FieldSpec.builder(ParameterizedTypeName.get(ClassName.get(JsonMapper.class), TypeVariableName.get(typeName)), jsonMapperVariableName).addModifiers(Modifier.PRIVATE, Modifier.FINAL).build());
constructorBuilder.addParameter(ClassName.get(ParameterizedType.class), typeArgumentName);
constructorBuilder.addStatement("$L = $T.mapperFor($L, partialMappers)", jsonMapperVariableName, LoganSquare.class, typeArgumentName);
}
}
constructorBuilder.addParameter(ParameterizedTypeName.get(ClassName.get(SimpleArrayMap.class), ClassName.get(ParameterizedType.class), ClassName.get(JsonMapper.class)), "partialMappers");
}
for (JsonFieldHolder jsonFieldHolder : mJsonObjectHolder.fieldMap.values()) {
if (jsonFieldHolder.type instanceof ParameterizedTypeField) {
final String jsonMapperVariableName = getJsonMapperVariableNameForTypeParameter(((ParameterizedTypeField) jsonFieldHolder.type).getParameterName());
if (!createdJsonMappers.contains(jsonMapperVariableName)) {
ParameterizedTypeName parameterizedType = ParameterizedTypeName.get(ClassName.get(JsonMapper.class), jsonFieldHolder.type.getTypeName());
createdJsonMappers.add(jsonMapperVariableName);
builder.addField(FieldSpec.builder(parameterizedType, jsonMapperVariableName).addModifiers(Modifier.PRIVATE, Modifier.FINAL).build());
String typeName = jsonMapperVariableName + "Type";
constructorBuilder.addStatement("$T $L = new $T<$T>() { }", ParameterizedType.class, typeName, ParameterizedType.class, jsonFieldHolder.type.getTypeName());
if (mJsonObjectHolder.typeParameters.size() > 0) {
constructorBuilder.beginControlFlow("if ($L.equals(type))", typeName);
constructorBuilder.addStatement("$L = ($T)this", jsonMapperVariableName, JsonMapper.class);
constructorBuilder.nextControlFlow("else");
constructorBuilder.addStatement("$L = $T.mapperFor($L, partialMappers)", jsonMapperVariableName, LoganSquare.class, typeName);
constructorBuilder.endControlFlow();
} else {
constructorBuilder.addStatement("$L = $T.mapperFor($L)", jsonMapperVariableName, LoganSquare.class, typeName);
}
}
}
}
if (createdJsonMappers.size() > 0) {
if (mJsonObjectHolder.hasParentClass()) {
constructorBuilder.addStatement("$L = $T.mapperFor(new $T<$T>() { })", PARENT_OBJECT_MAPPER_VARIABLE_NAME, LoganSquare.class, ParameterizedType.class, mJsonObjectHolder.getParameterizedParentTypeName());
}
builder.addMethod(constructorBuilder.build());
}
builder.addMethod(getParseMethod());
builder.addMethod(getParseFieldMethod());
builder.addMethod(getSerializeMethod());
addUsedJsonMapperVariables(builder);
addUsedTypeConverterMethods(builder);
return builder.build();
}
use of com.squareup.javapoet.ParameterizedTypeName in project tiger by google.
the class NewInjectorGenerator method createAnonymousBuiltinType.
/**
* Generate for either unique a binding or a contributor to a multi-binding. NewDependencyInfo is
* null for unique one and non-null or multi-binding one. ReferencingClass is the opposite, for
* multi-binding, it is the module in dependency. Scope is null for unique binding.
*/
private TypeSpec createAnonymousBuiltinType(ClassName leafInjectorClassName, NewBindingKey key, @Nullable TypeElement scope, @Nullable TypeElement referencingClass, @Nullable NewDependencyInfo newDependencyInfo) {
Preconditions.checkArgument(key.getTypeName() instanceof ParameterizedTypeName);
boolean isMultiBinding = newDependencyInfo != null;
if (isMultiBinding) {
Preconditions.checkArgument(referencingClass == null);
Preconditions.checkNotNull(scope);
} else {
Preconditions.checkNotNull(referencingClass);
}
TypeName rawTypeName = ((ParameterizedTypeName) key.getTypeName()).rawType;
Preconditions.checkArgument(Utils.hasBuiltinBinding(key), String.format("Built-in binding expected(Provider or Lazy), but get %s", key));
boolean isLazy = rawTypeName.equals(ClassName.get(Lazy.class));
NewBindingKey elementKey = Utils.getElementKeyForBuiltinBinding(key);
Preconditions.checkNotNull(elementKey);
if (!isMultiBinding) {
generateProvisionMethodIfNeeded(elementKey, referencingClass);
}
MethodSpec.Builder builderForGet = MethodSpec.methodBuilder("get").returns(elementKey.getTypeName()).addAnnotation(Override.class).addModifiers(Modifier.PUBLIC);
builderForGet.addStatement("$T var = null", elementKey.getTypeName());
if (isLazy) {
builderForGet.beginControlFlow("if (var == null)");
}
if (!isMultiBinding) {
builderForGet.addStatement("var = $N()", getProvisionMethodName(elementKey));
} else {
addNewStatementToMethodSpec(scope, newDependencyInfo, leafInjectorClassName, builderForGet, "var");
}
if (isLazy) {
builderForGet.endControlFlow();
}
builderForGet.addStatement("return var");
TypeSpec result = TypeSpec.anonymousClassBuilder("").addSuperinterface(key.getTypeName()).addMethod(builderForGet.build()).build();
return result;
}
use of com.squareup.javapoet.ParameterizedTypeName in project tiger by google.
the class NewInjectorGenerator method generateProvisionMethodForMap.
private void generateProvisionMethodForMap(final NewBindingKey key, TypeElement referencingClass, String suffix) {
TypeSpec.Builder componentSpecBuilder = getInjectorTypeSpecBuilder(getInjectorFor(key, referencingClass));
// messager.printMessage(Kind.NOTE, "generateProvisionMethodForSet: " + key +
// " PackagedInjector: "
// + getInjectorFor(key, referencingClass) + " SpecBuilder: " + componentSpecBuilder);
ParameterizedTypeName type = (ParameterizedTypeName) key.getTypeName();
Preconditions.checkArgument(type.rawType.equals(ClassName.get(Map.class)));
MethodSpec.Builder methodSpecBuilder = MethodSpec.methodBuilder(getProvisionMethodName(key) + suffix).addModifiers(suffix.isEmpty() ? Modifier.PUBLIC : Modifier.PRIVATE).returns(type);
methodSpecBuilder.addStatement("$T result = new $T<>()", type, HashMap.class);
methodSpecBuilder.addStatement("$T packagedMap", type);
SetMultimap<PackageElement, NewDependencyInfo> packageToDependencyInfoMap = HashMultimap.create();
Set<NewDependencyInfo> dependencyInfos = Utils.getDependencyInfo(dependencies, key);
Preconditions.checkNotNull(dependencyInfos, String.format("dependencyInfo not found for key: %s", key));
for (NewDependencyInfo dependencyInfo : Utils.getDependencyInfo(dependencies, key)) {
packageToDependencyInfoMap.put(Utils.getPackage(dependencyInfo.getSourceClassElement()), dependencyInfo);
}
for (PackageElement pkg : packageToDependencyInfoMap.keySet()) {
// messager.printMessage(Kind.NOTE, String.format("generateProvisionMethodForSet for %s from"
// +
// " %s", key, packageToDependencyInfoMap.get(pkg)));
generateMapTypeProvisionMethodForPackage(key, packageToDependencyInfoMap.get(pkg), suffix);
NewDependencyInfo dependencyInfo = Iterables.getFirst(packageToDependencyInfoMap.get(pkg), null);
Preconditions.checkNotNull(dependencyInfo, String.format("no dependencyInfo for set key %s in module %s", key, pkg));
ClassName packagedInjectorClassName = getPackagedInjectorForNewDependencyInfo(key, dependencyInfo);
methodSpecBuilder.addStatement("packagedMap = $L.$N().$N()", TOP_LEVEL_INJECTOR_FIELD, Utils.getGetMethodName(packagedInjectorClassName), getProvisionMethodName(key));
methodSpecBuilder.addStatement("result.putAll($L)", "packagedMap");
}
methodSpecBuilder.addStatement("return result");
componentSpecBuilder.addMethod(methodSpecBuilder.build());
}
use of com.squareup.javapoet.ParameterizedTypeName in project tiger by google.
the class NewInjectorGenerator method generateProvisionMethodFromClass.
/**
* Handles generic.
*/
private void generateProvisionMethodFromClass(NewBindingKey key, TypeElement referencingClass, String suffix) {
// System.out.println(
// "generateProvisionMethodFromClass. key: " + key + " referencingClass: " +
// referencingClass);
ClassName packagedInjectorClassName = getInjectorFor(key, referencingClass);
TypeSpec.Builder injectorSpecBuilder = getInjectorTypeSpecBuilder(packagedInjectorClassName);
TypeElement cls = getClassFromKey(key);
ExecutableElement ctor = Utils.findInjectedCtor(cls, processingEnv);
Preconditions.checkNotNull(ctor, String.format("Did not find ctor for %s", cls));
List<NewBindingKey> dependencyKeys = Utils.getDependenciesFromExecutableElement(ctor);
if (key.getTypeName() instanceof ParameterizedTypeName) {
List<NewBindingKey> specializedKeys = new ArrayList<>();
Map<TypeVariableName, TypeName> map = Utils.getMapFromTypeVariableToSpecialized((ParameterizedTypeName) key.getTypeName(), (ParameterizedTypeName) TypeName.get(cls.asType()));
for (NewBindingKey k : dependencyKeys) {
specializedKeys.add(Utils.specializeIfNeeded(k, map));
}
dependencyKeys = specializedKeys;
}
// System.out.println("generateProvisionMethodFromClass. dependencyKeys: " +
// dependencyKeys);
MethodSpec.Builder methodSpecBuilder = MethodSpec.methodBuilder(getProvisionMethodName(key) + suffix);
methodSpecBuilder.addModifiers(suffix.isEmpty() ? Modifier.PUBLIC : Modifier.PRIVATE).returns(key.getTypeName());
StringBuilder builder = new StringBuilder("$T result = new $T(");
if (dependencyKeys.size() > 0) {
for (NewBindingKey dependencyKey : dependencyKeys) {
// System.out.println("generateProvisionMethodFromClass. dependencyKey: "
// + dependencyKey);
generateProvisionMethodAndAppendAsParameter(dependencyKey, cls, packagedInjectorClassName, builder);
}
builder.delete(builder.length() - 2, builder.length());
}
builder.append(")");
methodSpecBuilder.addStatement(builder.toString(), key.getTypeName(), key.getTypeName());
if (Utils.hasInjectedFieldsOrMethods(cls, processingEnv)) {
// System.out.println("generateProvisionMethodFromClass. hasInjected");
generateInjectionMethod(key, referencingClass);
methodSpecBuilder.addStatement("inject(result)");
}
methodSpecBuilder.addStatement("return result");
injectorSpecBuilder.addMethod(methodSpecBuilder.build());
}
use of com.squareup.javapoet.ParameterizedTypeName in project tiger by google.
the class Utils method peelMapWithBuiltinValue.
/**
* If the key comes with value of type that has dagger builtin binding, return one
* with the type replaced by the element of the original value type, null otherwise.
* Nested built-in binding like Lazy<Lazy<Foo>>, Provider<Lazy<Foo>>, etc, are not
* supported.
*/
@Nullable
public static NewBindingKey peelMapWithBuiltinValue(NewBindingKey key) {
Preconditions.checkState(isMap(key), String.format("Expect a map but got %s", key));
ParameterizedTypeName parameterizedTypeName = (ParameterizedTypeName) key.getTypeName();
TypeName valueType = parameterizedTypeName.typeArguments.get(1);
if (hasBuiltinBinding(valueType)) {
TypeName mapKeyType = parameterizedTypeName.typeArguments.get(0);
TypeName elementType = Iterables.getOnlyElement(((ParameterizedTypeName) valueType).typeArguments);
TypeName newType = ParameterizedTypeName.get(ClassName.get(Map.class), mapKeyType, elementType);
return NewBindingKey.get(newType, key.getQualifier());
}
return null;
}
Aggregations