diff --git a/src/main/java/org/mapstruct/intellij/util/MapstructAnnotationUtils.java b/src/main/java/org/mapstruct/intellij/util/MapstructAnnotationUtils.java index 3dbec884..5c79438e 100644 --- a/src/main/java/org/mapstruct/intellij/util/MapstructAnnotationUtils.java +++ b/src/main/java/org/mapstruct/intellij/util/MapstructAnnotationUtils.java @@ -5,6 +5,7 @@ */ package org.mapstruct.intellij.util; +import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.HashSet; @@ -297,9 +298,12 @@ public static Stream findAllDefinedMappingAnnotations(@NotNull Ps private static Stream findAllDefinedMappingAnnotations(@NotNull PsiModifierListOwner owner, boolean includeMetaAnnotations) { //TODO cache + Stream mappingAnnotations = findMappingAnnotations( owner, includeMetaAnnotations ); + if ( includeMetaAnnotations ) { + return mappingAnnotations; + } PsiAnnotation mappings = findAnnotation( owner, true, MapstructUtil.MAPPINGS_ANNOTATION_FQN ); Stream mappingsAnnotations = extractMappingAnnotationsFromMappings( mappings ); - Stream mappingAnnotations = findMappingAnnotations( owner, includeMetaAnnotations ); return Stream.concat( mappingAnnotations, mappingsAnnotations ); } @@ -330,10 +334,10 @@ private static Stream findMappingAnnotations(@NotNull PsiModifier } @NotNull - private static Set findDirectAndMetaAnnotations(@NotNull PsiModifierListOwner owner, + private static List findDirectAndMetaAnnotations(@NotNull PsiModifierListOwner owner, Set visited) { - Set result = new HashSet<>(); + List result = new ArrayList<>(); // to avoid infinite loops, do not include meta annotations at this point findAllDefinedMappingAnnotations( owner, false ).forEach( result::add ); diff --git a/src/test/java/org/mapstruct/intellij/inspection/TargetPropertyMappedMoreThanOnceInspectionTest.java b/src/test/java/org/mapstruct/intellij/inspection/TargetPropertyMappedMoreThanOnceInspectionTest.java index 47aa2d3f..12e05564 100644 --- a/src/test/java/org/mapstruct/intellij/inspection/TargetPropertyMappedMoreThanOnceInspectionTest.java +++ b/src/test/java/org/mapstruct/intellij/inspection/TargetPropertyMappedMoreThanOnceInspectionTest.java @@ -65,4 +65,8 @@ public void testTargetPropertyMappedMoreThanOnce() { Caret currentCaret = myFixture.getEditor().getCaretModel().getCurrentCaret(); assertThat( currentCaret.getSelectedText( ) ).isEqualTo( "testName" ); } + + public void testTargetPropertyNotMappedMoreThanOnceFromAnnotation() { + doTest(); + } } diff --git a/testData/inspection/TargetPropertyNotMappedMoreThanOnceFromAnnotation.java b/testData/inspection/TargetPropertyNotMappedMoreThanOnceFromAnnotation.java new file mode 100644 index 00000000..cf894720 --- /dev/null +++ b/testData/inspection/TargetPropertyNotMappedMoreThanOnceFromAnnotation.java @@ -0,0 +1,63 @@ +/* + * Copyright MapStruct Authors. + * + * Licensed under the Apache License version 2.0, available at https://www.apache.org/licenses/LICENSE-2.0 + */ +import org.mapstruct.Mapper; +import org.mapstruct.Mapping; +import org.mapstruct.Mappings; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + + +class TargetClass { + private String name; + private String value; + + public String getName() { + return name; + } + + public void setName(String name) { + this.name = name; + } + + public String getValue() { + return value; + } + + public void setValue(String value) { + this.value = value; + } +} + +class SourceClass { + private String sourceName; + + public String getSourceName() { + return sourceName; + } + + public void setSourceName(String sourceName) { + this.sourceName = sourceName; + } +} + +@Retention(RetentionPolicy.RUNTIME) +@Target( ElementType.METHOD ) +@Mappings({ + @Mapping(target = "name", source = "sourceName"), + @Mapping(target = "value", ignore = true) +}) +@interface MyMappingAnnotation { +} + +@Mapper +interface MyMappingAnnotationMapper { + + @MyMappingAnnotation + TargetClass map(SourceClass source); +} \ No newline at end of file