[superbuilder] toBuilder + singular + javac6 was broken

superbuilder generated the node `x.pluralName(plural == null ? Collections.emptyList() : plural)`.
java6 is not smart enough to infer the appropriate generics for the emptyList() call.
Fixed by always specifying the needed type explicitly: Collections.<String>emptyList();
This commit is contained in:
Reinier Zwitserloot
2021-03-13 04:53:44 +01:00
parent c1bf4ec3b6
commit e8cd744d3b
13 changed files with 49 additions and 27 deletions
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2015-2020 The Project Lombok Authors.
* Copyright (C) 2015-2021 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -451,7 +451,17 @@ public class EclipseSingularsRecipes {
statements.add(0, nullCheck);
}
protected abstract int getTypeArgumentsCount();
protected abstract char[][] getEmptyMakerReceiver(String targetFqn);
protected abstract char[] getEmptyMakerSelector(String targetFqn);
public MessageSend getEmptyExpression(String targetFqn, SingularData data, EclipseNode typeNode, ASTNode source) {
MessageSend send = new MessageSend();
send.receiver = generateQualifiedNameRef(source, getEmptyMakerReceiver(targetFqn));
send.selector = getEmptyMakerSelector(targetFqn);
send.typeArguments = createTypeArgs(getTypeArgumentsCount(), false, typeNode, data.getTypeArgs());
return send;
}
}
}
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2013-2020 The Project Lombok Authors.
* Copyright (C) 2013-2021 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -817,9 +817,7 @@ public class HandleSuperBuilder extends EclipseAnnotationHandler<SuperBuilder> {
ms.arguments = tgt;
} else {
Expression ifNull = new EqualExpression(tgt[0], new NullLiteral(0, 0), OperatorIds.EQUAL_EQUAL);
MessageSend emptyCollection = new MessageSend();
emptyCollection.receiver = generateQualifiedNameRef(source, bfd.singularData.getSingularizer().getEmptyMakerReceiver(bfd.singularData.getTargetFqn()));
emptyCollection.selector = bfd.singularData.getSingularizer().getEmptyMakerSelector(bfd.singularData.getTargetFqn());
MessageSend emptyCollection = bfd.singularData.getSingularizer().getEmptyExpression(bfd.singularData.getTargetFqn(), bfd.singularData, type, source);
ms.arguments = new Expression[] {new ConditionalExpression(ifNull, emptyCollection, tgt[1])};
}
ms.receiver = new SingleNameReference(BUILDER_VARIABLE_NAME, 0);
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2015-2020 The Project Lombok Authors.
* Copyright (C) 2015-2021 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -279,7 +279,7 @@ abstract class EclipseGuavaSingularizer extends EclipseSingularizer {
protected abstract String getAddMethodName();
protected abstract String getAddAllTypeName();
protected int getTypeArgumentsCount() {
@Override protected int getTypeArgumentsCount() {
return getArgumentSuffixes().size();
}
}
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2015-2020 The Project Lombok Authors.
* Copyright (C) 2015-2021 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -156,7 +156,7 @@ abstract class EclipseJavaUtilListSetSingularizer extends EclipseJavaUtilSingula
Annotation[] selfReturnAnnotations = generateSelfReturnAnnotations(deprecate, cfv, data.getSource());
Annotation[] copyToSetterAnnotations = copyAnnotations(md, findCopyableToBuilderSingularSetterAnnotations(data.getAnnotation().up()));
md.annotations = concat(selfReturnAnnotations, copyToSetterAnnotations, Annotation.class);
if (returnStatement != null) createRelevantNonNullAnnotation(builderType, md);
data.setGeneratedByRecursive(md);
HandleNonNull.INSTANCE.fix(injectMethod(builderType, md));
@@ -194,9 +194,13 @@ abstract class EclipseJavaUtilListSetSingularizer extends EclipseJavaUtilSingula
Annotation[] selfReturnAnnotations = generateSelfReturnAnnotations(deprecate, cfv, data.getSource());
Annotation[] copyToSetterAnnotations = copyAnnotations(md, findCopyableToSetterAnnotations(data.getAnnotation().up()));
md.annotations = concat(selfReturnAnnotations, copyToSetterAnnotations, Annotation.class);
if (returnStatement != null) createRelevantNonNullAnnotation(builderType, md);
data.setGeneratedByRecursive(md);
injectMethod(builderType, md);
}
@Override protected int getTypeArgumentsCount() {
return 1;
}
}
@@ -1,5 +1,5 @@
/*
* Copyright (C) 2015-2020 The Project Lombok Authors.
* Copyright (C) 2015-2021 The Project Lombok Authors.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
@@ -349,4 +349,8 @@ public class EclipseJavaUtilMapSingularizer extends EclipseJavaUtilSingularizer
statements.addAll(createJavaUtilSimpleCreationAndFillStatements(data, builderType, true, true, false, true, "TreeMap", builderVariable));
}
}
@Override protected int getTypeArgumentsCount() {
return 2;
}
}
@@ -731,7 +731,7 @@ public class HandleSuperBuilder extends JavacAnnotationHandler<SuperBuilder> {
// Call the builder's setter methods to fill the values from the instance.
for (BuilderFieldData bfd : job.builderFields) {
JCExpressionStatement exec = createSetterCallWithInstanceValue(bfd, job.parentType, maker, setterPrefix);
JCExpressionStatement exec = createSetterCallWithInstanceValue(bfd, job, setterPrefix);
body.append(exec);
}
@@ -740,22 +740,23 @@ public class HandleSuperBuilder extends JavacAnnotationHandler<SuperBuilder> {
return maker.MethodDef(modifiers, name, returnType, copyTypeParams(job.builderType, job.typeParams), List.of(paramInstance, paramBuilder), List.<JCExpression>nil(), bodyBlock, null);
}
private JCExpressionStatement createSetterCallWithInstanceValue(BuilderFieldData bfd, JavacNode type, JavacTreeMaker maker, String setterPrefix) {
private JCExpressionStatement createSetterCallWithInstanceValue(BuilderFieldData bfd, SuperBuilderJob job, String setterPrefix) {
JavacTreeMaker maker = job.getTreeMaker();
JCExpression[] tgt = new JCExpression[bfd.singularData == null ? 1 : 2];
if (bfd.obtainVia == null || !bfd.obtainVia.field().isEmpty()) {
for (int i = 0; i < tgt.length; i++) {
tgt[i] = maker.Select(maker.Ident(type.toName(INSTANCE_VARIABLE_NAME)), bfd.obtainVia == null ? bfd.rawName : type.toName(bfd.obtainVia.field()));
tgt[i] = maker.Select(maker.Ident(job.toName(INSTANCE_VARIABLE_NAME)), bfd.obtainVia == null ? bfd.rawName : job.toName(bfd.obtainVia.field()));
}
} else {
if (bfd.obtainVia.isStatic()) {
for (int i = 0; i < tgt.length; i++) {
JCExpression typeRef = namePlusTypeParamsToTypeReference(maker, type, List.<JCTypeParameter>nil());
JCExpression c = maker.Select(typeRef, type.toName(bfd.obtainVia.method()));
tgt[i] = maker.Apply(List.<JCExpression>nil(), c, List.<JCExpression>of(maker.Ident(type.toName(INSTANCE_VARIABLE_NAME))));
JCExpression typeRef = namePlusTypeParamsToTypeReference(maker, job.parentType, List.<JCTypeParameter>nil());
JCExpression c = maker.Select(typeRef, job.toName(bfd.obtainVia.method()));
tgt[i] = maker.Apply(List.<JCExpression>nil(), c, List.<JCExpression>of(maker.Ident(job.toName(INSTANCE_VARIABLE_NAME))));
}
} else {
for (int i = 0; i < tgt.length; i++) {
JCExpression c = maker.Select(maker.Ident(type.toName(INSTANCE_VARIABLE_NAME)), type.toName(bfd.obtainVia.method()));
JCExpression c = maker.Select(maker.Ident(job.toName(INSTANCE_VARIABLE_NAME)), job.toName(bfd.obtainVia.method()));
tgt[i] = maker.Apply(List.<JCExpression>nil(), c, List.<JCExpression>nil());
}
}
@@ -766,13 +767,12 @@ public class HandleSuperBuilder extends JavacAnnotationHandler<SuperBuilder> {
arg = tgt[0];
} else {
JCExpression eqNull = maker.Binary(CTC_EQUAL, tgt[0], maker.Literal(CTC_BOT, null));
String emptyMaker = bfd.singularData.getSingularizer().getEmptyMaker(bfd.singularData.getTargetFqn());
JCExpression emptyCollection = maker.Apply(List.<JCExpression>nil(), chainDots(type, emptyMaker.split("\\.")), List.<JCExpression>nil());
JCExpression emptyCollection = bfd.singularData.getSingularizer().getEmptyExpression(bfd.singularData.getTargetFqn(), maker, bfd.singularData, job.parentType, job.sourceNode);
arg = maker.Conditional(eqNull, emptyCollection, tgt[1]);
}
String setterName = HandlerUtil.buildAccessorName(setterPrefix, bfd.name.toString());
JCMethodInvocation apply = maker.Apply(List.<JCExpression>nil(), maker.Select(maker.Ident(type.toName(BUILDER_VARIABLE_NAME)), type.toName(setterName)), List.of(arg));
JCMethodInvocation apply = maker.Apply(List.<JCExpression>nil(), maker.Select(maker.Ident(job.toName(BUILDER_VARIABLE_NAME)), job.toName(setterName)), List.of(arg));
JCExpressionStatement exec = maker.Exec(apply);
return exec;
}
@@ -501,5 +501,11 @@ public class JavacSingularsRecipes {
protected abstract int getTypeArgumentsCount();
protected abstract String getEmptyMaker(String target);
public JCExpression getEmptyExpression(String target, JavacTreeMaker maker, SingularData data, JavacNode builderType, JavacNode source) {
String emptyMaker = getEmptyMaker(target);
List<JCExpression> typeArgs = createTypeArgs(getTypeArgumentsCount(), false, builderType, data.getTypeArgs(), source);
return maker.Apply(typeArgs, chainDots(builderType, emptyMaker.split("\\.")), List.<JCExpression>nil());
}
}
}
@@ -35,7 +35,7 @@ public class SuperBuilderBasicToBuilder {
b.obtainViaField(instance.field1);
b.obtainViaMethod(instance.method());
b.obtainViaStaticMethod(SuperBuilderBasicToBuilder.Parent.staticMethod(instance));
b.items(instance.items == null ? java.util.Collections.emptyList() : instance.items);
b.items(instance.items == null ? java.util.Collections.<String>emptyList() : instance.items);
}
@java.lang.SuppressWarnings("all")
protected abstract B self();
@@ -19,7 +19,7 @@ public class SuperBuilderWithGenericsAndToBuilder {
@java.lang.SuppressWarnings("all")
private static <A> void $fillValuesFromInstanceIntoBuilder(final SuperBuilderWithGenericsAndToBuilder.Parent<A> instance, final SuperBuilderWithGenericsAndToBuilder.Parent.ParentBuilder<A, ?, ?> b) {
b.field1(instance.field1);
b.items(instance.items == null ? java.util.Collections.emptyMap() : instance.items);
b.items(instance.items == null ? java.util.Collections.<Integer, String>emptyMap() : instance.items);
}
@java.lang.SuppressWarnings("all")
protected abstract B self();
@@ -35,7 +35,7 @@ public class SuperBuilderWithSetterPrefix {
b.withObtainViaField(instance.field1);
b.withObtainViaMethod(instance.method());
b.withObtainViaStaticMethod(SuperBuilderWithSetterPrefix.Parent.staticMethod(instance));
b.withItems(instance.items == null ? java.util.Collections.emptyList() : instance.items);
b.withItems(instance.items == null ? java.util.Collections.<String>emptyList() : instance.items);
}
@java.lang.SuppressWarnings("all")
protected abstract B self();
@@ -19,7 +19,7 @@ public class SuperBuilderBasicToBuilder {
b.obtainViaField(instance.field1);
b.obtainViaMethod(instance.method());
b.obtainViaStaticMethod(SuperBuilderBasicToBuilder.Parent.staticMethod(instance));
b.items(((instance.items == null) ? java.util.Collections.emptyList() : instance.items));
b.items(((instance.items == null) ? java.util.Collections.<String>emptyList() : instance.items));
}
protected abstract @java.lang.SuppressWarnings("all") B self();
public abstract @java.lang.SuppressWarnings("all") C build();
@@ -14,7 +14,7 @@ public class SuperBuilderWithGenericsAndToBuilder {
}
private static @java.lang.SuppressWarnings("all") <A>void $fillValuesFromInstanceIntoBuilder(final SuperBuilderWithGenericsAndToBuilder.Parent<A> instance, final SuperBuilderWithGenericsAndToBuilder.Parent.ParentBuilder<A, ?, ?> b) {
b.field1(instance.field1);
b.items(((instance.items == null) ? java.util.Collections.emptyMap() : instance.items));
b.items(((instance.items == null) ? java.util.Collections.<Integer, String>emptyMap() : instance.items));
}
protected abstract @java.lang.SuppressWarnings("all") B self();
public abstract @java.lang.SuppressWarnings("all") C build();
@@ -19,7 +19,7 @@ public class SuperBuilderWithSetterPrefix {
b.withObtainViaField(instance.field1);
b.withObtainViaMethod(instance.method());
b.withObtainViaStaticMethod(SuperBuilderWithSetterPrefix.Parent.staticMethod(instance));
b.withItems(((instance.items == null) ? java.util.Collections.emptyList() : instance.items));
b.withItems(((instance.items == null) ? java.util.Collections.<String>emptyList() : instance.items));
}
protected abstract @java.lang.SuppressWarnings("all") B self();
public abstract @java.lang.SuppressWarnings("all") C build();