Skip to content

Commit d39eba5

Browse files
committed
fix tests and add annotation check by simple name string
1 parent 298869e commit d39eba5

3 files changed

Lines changed: 82 additions & 31 deletions

File tree

pom.xml

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
<?xml version="1.0" encoding="UTF-8"?>
2-
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
2+
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
3+
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
34
<modelVersion>4.0.0</modelVersion>
45

56
<parent>
@@ -26,7 +27,7 @@
2627
<dependency>
2728
<groupId>it.aboutbits</groupId>
2829
<artifactId>archunit-toolbox</artifactId>
29-
<version>1.0.0-RC1</version>
30+
<version>1.1.0</version>
3031
</dependency>
3132
</dependencies>
3233
</dependencyManagement>

src/main/java/it/aboutbits/springboot/toolbox/swagger/customization/default_not_null/NullableCustomizer.java

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -130,12 +130,13 @@ private static boolean isNullable(
130130
AnnotatedType annotatedType,
131131
Annotation[] annotations
132132
) {
133-
if (annotatedType.isAnnotationPresent(org.jspecify.annotations.Nullable.class)) {
134-
return true;
133+
for (var annotation : annotatedType.getAnnotations()) {
134+
if (annotation.annotationType().getSimpleName().equals("Nullable")) {
135+
return true;
136+
}
135137
}
136138
for (var annotation : annotations) {
137-
var name = annotation.annotationType().getName();
138-
if (name.equals("org.springframework.lang.Nullable") || name.equals("jakarta.annotation.Nullable")) {
139+
if (annotation.annotationType().getSimpleName().equals("Nullable")) {
139140
return true;
140141
}
141142
}

src/test/java/it/aboutbits/springboot/toolbox/swagger/customization/default_not_null/NullableCustomizerTest.java

Lines changed: 74 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -8,10 +8,10 @@
88
import org.jspecify.annotations.Nullable;
99
import org.junit.jupiter.api.Test;
1010

11-
import java.util.List;
11+
import java.lang.annotation.Retention;
12+
import java.lang.annotation.RetentionPolicy;
1213

13-
import static org.junit.jupiter.api.Assertions.assertDoesNotThrow;
14-
import static org.junit.jupiter.api.Assertions.assertTrue;
14+
import static org.assertj.core.api.Assertions.assertThat;
1515

1616
@NullUnmarked
1717
class NullableCustomizerTest {
@@ -53,6 +53,7 @@ public String directMethod() {
5353

5454
@Test
5555
void shouldFindFieldInSuperClass() {
56+
// given
5657
var customizer = new NullableCustomizer();
5758
var openApi = new OpenAPI();
5859
var components = new Components();
@@ -65,15 +66,19 @@ void shouldFindFieldInSuperClass() {
6566
components.addSchemas(SubClass.class.getName(), subClassSchema);
6667
openApi.setComponents(components);
6768

68-
assertDoesNotThrow(() -> customizer.customise(openApi));
69+
// when
70+
customizer.customise(openApi);
6971

70-
List<String> required = subClassSchema.getRequired();
71-
assertTrue(required != null && required.contains("subField"), "subField should be required");
72-
assertTrue(required == null || !required.contains("baseField"), "baseField should NOT be required");
72+
// then
73+
var required = subClassSchema.getRequired();
74+
75+
assertThat(required).as("subField should be required").contains("subField");
76+
assertThat(required).as("baseField should NOT be required").doesNotContain("baseField");
7377
}
7478

7579
@Test
7680
void shouldFindAnnotationOnGetter() {
81+
// given
7782
var customizer = new NullableCustomizer();
7883
var openApi = new OpenAPI();
7984
var components = new Components();
@@ -85,14 +90,17 @@ void shouldFindAnnotationOnGetter() {
8590
components.addSchemas(MethodAnnotated.class.getName(), schema);
8691
openApi.setComponents(components);
8792

88-
assertDoesNotThrow(() -> customizer.customise(openApi));
93+
// when
94+
customizer.customise(openApi);
8995

90-
List<String> required = schema.getRequired();
91-
assertTrue(required == null || !required.contains("annotatedGetter"), "annotatedGetter should NOT be required");
96+
// then
97+
var required = schema.getRequired();
98+
assertThat(required).as("annotatedGetter should NOT be required").isNullOrEmpty();
9299
}
93100

94101
@Test
95102
void shouldFindAnnotationOnDirectMethod() {
103+
// given
96104
var customizer = new NullableCustomizer();
97105
var openApi = new OpenAPI();
98106
var components = new Components();
@@ -104,14 +112,17 @@ void shouldFindAnnotationOnDirectMethod() {
104112
components.addSchemas(DirectMethodAnnotated.class.getName(), schema);
105113
openApi.setComponents(components);
106114

107-
assertDoesNotThrow(() -> customizer.customise(openApi));
115+
// when
116+
customizer.customise(openApi);
108117

109-
List<String> required = schema.getRequired();
110-
assertTrue(required == null || !required.contains("directMethod"), "directMethod should NOT be required");
118+
// then
119+
var required = schema.getRequired();
120+
assertThat(required).as("directMethod should NOT be required").isNullOrEmpty();
111121
}
112122

113123
@Test
114124
void shouldHandleConcatenatedFqns() {
125+
// given
115126
var customizer = new NullableCustomizer();
116127
var openApi = new OpenAPI();
117128
var components = new Components();
@@ -125,17 +136,17 @@ void shouldHandleConcatenatedFqns() {
125136
components.addSchemas(concatenatedFqn, schema);
126137
openApi.setComponents(components);
127138

128-
assertDoesNotThrow(() -> customizer.customise(openApi));
139+
// when
140+
customizer.customise(openApi);
129141

130-
List<String> required = schema.getRequired();
131-
assertTrue(
132-
required == null || !required.contains("baseField"),
133-
"baseField should NOT be required even with concatenated FQN"
134-
);
142+
// then
143+
var required = schema.getRequired();
144+
assertThat(required).as("baseField should NOT be required even with concatenated FQN").isNullOrEmpty();
135145
}
136146

137147
@Test
138148
void shouldNotThrowWhenFieldNotFound() {
149+
// given
139150
var customizer = new NullableCustomizer();
140151
var openApi = new OpenAPI();
141152
var components = new Components();
@@ -147,12 +158,50 @@ void shouldNotThrowWhenFieldNotFound() {
147158
components.addSchemas(SubClass.class.getName(), schema);
148159
openApi.setComponents(components);
149160

150-
assertDoesNotThrow(() -> customizer.customise(openApi));
161+
// when
162+
customizer.customise(openApi);
163+
164+
// then
165+
var required = schema.getRequired();
166+
assertThat(required).as("nonExistent field should be considered required if not found and not nullable")
167+
.contains("nonExistent");
168+
}
169+
170+
@Test
171+
void shouldFindCustomNullableAnnotation() {
172+
// given
173+
var customizer = new NullableCustomizer();
174+
var openApi = new OpenAPI();
175+
var components = new Components();
176+
177+
var schema = new Schema<Object>();
178+
schema.setName(CustomNullableClass.class.getName());
179+
schema.addProperty("customNullableField", new StringSchema());
180+
181+
components.addSchemas(CustomNullableClass.class.getName(), schema);
182+
openApi.setComponents(components);
183+
184+
// when
185+
customizer.customise(openApi);
186+
187+
// then
188+
var required = schema.getRequired();
189+
assertThat(required).as("customNullableField should NOT be required").isNullOrEmpty();
190+
}
191+
192+
public static class Nest {
193+
@Retention(RetentionPolicy.RUNTIME)
194+
public @interface Nullable {
195+
}
196+
}
151197

152-
List<String> required = schema.getRequired();
153-
assertTrue(
154-
required != null && required.contains("nonExistent"),
155-
"nonExistent field should be considered required if not found and not nullable"
156-
);
198+
public static class CustomNullableClass {
199+
@Nest.Nullable
200+
private String customNullableField;
201+
202+
@SuppressWarnings("NullAway")
203+
public String getCustomNullableField() {
204+
return customNullableField;
205+
}
157206
}
158207
}

0 commit comments

Comments
 (0)