Skip to content

Commit 5a64dc1

Browse files
committed
Drop dead overloads and trim verbose comments
The single-arg analyzeTypeAndSubtypes, the no-polymorphic-set ParserWriter constructor, and the 4-arg generateParserForFields each had exactly one caller in the previous commit; inline them so there is one entry point per operation. Also strip narration-style comments and accessor noise from fixtures that the analyzer never touches.
1 parent e7e1d6f commit 5a64dc1

6 files changed

Lines changed: 24 additions & 111 deletions

File tree

gwt-beans-codegen-core/src/main/java/nl/aerius/codegen/analyzer/TypeAnalyzer.java

Lines changed: 10 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -106,7 +106,7 @@ public Set<ClassName> analyzeClass(final String className) {
106106
printedTypes.clear();
107107
polymorphicallyReachedTypes.clear();
108108

109-
analyzeTypeAndSubtypes(rootClass);
109+
analyzeTypeAndSubtypes(rootClass, true);
110110

111111
if (!skippedTypes.isEmpty()) {
112112
logger.info("Warning: The following types were not found and skipped:");
@@ -120,21 +120,15 @@ public Set<ClassName> analyzeClass(final String className) {
120120
}
121121

122122
/**
123-
* Returns the polymorphic base types that were reached directly (as a field
124-
* type or type argument) during the most recent analysis. Such types need a
125-
* polymorphic dispatch parser; polymorphic bases reached only via a concrete
126-
* subtype's superclass walk are absent from this set and should be emitted as
127-
* standard parsers (so the concrete subtype can still parse its inherited
128-
* fields without forcing sibling subtypes to be generated).
123+
* Polymorphic bases reached directly (as a field type or type argument) in
124+
* the most recent analysis. The generator emits a discriminator switch for
125+
* these; bases reached only via a concrete subtype's superclass chain are
126+
* absent and get a standard parse method instead.
129127
*/
130128
public Set<Class<?>> getPolymorphicallyReachedTypes() {
131129
return polymorphicallyReachedTypes;
132130
}
133131

134-
private void analyzeTypeAndSubtypes(final Class<?> type) {
135-
analyzeTypeAndSubtypes(type, true);
136-
}
137-
138132
private void analyzeTypeAndSubtypes(final Class<?> type, final boolean reachedDirectly) {
139133
if (!shouldAnalyzeType(type)) {
140134
return;
@@ -145,34 +139,28 @@ private void analyzeTypeAndSubtypes(final Class<?> type, final boolean reachedDi
145139
final boolean newPolymorphicReach = polymorphic && reachedDirectly && polymorphicallyReachedTypes.add(type);
146140

147141
if (!firstVisit && !newPolymorphicReach) {
148-
return; // Already processed and no new direct reach to expand on
142+
return;
149143
}
150144

151145
if (firstVisit) {
152-
// Print the class hierarchy if we haven't seen this type before
153146
if (!printedTypes.contains(type.getName())) {
154147
printClassHierarchy(type);
155148
printedTypes.add(type.getName());
156149
}
157150

158-
// If this type has a custom parser, skip adding it for generation
159-
// but continue analyzing its fields and subtypes
160151
if (!hasCustomParser(type)) {
161152
addTypeForGeneration(type);
162153
} else {
163154
logger.info("Skipping parser generation for " + type.getName() + " (has custom parser)");
164155
}
165156

166-
// Walk superclasses, but mark them as not-directly-reached so a polymorphic
167-
// base discovered only via a concrete subtype's superclass chain does not
168-
// expand into its sibling subtypes.
157+
// Superclasses are not "directly reached" - if the superclass is a
158+
// polymorphic base, sibling subtypes stay unwalked.
169159
final Class<?> superclass = type.getSuperclass();
170160
if (superclass != null && superclass != Object.class) {
171161
analyzeTypeAndSubtypes(superclass, false);
172162
}
173163

174-
// Always analyze fields, even for types with custom parsers
175-
// This ensures we discover all types that might need parsers
176164
for (final Field field : ConstructorAnalyzer.getParseableFields(type)) {
177165
try {
178166
analyzeField(field);
@@ -244,12 +232,12 @@ private void analyzeType(final Type type) {
244232
if (isUnsupportedType(classType)) {
245233
throw new UnsupportedTypeException(classType.getName(), "type parameter/element", Object.class);
246234
}
247-
analyzeTypeAndSubtypes(classType);
235+
analyzeTypeAndSubtypes(classType, true);
248236
} else if (type instanceof ParameterizedType) {
249237
final ParameterizedType paramType = (ParameterizedType) type;
250238
// Analyze the raw type
251239
if (paramType.getRawType() instanceof Class<?>) {
252-
analyzeTypeAndSubtypes((Class<?>) paramType.getRawType());
240+
analyzeTypeAndSubtypes((Class<?>) paramType.getRawType(), true);
253241
}
254242
// Analyze all type arguments recursively
255243
for (final Type typeArg : paramType.getActualTypeArguments()) {

gwt-beans-codegen-core/src/main/java/nl/aerius/codegen/generator/ParserWriter.java

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
package nl.aerius.codegen.generator;
22

33
import java.io.IOException;
4-
import java.util.Collections;
54
import java.util.Set;
65

76
import com.palantir.javapoet.ClassName;
@@ -23,11 +22,6 @@ public class ParserWriter {
2322
private final Logger logger;
2423
private final Set<Class<?>> polymorphicallyReachedTypes;
2524

26-
public ParserWriter(final String outputDir, final String parserPackage, final String generatorName,
27-
final String generatorDetails, final ClassFinder classFinder, final Logger logger) {
28-
this(outputDir, parserPackage, generatorName, generatorDetails, classFinder, logger, Collections.emptySet());
29-
}
30-
3125
public ParserWriter(final String outputDir, final String parserPackage, final String generatorName,
3226
final String generatorDetails, final ClassFinder classFinder, final Logger logger,
3327
final Set<Class<?>> polymorphicallyReachedTypes) {

gwt-beans-codegen-core/src/main/java/nl/aerius/codegen/generator/ParserWriterUtils.java

Lines changed: 6 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -119,24 +119,12 @@ public static void registerCustomParser(final String typeName, final String pack
119119
}
120120

121121
/**
122-
* Main entry point for generating a parser class.
123-
* Creates both parse(String) and parse(JSONObjectHandle) methods.
124-
* For constructor-based types (no setters), generates constructor-based parse method.
125-
* @param classFinder
126-
*/
127-
public static void generateParserForFields(final TypeSpec.Builder typeSpec, final Class<?> targetClass, final String parserPackage,
128-
final ClassFinder classFinder) {
129-
generateParserForFields(typeSpec, targetClass, parserPackage, classFinder,
130-
hasJsonTypeInfoWithNameDiscriminator(targetClass));
131-
}
132-
133-
/**
134-
* Main entry point for generating a parser class with explicit polymorphic
135-
* dispatch control. When {@code usePolymorphicDispatch} is false on a class
136-
* that has @JsonTypeInfo/@JsonSubTypes, a standard parse method is emitted
137-
* instead of the discriminator switch - used when the analyzer determined
138-
* the type is reachable only via a concrete subtype, so sibling subtype
139-
* parsers are not generated and a polymorphic switch would not compile.
122+
* Main entry point for generating a parser class. When
123+
* {@code usePolymorphicDispatch} is false on a class that has
124+
* {@code @JsonTypeInfo}/{@code @JsonSubTypes}, a standard parse method is
125+
* emitted instead of the discriminator switch - the caller has determined
126+
* the type is reached only via a concrete subtype and the sibling subtype
127+
* parsers are not generated.
140128
*/
141129
public static void generateParserForFields(final TypeSpec.Builder typeSpec, final Class<?> targetClass, final String parserPackage,
142130
final ClassFinder classFinder, final boolean usePolymorphicDispatch) {

gwt-beans-codegen-core/src/test/java/nl/aerius/codegen/analyzer/TypeAnalyzerTest.java

Lines changed: 5 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -58,26 +58,19 @@ void testCustomParserTypeHandling() {
5858
void abstractBaseReachedViaConcreteSubtypeOnlyDoesNotExpandSiblings() {
5959
final Set<ClassName> types = analyzer.analyzeClass(ConcreteOnlyRootClass.class.getName());
6060

61-
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_ConcreteOnlyRootClass")));
6261
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubAlpha")));
63-
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolyAbstractBase")),
64-
"Abstract base should still be discovered (its parse(handle, config) is invoked by the subtype parser)");
65-
assertFalse(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubBeta")),
66-
"Sibling subtype must be skipped when the base is only reached via a concrete subtype");
67-
assertFalse(analyzer.getPolymorphicallyReachedTypes().contains(PolyAbstractBase.class),
68-
"Base reached only via concrete subtype's superclass walk should NOT be flagged for polymorphic dispatch");
62+
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolyAbstractBase")));
63+
assertFalse(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubBeta")));
64+
assertFalse(analyzer.getPolymorphicallyReachedTypes().contains(PolyAbstractBase.class));
6965
}
7066

7167
@Test
7268
void abstractBaseReachedDirectlyExpandsAllSubtypes() {
7369
final Set<ClassName> types = analyzer.analyzeClass(AbstractFieldRootClass.class.getName());
7470

75-
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolyAbstractBase")));
7671
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubAlpha")));
77-
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubBeta")),
78-
"Abstract field type must walk all subtypes for the discriminator switch");
79-
assertTrue(analyzer.getPolymorphicallyReachedTypes().contains(PolyAbstractBase.class),
80-
"Direct abstract reach must flag the base for polymorphic dispatch generation");
72+
assertTrue(types.contains(ClassName.get("nl.aerius.codegen.analyzer", "TypeAnalyzerTest_PolySubBeta")));
73+
assertTrue(analyzer.getPolymorphicallyReachedTypes().contains(PolyAbstractBase.class));
8174
}
8275

8376
@Test
@@ -130,71 +123,28 @@ private static class ComplexNestedTestClass {
130123
private Map<TestEnum, Map<Integer, Map<Integer, String>>> complexNestedMap;
131124
}
132125

133-
// Polymorphic hierarchy used by reach-tracking tests.
134126
@JsonTypeInfo(use = Id.NAME, property = "_type")
135127
@JsonSubTypes({
136128
@Type(value = PolySubAlpha.class, name = "alpha"),
137129
@Type(value = PolySubBeta.class, name = "beta")
138130
})
139131
private static abstract class PolyAbstractBase {
140132
private String baseLabel;
141-
142-
public String getBaseLabel() {
143-
return baseLabel;
144-
}
145-
146-
public void setBaseLabel(final String baseLabel) {
147-
this.baseLabel = baseLabel;
148-
}
149133
}
150134

151135
private static class PolySubAlpha extends PolyAbstractBase {
152136
private int alphaValue;
153-
154-
public int getAlphaValue() {
155-
return alphaValue;
156-
}
157-
158-
public void setAlphaValue(final int alphaValue) {
159-
this.alphaValue = alphaValue;
160-
}
161137
}
162138

163139
private static class PolySubBeta extends PolyAbstractBase {
164140
private boolean betaFlag;
165-
166-
public boolean isBetaFlag() {
167-
return betaFlag;
168-
}
169-
170-
public void setBetaFlag(final boolean betaFlag) {
171-
this.betaFlag = betaFlag;
172-
}
173141
}
174142

175-
// Field declares the concrete subtype - base is reached only via its superclass chain.
176143
private static class ConcreteOnlyRootClass {
177144
private PolySubAlpha onlyConcrete;
178-
179-
public PolySubAlpha getOnlyConcrete() {
180-
return onlyConcrete;
181-
}
182-
183-
public void setOnlyConcrete(final PolySubAlpha onlyConcrete) {
184-
this.onlyConcrete = onlyConcrete;
185-
}
186145
}
187146

188-
// Field declares the abstract base - every subtype must be reachable.
189147
private static class AbstractFieldRootClass {
190148
private PolyAbstractBase polymorphic;
191-
192-
public PolyAbstractBase getPolymorphic() {
193-
return polymorphic;
194-
}
195-
196-
public void setPolymorphic(final PolyAbstractBase polymorphic) {
197-
this.polymorphic = polymorphic;
198-
}
199149
}
200150
}

gwt-beans-codegen-core/src/test/java/nl/aerius/codegen/test/GeneratedParserValidationTest.java

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -70,10 +70,6 @@ Stream<DynamicTest> shouldGenerateMatchingParsers() throws IOException {
7070
void shouldSkipSiblingSubtypeWhenOnlyConcreteSubtypeIsReached() {
7171
final Path siblingParser = outputDir.resolve("nl/aerius/codegen/test/generated/TestSinglePolySubYParser.java");
7272
Assertions.assertFalse(Files.exists(siblingParser),
73-
"TestSinglePolySubYParser should NOT be generated: nothing in the reachable type graph "
74-
+ "references TestSinglePolyBase abstractly, only TestSinglePolySubX is referenced. "
75-
+ "Generating a parser for TestSinglePolySubY would force callers to ship hand-written "
76-
+ "custom parsers for hierarchies that contain unsupported codegen patterns. "
77-
+ "Found unexpected file at: " + siblingParser);
73+
"Sibling subtype parser must not be generated when only the other concrete subtype is referenced: " + siblingParser);
7874
}
7975
}

gwt-beans-codegen-core/src/test/java/nl/aerius/codegen/test/types/TestConcreteSubtypeOnlyType.java

Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,11 +3,8 @@
33
import nl.aerius.codegen.test.types.polymorphic.TestSinglePolySubX;
44

55
/**
6-
* Wires only a concrete subtype of a polymorphic hierarchy. The hierarchy's
7-
* abstract base (TestSinglePolyBase) is reachable via the subtype's superclass
8-
* chain, but no field is declared as the base itself - so the generator should
9-
* skip sibling subtype parsers (TestSinglePolySubY) and emit a plain parser
10-
* for the abstract base rather than a polymorphic discriminator switch.
6+
* References only one concrete subtype of a polymorphic hierarchy. The
7+
* sibling subtype (TestSinglePolySubY) must not get a generated parser.
118
*/
129
public class TestConcreteSubtypeOnlyType {
1310
private TestSinglePolySubX onlySubtype;

0 commit comments

Comments
 (0)