xref: /aosp_15_r20/external/dagger2/javatests/dagger/internal/codegen/XAnnotationsToStableStringTest.java (revision f585d8a307d0621d6060bd7e80091fdcbf94fe27)
1 /*
2  * Copyright (C) 2022 The Dagger Authors.
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  * http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package dagger.internal.codegen;
18 
19 import static com.google.common.truth.Truth.assertThat;
20 
21 import androidx.room.compiler.processing.XAnnotation;
22 import androidx.room.compiler.processing.XProcessingEnv;
23 import androidx.room.compiler.processing.XTypeElement;
24 import com.google.testing.compile.CompilationRule;
25 import com.squareup.javapoet.ClassName;
26 import dagger.Component;
27 import dagger.internal.codegen.javac.JavacPluginModule;
28 import dagger.internal.codegen.xprocessing.XAnnotations;
29 import javax.inject.Inject;
30 import javax.inject.Singleton;
31 import javax.lang.model.util.Elements;
32 import javax.lang.model.util.Types;
33 import org.junit.Before;
34 import org.junit.Rule;
35 import org.junit.Test;
36 import org.junit.runner.RunWith;
37 import org.junit.runners.JUnit4;
38 
39 @RunWith(JUnit4.class)
40 public class XAnnotationsToStableStringTest {
41   static final class Foo {}
42 
43   enum MyEnum {
44     V1,
45     V2
46   }
47 
48   @interface SingleValueWithCustomNameAnnotation {
classValue()49     Class<?> classValue();
50   }
51 
52   @interface SingleValueWithDefaultAnnotation {
value()53     Class<?> value() default Object.class;
54   }
55 
56   @interface SingleValueAnnotation {
value()57     Class<?> value();
58   }
59 
60   @interface MultiValueAnnotation {
enumValue()61     MyEnum enumValue();
62 
classValue()63     Class<?> classValue();
64 
booleanValue()65     boolean booleanValue();
66 
byteValue()67     byte byteValue();
68 
charValue()69     char charValue();
70 
intValue()71     int intValue();
72 
longValue()73     long longValue();
74 
shortValue()75     short shortValue();
76 
floatValue()77     float floatValue();
78 
doubleValue()79     double doubleValue();
80 
stringValue()81     String stringValue();
82 
stringWithDefaultValue()83     String stringWithDefaultValue() default "Default value";
84 
stringWithMultipleArrayValue()85     String[] stringWithMultipleArrayValue();
86 
stringWithSingleArrayValue()87     String[] stringWithSingleArrayValue();
88 
singleValueAnnotations()89     SingleValueAnnotation[] singleValueAnnotations();
90   }
91 
92   @SingleValueAnnotation(value = Foo.class)
93   @SingleValueWithDefaultAnnotation
94   @SingleValueWithCustomNameAnnotation(classValue = Foo.class)
95   @MultiValueAnnotation(
96       // Note: the value orders are purposely randomized for this test
97       doubleValue = 13.2,
98       longValue = 7L,
99       stringWithSingleArrayValue = {"STRING_VALUE1"},
100       byteValue = 3,
101       enumValue = MyEnum.V1,
102       charValue = 'c',
103       stringWithMultipleArrayValue = {"STRING_VALUE1", "STRING_VALUE2"},
104       shortValue = 9,
105       classValue = Foo.class,
106       stringValue = "STRING_VALUE1",
107       booleanValue = false,
108       floatValue = 11.1f,
109       singleValueAnnotations = {
110         @SingleValueAnnotation(Object.class),
111         @SingleValueAnnotation(Foo.class),
112         @SingleValueAnnotation(String.class)
113       },
114       intValue = 5)
115   interface Usage {}
116 
117   @Rule public CompilationRule compilationRule = new CompilationRule();
118 
119   @Inject XProcessingEnv processingEnv;
120 
121   private final String testName = getClass().getCanonicalName();
122 
123   @Before
setUp()124   public void setUp() {
125     TestComponent.create(compilationRule.getElements(), compilationRule.getTypes()).inject(this);
126   }
127 
128   @Test
multiValueAnnotationTest()129   public void multiValueAnnotationTest() {
130     XTypeElement typeElement = processingEnv.requireTypeElement(Usage.class.getCanonicalName());
131     XAnnotation annotation = typeElement.getAnnotation(ClassName.get(MultiValueAnnotation.class));
132     assertThat(XAnnotations.toStableString(annotation))
133         .isEqualTo(
134             String.format(
135                 "@%1$s.MultiValueAnnotation("
136                     + "enumValue=V1, "
137                     + "classValue=%1$s.Foo, "
138                     + "booleanValue=false, "
139                     + "byteValue=3, "
140                     + "charValue='c', "
141                     + "intValue=5, "
142                     + "longValue=7, "
143                     + "shortValue=9, "
144                     + "floatValue=11.1, "
145                     + "doubleValue=13.2, "
146                     + "stringValue=\"STRING_VALUE1\", "
147                     + "stringWithDefaultValue=\"Default value\", "
148                     + "stringWithMultipleArrayValue={\"STRING_VALUE1\", \"STRING_VALUE2\"}, "
149                     + "stringWithSingleArrayValue={\"STRING_VALUE1\"}, "
150                     + "singleValueAnnotations={"
151                     + "@%1$s.SingleValueAnnotation(java.lang.Object), "
152                     + "@%1$s.SingleValueAnnotation(%1$s.Foo), "
153                     + "@%1$s.SingleValueAnnotation(java.lang.String)"
154                     + "})",
155                 testName));
156   }
157 
158   @Test
singleValueAnnotationTest()159   public void singleValueAnnotationTest() {
160     XTypeElement typeElement = processingEnv.requireTypeElement(Usage.class.getCanonicalName());
161     XAnnotation annotation = typeElement.getAnnotation(ClassName.get(SingleValueAnnotation.class));
162     assertThat(XAnnotations.toStableString(annotation))
163         .isEqualTo(String.format("@%1$s.SingleValueAnnotation(%1$s.Foo)", testName));
164   }
165 
166   @Test
singleValueWithDefaultAnnotationTest()167   public void singleValueWithDefaultAnnotationTest() {
168     XTypeElement typeElement = processingEnv.requireTypeElement(Usage.class.getCanonicalName());
169     XAnnotation annotation =
170         typeElement.getAnnotation(ClassName.get(SingleValueWithDefaultAnnotation.class));
171     assertThat(XAnnotations.toStableString(annotation))
172         .isEqualTo(
173             String.format("@%1$s.SingleValueWithDefaultAnnotation(java.lang.Object)", testName));
174   }
175 
176   @Test
singleValueWithCustomNameAnnotationTest()177   public void singleValueWithCustomNameAnnotationTest() {
178     XTypeElement typeElement = processingEnv.requireTypeElement(Usage.class.getCanonicalName());
179     XAnnotation annotation =
180         typeElement.getAnnotation(ClassName.get(SingleValueWithCustomNameAnnotation.class));
181     assertThat(XAnnotations.toStableString(annotation))
182         .isEqualTo(
183             String.format(
184                 "@%1$s.SingleValueWithCustomNameAnnotation(classValue=%1$s.Foo)", testName));
185   }
186 
187   @Singleton
188   @Component(modules = JavacPluginModule.class)
189   interface TestComponent {
create(Elements elements, Types types)190     static TestComponent create(Elements elements, Types types) {
191       return DaggerXAnnotationsToStableStringTest_TestComponent.builder()
192           .javacPluginModule(new JavacPluginModule(elements, types))
193           .build();
194     }
195 
inject(XAnnotationsToStableStringTest test)196     void inject(XAnnotationsToStableStringTest test);
197   }
198 }
199