@Override public AnnotationAppender onParameterizedType(TypeDescription.Generic parameterizedType) { StringBuilder typePath = new StringBuilder(this.typePath); for (int index = 0; index < parameterizedType.asErasure().getSegmentCount(); index++) { typePath = typePath.append(INNER_CLASS_PATH); } AnnotationAppender annotationAppender = apply(parameterizedType, typePath.toString()); TypeDescription.Generic ownerType = parameterizedType.getOwnerType(); if (ownerType != null) { annotationAppender = ownerType.accept( new ForTypeAnnotations( annotationAppender, annotationValueFilter, typeReference, this.typePath)); } int index = 0; for (TypeDescription.Generic typeArgument : parameterizedType.getTypeArguments()) { annotationAppender = typeArgument.accept( new ForTypeAnnotations( annotationAppender, annotationValueFilter, typeReference, typePath.toString() + index++ + INDEXED_TYPE_DELIMITER)); } return annotationAppender; }
@Override @Before @SuppressWarnings("unchecked") public void setUp() throws Exception { super.setUp(); when(firstSourceType.getStackSize()).thenReturn(StackSize.SINGLE); when(secondSourceType.getStackSize()).thenReturn(StackSize.SINGLE); when(componentType.asErasure()).thenReturn(rawComponentType); when(targetType.getComponentType()).thenReturn(componentType); when(targetType.asErasure()).thenReturn(rawTargetType); when(firstSourceType.asGenericType()).thenReturn(firstSourceType); when(firstSourceType.accept(any(TypeDescription.Generic.Visitor.class))) .thenReturn(firstSourceType); when(secondSourceType.asGenericType()).thenReturn(secondSourceType); when(secondSourceType.accept(any(TypeDescription.Generic.Visitor.class))) .thenReturn(secondSourceType); }
@Override public void apply( MethodVisitor methodVisitor, MethodDescription methodDescription, AnnotationValueFilter annotationValueFilter) { AnnotationAppender annotationAppender = new AnnotationAppender.Default(new AnnotationAppender.Target.OnMethod(methodVisitor)); annotationAppender = methodDescription .getReturnType() .accept( AnnotationAppender.ForTypeAnnotations.ofMethodReturnType( annotationAppender, annotationValueFilter)); annotationAppender = AnnotationAppender.ForTypeAnnotations.ofTypeVariable( annotationAppender, annotationValueFilter, AnnotationAppender.ForTypeAnnotations.VARIABLE_ON_INVOKEABLE, methodDescription.getTypeVariables()); for (AnnotationDescription annotation : methodDescription.getDeclaredAnnotations()) { annotationAppender = annotationAppender.append(annotation, annotationValueFilter); } for (ParameterDescription parameterDescription : methodDescription.getParameters()) { AnnotationAppender parameterAppender = new AnnotationAppender.Default( new AnnotationAppender.Target.OnMethodParameter( methodVisitor, parameterDescription.getIndex())); parameterAppender = parameterDescription .getType() .accept( AnnotationAppender.ForTypeAnnotations.ofMethodParameterType( parameterAppender, annotationValueFilter, parameterDescription.getIndex())); for (AnnotationDescription annotation : parameterDescription.getDeclaredAnnotations()) { parameterAppender = parameterAppender.append(annotation, annotationValueFilter); } } int exceptionTypeIndex = 0; for (TypeDescription.Generic exceptionType : methodDescription.getExceptionTypes()) { annotationAppender = exceptionType.accept( AnnotationAppender.ForTypeAnnotations.ofExceptionType( annotationAppender, annotationValueFilter, exceptionTypeIndex++)); } }
/** * Appends all supplied type variables to the supplied method appender. * * @param annotationAppender The annotation appender to write any type annotation to. * @param annotationValueFilter The annotation value filter to apply. * @param variableOnType {@code true} if the type variables are declared by a type, {@code * false} if they are declared by a method. * @param subListIndex The index of the first type variable to append. All previous type * variables are ignored. * @param typeVariables The type variables to append. * @return The resulting annotation appender. */ public static AnnotationAppender ofTypeVariable( AnnotationAppender annotationAppender, AnnotationValueFilter annotationValueFilter, boolean variableOnType, int subListIndex, List<? extends TypeDescription.Generic> typeVariables) { int typeVariableIndex = subListIndex, variableBaseReference, variableBoundBaseBase; if (variableOnType) { variableBaseReference = TypeReference.CLASS_TYPE_PARAMETER; variableBoundBaseBase = TypeReference.CLASS_TYPE_PARAMETER_BOUND; } else { variableBaseReference = TypeReference.METHOD_TYPE_PARAMETER; variableBoundBaseBase = TypeReference.METHOD_TYPE_PARAMETER_BOUND; } for (TypeDescription.Generic typeVariable : typeVariables.subList(subListIndex, typeVariables.size())) { int typeReference = TypeReference.newTypeParameterReference(variableBaseReference, typeVariableIndex) .getValue(); for (AnnotationDescription annotationDescription : typeVariable.getDeclaredAnnotations()) { annotationAppender = annotationAppender.append( annotationDescription, annotationValueFilter, typeReference, EMPTY_TYPE_PATH); } int boundIndex = !typeVariable.getUpperBounds().get(0).getSort().isTypeVariable() && typeVariable.getUpperBounds().get(0).asErasure().isInterface() ? 1 : 0; for (TypeDescription.Generic typeBound : typeVariable.getUpperBounds()) { annotationAppender = typeBound.accept( new ForTypeAnnotations( annotationAppender, annotationValueFilter, TypeReference.newTypeParameterBoundReference( variableBoundBaseBase, typeVariableIndex, boundIndex++))); } typeVariableIndex++; } return annotationAppender; }