/** * Establishes the type bound: * * <ol> * <li>{@code<? extends Number>}, returns Number * <li>{@code<? super Number>}, returns Number * <li>{@code<?>}, returns Object * <li>{@code<T extends Number>, returns Number} * </ol> * * @param typeMirror the type to return the bound for * @return the bound for this parameter */ public TypeMirror getTypeBound(TypeMirror typeMirror) { if (typeMirror.getKind() == TypeKind.WILDCARD) { WildcardType wildCardType = (WildcardType) typeMirror; if (wildCardType.getExtendsBound() != null) { return wildCardType.getExtendsBound(); } if (wildCardType.getSuperBound() != null) { return wildCardType.getSuperBound(); } String wildCardName = wildCardType.toString(); if ("?".equals(wildCardName)) { return elementUtils.getTypeElement(Object.class.getCanonicalName()).asType(); } } else if (typeMirror.getKind() == TypeKind.TYPEVAR) { TypeVariable typeVariableType = (TypeVariable) typeMirror; if (typeVariableType.getUpperBound() != null) { return typeVariableType.getUpperBound(); } // Lowerbounds intentionally left out: Type variables otherwise have a lower bound of // NullType. } return typeMirror; }
void caseType(TypeMirror type) { if (ended) { // to prevent additional recursive effects when using workaround return; } switch (type.getKind()) { case ERROR: unresolvedTypeHasOccured = true; // $FALL-THROUGH$ case DECLARED: DeclaredType declaredType = (DeclaredType) type; appendResolved(declaredType); appendTypeArguments(type, declaredType); break; case ARRAY: TypeMirror componentType = ((ArrayType) type).getComponentType(); int mark = buffer.length(); caseType(componentType); cutTypeArgument(type, mark); buffer.append('[').append(']'); break; case WILDCARD: WildcardType wildcard = (WildcardType) type; @Nullable TypeMirror extendsBound = wildcard.getExtendsBound(); @Nullable TypeMirror superBound = wildcard.getSuperBound(); if (extendsBound != null) { buffer.append("? extends "); caseType(extendsBound); } else if (superBound != null) { buffer.append("? super "); caseType(superBound); } else { buffer.append('?'); } break; case TYPEVAR: // this workaround breaks this recursive flow, so we set up // ended flag if (tryToUseSourceAsAWorkaround()) { ended = true; break; } reporter.error( "It is a compiler/annotation processing bug to receive type variables '%s' here." + " To avoid it — do not use not yet generated types in %s attribute", type, element.getSimpleName()); // just append as toString whatever we have buffer.append(type); break; default: buffer.append(type); } }
public static TypeName get(javax.lang.model.type.WildcardType mirror) { TypeMirror extendsBound = mirror.getExtendsBound(); if (extendsBound == null) { TypeMirror superBound = mirror.getSuperBound(); if (superBound == null) { return subtypeOf(Object.class); } else { return supertypeOf(TypeName.get(superBound)); } } else { return subtypeOf(TypeName.get(extendsBound)); } }
static TypeName get( javax.lang.model.type.WildcardType mirror, Map<TypeParameterElement, TypeVariableName> typeVariables) { TypeMirror extendsBound = mirror.getExtendsBound(); if (extendsBound == null) { TypeMirror superBound = mirror.getSuperBound(); if (superBound == null) { return subtypeOf(Object.class); } else { return supertypeOf(TypeName.get(superBound, typeVariables)); } } else { return subtypeOf(TypeName.get(extendsBound, typeVariables)); } }
@Override public JsonElement visitList(DeclaredType t, Element el) { JsonElement jsonElement; String converterClassName = getConverterClassName(el); if (converterClassName != null) { jsonElement = genJsonElement(t, el, Kind.CONVERTER); } else { List<? extends TypeMirror> generics = t.getTypeArguments(); if (generics.size() != 1) { Log.e("expected single type generics.", el); encountError = true; return defaultAction(t, el); } TypeMirror tm = generics.get(0); if (tm instanceof WildcardType) { WildcardType wt = (WildcardType) tm; TypeMirror extendsBound = wt.getExtendsBound(); if (extendsBound != null) { tm = extendsBound; } TypeMirror superBound = wt.getSuperBound(); if (superBound != null) { Log.e("super is not supported.", el); encountError = true; return defaultAction(t, el); } } Element type = processingEnv.getTypeUtils().asElement(tm); JsonModel hash = type.getAnnotation(JsonModel.class); if (hash == null) { Log.e("expect for use decorated class by JsonModel annotation.", el); encountError = true; return defaultAction(t, el); } jsonElement = new JsonElement(); jsonElement.setKey(getElementKeyString(el)); JsonKey key = el.getAnnotation(JsonKey.class); String setter = getElementSetter(el); if (key.in() && setter == null) { Log.e("can't find setter method", el); encountError = true; return defaultAction(t, el); } String getter = getElementGetter(el); if (key.out() && getter == null) { Log.e("can't find getter method", el); encountError = true; return defaultAction(t, el); } jsonElement.setIn(key.in()); jsonElement.setSetter(setter); jsonElement.setOut(key.out()); jsonElement.setGetter(getter); jsonElement.setModelName(tm.toString()); jsonElement.setKind(Kind.LIST); } return jsonElement; }
static WildcardName forTypeMirror(WildcardType mirror) { return new WildcardName( Optional.fromNullable(mirror.getExtendsBound()).transform(FOR_TYPE_MIRROR), Optional.fromNullable(mirror.getSuperBound()).transform(FOR_TYPE_MIRROR)); }
@Override public TypeElement visitWildcard(WildcardType t, Void p) { return visit(t.getExtendsBound()); }