Search in sources :

Example 16 with Type

use of org.mapstruct.ap.internal.model.common.Type in project mapstruct by mapstruct.

the class BuiltInMethod method matches.

/**
 * {@inheritDoc}
 * <p>
 * Default the targetType should be assignable to the returnType and the sourceType to the parameter,
 * excluding generic type variables. When the implementor sees a need for this, this method can be overridden.
 */
@Override
public boolean matches(List<Type> sourceTypes, Type targetType) {
    if (sourceTypes.size() != 1) {
        return false;
    }
    Type sourceType = first(sourceTypes);
    Type returnType = getReturnType().resolveParameterToType(sourceType, getParameter().getType()).getMatch();
    if (returnType == null) {
        return false;
    }
    return returnType.isAssignableTo(targetType) && sourceType.erasure().isAssignableTo(getParameter().getType());
}
Also used : Type(org.mapstruct.ap.internal.model.common.Type)

Example 17 with Type

use of org.mapstruct.ap.internal.model.common.Type in project mapstruct by mapstruct.

the class SetterWrapper method getThrownTypes.

@Override
public List<Type> getThrownTypes() {
    List<Type> parentThrownTypes = super.getThrownTypes();
    List<Type> result = new ArrayList<>(parentThrownTypes);
    for (Type thrownTypeToExclude : thrownTypesToExclude) {
        for (Type parentThrownType : parentThrownTypes) {
            if (parentThrownType.isAssignableTo(thrownTypeToExclude)) {
                result.remove(parentThrownType);
            }
        }
    }
    return result;
}
Also used : Type(org.mapstruct.ap.internal.model.common.Type) ArrayList(java.util.ArrayList)

Example 18 with Type

use of org.mapstruct.ap.internal.model.common.Type in project mapstruct by mapstruct.

the class MethodMatcher method matchResultType.

private boolean matchResultType(Type resultType, Map<TypeVariable, TypeMirror> genericTypesMap) {
    Type candidateResultType = candidateMethod.getResultType();
    if (!isJavaLangObject(candidateResultType.getTypeMirror()) && !candidateResultType.isVoid()) {
        final Assignability visitedAssignability;
        if (candidateMethod.getReturnType().isVoid()) {
            // for void-methods, the result-type of the candidate needs to be assignable from the given result type
            visitedAssignability = Assignability.VISITED_ASSIGNABLE_FROM;
        } else {
            // for non-void methods, the result-type of the candidate needs to be assignable to the given result
            // type
            visitedAssignability = Assignability.VISITED_ASSIGNABLE_TO;
        }
        TypeMatcher returnTypeMatcher = new TypeMatcher(visitedAssignability, genericTypesMap);
        if (!returnTypeMatcher.visit(candidateResultType.getTypeMirror(), resultType.getTypeMirror())) {
            if (resultType.isPrimitive()) {
                TypeMirror boxedType = typeUtils.boxedClass((PrimitiveType) resultType.getTypeMirror()).asType();
                TypeMatcher boxedReturnTypeMatcher = new TypeMatcher(visitedAssignability, genericTypesMap);
                if (!boxedReturnTypeMatcher.visit(candidateResultType.getTypeMirror(), boxedType)) {
                    return false;
                }
            } else if (candidateResultType.getTypeMirror().getKind().isPrimitive()) {
                TypeMirror boxedCandidateReturnType = typeUtils.boxedClass((PrimitiveType) candidateResultType.getTypeMirror()).asType();
                TypeMatcher boxedReturnTypeMatcher = new TypeMatcher(visitedAssignability, genericTypesMap);
                if (!boxedReturnTypeMatcher.visit(boxedCandidateReturnType, resultType.getTypeMirror())) {
                    return false;
                }
            } else {
                return false;
            }
        }
    }
    return true;
}
Also used : ArrayType(javax.lang.model.type.ArrayType) Type(org.mapstruct.ap.internal.model.common.Type) DeclaredType(javax.lang.model.type.DeclaredType) PrimitiveType(javax.lang.model.type.PrimitiveType) WildcardType(javax.lang.model.type.WildcardType) TypeMirror(javax.lang.model.type.TypeMirror) PrimitiveType(javax.lang.model.type.PrimitiveType)

Example 19 with Type

use of org.mapstruct.ap.internal.model.common.Type in project mapstruct by mapstruct.

the class MethodRetrievalProcessor method checkParameterAndReturnType.

private boolean checkParameterAndReturnType(ExecutableElement method, List<Parameter> sourceParameters, Parameter targetParameter, List<Parameter> contextParameters, Type resultType, Type returnType, boolean containsTargetTypeParameter) {
    if (sourceParameters.isEmpty()) {
        messager.printMessage(method, Message.RETRIEVAL_NO_INPUT_ARGS);
        return false;
    }
    if (targetParameter != null && (sourceParameters.size() + contextParameters.size() + 1 != method.getParameters().size())) {
        messager.printMessage(method, Message.RETRIEVAL_DUPLICATE_MAPPING_TARGETS);
        return false;
    }
    if (isVoid(resultType)) {
        messager.printMessage(method, Message.RETRIEVAL_VOID_MAPPING_METHOD);
        return false;
    }
    if (returnType.getTypeMirror().getKind() != TypeKind.VOID && !resultType.isAssignableTo(returnType)) {
        messager.printMessage(method, Message.RETRIEVAL_NON_ASSIGNABLE_RESULTTYPE);
        return false;
    }
    for (Parameter sourceParameter : sourceParameters) {
        if (sourceParameter.getType().isTypeVar()) {
            messager.printMessage(method, Message.RETRIEVAL_TYPE_VAR_SOURCE);
            return false;
        }
    }
    Set<Type> contextParameterTypes = new HashSet<Type>();
    for (Parameter contextParameter : contextParameters) {
        if (!contextParameterTypes.add(contextParameter.getType())) {
            messager.printMessage(method, Message.RETRIEVAL_CONTEXT_PARAMS_WITH_SAME_TYPE);
            return false;
        }
    }
    if (returnType.isTypeVar() || resultType.isTypeVar()) {
        messager.printMessage(method, Message.RETRIEVAL_TYPE_VAR_RESULT);
        return false;
    }
    Type parameterType = sourceParameters.get(0).getType();
    if (parameterType.isIterableOrStreamType() && !resultType.isIterableOrStreamType()) {
        messager.printMessage(method, Message.RETRIEVAL_ITERABLE_TO_NON_ITERABLE);
        return false;
    }
    if (containsTargetTypeParameter) {
        messager.printMessage(method, Message.RETRIEVAL_MAPPING_HAS_TARGET_TYPE_PARAMETER);
        return false;
    }
    if (!parameterType.isIterableOrStreamType() && resultType.isIterableOrStreamType()) {
        messager.printMessage(method, Message.RETRIEVAL_NON_ITERABLE_TO_ITERABLE);
        return false;
    }
    if (parameterType.isPrimitive()) {
        messager.printMessage(method, Message.RETRIEVAL_PRIMITIVE_PARAMETER);
        return false;
    }
    if (resultType.isPrimitive()) {
        messager.printMessage(method, Message.RETRIEVAL_PRIMITIVE_RETURN);
        return false;
    }
    if (parameterType.isEnumType() && !resultType.isEnumType()) {
        messager.printMessage(method, Message.RETRIEVAL_ENUM_TO_NON_ENUM);
        return false;
    }
    if (!parameterType.isEnumType() && resultType.isEnumType()) {
        messager.printMessage(method, Message.RETRIEVAL_NON_ENUM_TO_ENUM);
        return false;
    }
    for (Type typeParameter : resultType.getTypeParameters()) {
        if (typeParameter.isTypeVar()) {
            messager.printMessage(method, Message.RETRIEVAL_TYPE_VAR_RESULT);
            return false;
        }
        if (typeParameter.isWildCardExtendsBound()) {
            messager.printMessage(method, Message.RETRIEVAL_WILDCARD_EXTENDS_BOUND_RESULT);
            return false;
        }
    }
    for (Type typeParameter : parameterType.getTypeParameters()) {
        if (typeParameter.isWildCardSuperBound()) {
            messager.printMessage(method, Message.RETRIEVAL_WILDCARD_SUPER_BOUND_SOURCE);
            return false;
        }
        if (typeParameter.isTypeVar()) {
            messager.printMessage(method, Message.RETRIEVAL_TYPE_VAR_SOURCE);
            return false;
        }
    }
    return true;
}
Also used : Type(org.mapstruct.ap.internal.model.common.Type) DeclaredType(javax.lang.model.type.DeclaredType) ExecutableType(javax.lang.model.type.ExecutableType) Parameter(org.mapstruct.ap.internal.model.common.Parameter) HashSet(java.util.HashSet)

Example 20 with Type

use of org.mapstruct.ap.internal.model.common.Type in project mapstruct by mapstruct.

the class MethodMatcher method matches.

/**
 * Whether the given source and target types are matched by this matcher's candidate method.
 *
 * @param sourceTypes the source types
 * @param resultType the target type
 * @return {@code true} when both, source type and target types match the signature of this matcher's method;
 *         {@code false} otherwise.
 */
boolean matches(List<Type> sourceTypes, Type resultType) {
    // check & collect generic types.
    Map<TypeVariable, TypeMirror> genericTypesMap = new HashMap<TypeVariable, TypeMirror>();
    if (candidateMethod.getParameters().size() == sourceTypes.size()) {
        int i = 0;
        for (Parameter candidateParam : candidateMethod.getParameters()) {
            Type sourceType = sourceTypes.get(i++);
            if (sourceType == null || !matchSourceType(sourceType, candidateParam.getType(), genericTypesMap)) {
                return false;
            }
        }
    } else {
        return false;
    }
    // check if the method matches the proper result type to construct
    Parameter targetTypeParameter = candidateMethod.getTargetTypeParameter();
    if (targetTypeParameter != null) {
        Type returnClassType = typeFactory.classTypeOf(resultType);
        if (!matchSourceType(returnClassType, targetTypeParameter.getType(), genericTypesMap)) {
            return false;
        }
    }
    // check result type
    if (!matchResultType(resultType, genericTypesMap)) {
        return false;
    }
    // check if all type parameters are indeed mapped
    if (candidateMethod.getExecutable().getTypeParameters().size() != genericTypesMap.size()) {
        return false;
    }
    // check if all entries are in the bounds
    for (Map.Entry<TypeVariable, TypeMirror> entry : genericTypesMap.entrySet()) {
        if (!isWithinBounds(entry.getValue(), getTypeParamFromCandidate(entry.getKey()))) {
            // checks if the found Type is in bounds of the TypeParameters bounds.
            return false;
        }
    }
    return true;
}
Also used : ArrayType(javax.lang.model.type.ArrayType) Type(org.mapstruct.ap.internal.model.common.Type) DeclaredType(javax.lang.model.type.DeclaredType) PrimitiveType(javax.lang.model.type.PrimitiveType) WildcardType(javax.lang.model.type.WildcardType) TypeVariable(javax.lang.model.type.TypeVariable) TypeMirror(javax.lang.model.type.TypeMirror) HashMap(java.util.HashMap) Parameter(org.mapstruct.ap.internal.model.common.Parameter) HashMap(java.util.HashMap) Map(java.util.Map)

Aggregations

Type (org.mapstruct.ap.internal.model.common.Type)36 ArrayList (java.util.ArrayList)13 Parameter (org.mapstruct.ap.internal.model.common.Parameter)11 DeclaredType (javax.lang.model.type.DeclaredType)10 ExecutableType (javax.lang.model.type.ExecutableType)6 SourceMethod (org.mapstruct.ap.internal.model.source.SourceMethod)6 HashSet (java.util.HashSet)5 TypeMirror (javax.lang.model.type.TypeMirror)4 TreeSet (java.util.TreeSet)3 BeanMappingMethod (org.mapstruct.ap.internal.model.BeanMappingMethod)3 ContainerMappingMethod (org.mapstruct.ap.internal.model.ContainerMappingMethod)3 IterableMappingMethod (org.mapstruct.ap.internal.model.IterableMappingMethod)3 MapMappingMethod (org.mapstruct.ap.internal.model.MapMappingMethod)3 MappingMethod (org.mapstruct.ap.internal.model.MappingMethod)3 StreamMappingMethod (org.mapstruct.ap.internal.model.StreamMappingMethod)3 ValueMappingMethod (org.mapstruct.ap.internal.model.ValueMappingMethod)3 Map (java.util.Map)2 ExecutableElement (javax.lang.model.element.ExecutableElement)2 TypeElement (javax.lang.model.element.TypeElement)2 ArrayType (javax.lang.model.type.ArrayType)2