/** * Given a subtype of {@code Map<K,V>}, returns the corresponding map entry type {@code Map.Entry<K,V>}. * @param mapType the map subtype * @return the map entry type */ public static Type resolveMapEntryType(Type mapType) { Type keyType = resolveType(KEY, mapType); Type valueType = resolveType(VALUE, mapType); return resolveMapEntryType(keyType, valueType); }
private static Type resolveMaplikeEntryType(Type maplikeType, Type keyParam, Type valueParam) { Type keyType = GenericTypes.resolveType(keyParam, maplikeType); Type valueType = GenericTypes.resolveType(valueParam, maplikeType); return resolveMapEntryType(keyType, valueType); }
public SqlCallHandler(Class<?> sqlObjectType, Method method) { super(sqlObjectType, method); Type returnType = GenericTypes.resolveType(method.getGenericReturnType(), sqlObjectType); Class<?> returnClass = GenericTypes.getErasedType(returnType); if (Void.TYPE.equals(returnClass)) { returnOutParams = false; } else if (OutParameters.class.isAssignableFrom(returnClass)) { returnOutParams = true; } else { throw new IllegalArgumentException("@SqlCall methods may only return null or OutParameters at present"); } }
Type parameterType = resolveType(parameterizedSupertype.getTypeParameters()[n], type); return parameterType instanceof Class || parameterType instanceof ParameterizedType ? Optional.of(parameterType)
@Override public java.util.Optional<Type> elementType(Type containerType) { Class<?> erasedType = getErasedType(containerType); if (Multimap.class.isAssignableFrom(erasedType)) { Type keyType = resolveType(multimapKey, containerType); Type valueType = resolveType(multimapValue, containerType); return java.util.Optional.of(resolveMapEntryType(keyType, valueType)); } else if (Map.class.isAssignableFrom(erasedType)) { return java.util.Optional.of(resolveMapEntryType(containerType)); } return findGenericParameter(containerType, erasedType); }
@SuppressWarnings("unchecked") static RowMapperFactory factory() { return (type, config) -> { if (type instanceof ParameterizedType && getErasedType(type).equals(Map.Entry.class)) { Type keyType = resolveType(KEY_PARAM, type); Type valueType = resolveType(VALUE_PARAM, type); RowMapper<?> keyMapper = getKeyMapper(keyType, config); RowMapper<?> valueMapper = getValueMapper(valueType, config); return Optional.of(new MapEntryMapper(keyMapper, valueMapper)); } return Optional.empty(); }; }
@Test public void resolveTypeUnrelatedContext() throws NoSuchMethodException { abstract class A1<T> { abstract T a(); } abstract class A2<T> { abstract T a(); } abstract class B extends A2<String> {} Type t = A1.class.getDeclaredMethod("a").getGenericReturnType(); assertThat(GenericTypes.resolveType(t, B.class)).isEqualTo(t); }
@Test public void resolveType() throws NoSuchMethodException { abstract class A<T> { abstract T a(); } abstract class B extends A<String> {} assertThat(GenericTypes.resolveType(A.class.getDeclaredMethod("a").getGenericReturnType(), B.class)) .isEqualTo(String.class); }
@Override protected ImmutablesPojoProperty<T> createProperty(String name, Method m) { final Class<?> builderClass = builder.get().getClass(); try { final Type propertyType = GenericTypes.resolveType(m.getGenericReturnType(), getType()); return new ImmutablesPojoProperty<T>( name, QualifiedType.of(propertyType).with(Qualifiers.getQualifiers(m)), m, alwaysSet(), MethodHandles.lookup().unreflect(m), findBuilderSetter(builderClass, name, propertyType)); } catch (IllegalAccessException | NoSuchMethodException e) { throw new IllegalArgumentException("Failed to inspect method " + m, e); } }
Type returnType = GenericTypes.resolveType(method.getGenericReturnType(), extensionType); QualifiedType<?> qualifiedReturnType = QualifiedType.of(returnType).with(getQualifiers(method)); Class<?> returnClass = getErasedType(returnType);
@Override protected ImmutablesPojoProperty<T> createProperty(String name, Method m) { final Type propertyType = GenericTypes.resolveType(m.getGenericReturnType(), getType()); try { return new ImmutablesPojoProperty<T>( name, QualifiedType.of(propertyType).with(Qualifiers.getQualifiers(m)), m, isSetMethod(name), MethodHandles.lookup().unreflect(m), MethodHandles.lookup().findVirtual(impl, setterName(name), MethodType.methodType(impl, GenericTypes.getErasedType(propertyType)))); } catch (IllegalAccessException | NoSuchMethodException e) { throw new IllegalArgumentException("Failed to inspect method " + m, e); } }
public SqlUpdateHandler(Class<?> sqlObjectType, Method method) { super(sqlObjectType, method); if (method.isAnnotationPresent(UseRowReducer.class)) { throw new UnsupportedOperationException("Cannot declare @UseRowReducer on a @SqlUpdate method."); } boolean isGetGeneratedKeys = method.isAnnotationPresent(GetGeneratedKeys.class); QualifiedType<?> returnType = QualifiedType.of( GenericTypes.resolveType(method.getGenericReturnType(), sqlObjectType)) .with(getQualifiers(method)); if (isGetGeneratedKeys) { ResultReturner magic = ResultReturner.forMethod(sqlObjectType, method); String[] columnNames = method.getAnnotation(GetGeneratedKeys.class).value(); this.returner = update -> { ResultBearing resultBearing = update.executeAndReturnGeneratedKeys(columnNames); UseRowMapper useRowMapper = method.getAnnotation(UseRowMapper.class); ResultIterable<?> iterable = useRowMapper == null ? resultBearing.mapTo(returnType) : resultBearing.map(rowMapperFor(useRowMapper)); return magic.mappedResult(iterable, update.getContext()); }; } else if (isNumeric(method.getReturnType())) { this.returner = update -> update.execute(); } else if (isBoolean(method.getReturnType())) { this.returner = update -> update.execute() > 0; } else { throw new UnableToCreateSqlObjectException(invalidReturnTypeMessage(method, returnType)); } }
Class<? extends Tuple> tupleClass = (Class<? extends Tuple>) erasedType; Array<Tuple2<Type, Integer>> tupleTypes = Array.of(tupleClass.getTypeParameters()) .map(tp -> resolveType(tp, type)) .zipWithIndex((t, i) -> Tuple.of(t, i + 1));
/** * Given a subtype of {@code Map<K,V>}, returns the corresponding map entry type {@code Map.Entry<K,V>}. * @param mapType the map subtype * @return the map entry type */ public static Type resolveMapEntryType(Type mapType) { Type keyType = resolveType(KEY, mapType); Type valueType = resolveType(VALUE, mapType); return resolveMapEntryType(keyType, valueType); }
/** * For the given type which extends parameterizedSupertype, returns the * first generic parameter for parameterized supertype, if concretely * expressed. * * <p> * Example: * </p> * <ul> * <li>if <code>type</code> is <code>ArrayList<String></code> and * <code>parameterizedSuperType</code> is <code>List.class</code>, returns * <code>Optional.of(String.class)</code>.</li> * <li>if <code>type</code> is <code>ArrayList.class</code> (raw) and * <code>parameterizedSuperType</code> is <code>List.class</code>, returns * <code>Optional.empty()</code>.</li> * </ul> * * @param type * the subtype of parameterizedSupertype * @param parameterizedSupertype * the parameterized supertype from which we want the generic * parameter * @return the parameter on the supertype, if it is concretely defined. */ public static Optional<Type> findGenericParameter(Type type, Class<?> parameterizedSupertype) { Type parameterType = resolveType(parameterizedSupertype.getTypeParameters()[0], type); return parameterType instanceof Class || parameterType instanceof ParameterizedType ? Optional.of(parameterType) : Optional.empty(); }
@Override public java.util.Optional<Type> elementType(Type containerType) { Class<?> erasedType = getErasedType(containerType); if (Multimap.class.isAssignableFrom(erasedType)) { Type keyType = resolveType(multimapKey, containerType); Type valueType = resolveType(multimapValue, containerType); return java.util.Optional.of(resolveMapEntryType(keyType, valueType)); } else if (Map.class.isAssignableFrom(erasedType)) { return java.util.Optional.of(resolveMapEntryType(containerType)); } return findGenericParameter(containerType, erasedType); }
@SuppressWarnings("unchecked") static RowMapperFactory factory() { return (type, config) -> { if (type instanceof ParameterizedType && getErasedType(type).equals(Map.Entry.class)) { Type keyType = resolveType(KEY_PARAM, type); Type valueType = resolveType(VALUE_PARAM, type); RowMapper<?> keyMapper = getKeyMapper(keyType, config); RowMapper<?> valueMapper = getValueMapper(valueType, config); return Optional.of(new MapEntryMapper(keyMapper, valueMapper)); } return Optional.empty(); }; }