Skip to content

Commit

Permalink
Convert most of the checks as used for UseLombokGetter
Browse files Browse the repository at this point in the history
  • Loading branch information
timtebeek committed Dec 15, 2024
1 parent 108fdfd commit 81c9699
Show file tree
Hide file tree
Showing 2 changed files with 51 additions and 69 deletions.
80 changes: 40 additions & 40 deletions src/main/java/org/openrewrite/java/migrate/lombok/LombokUtils.java
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,7 @@
import org.openrewrite.java.tree.Expression;
import org.openrewrite.java.tree.J;
import org.openrewrite.java.tree.JavaType;
import org.openrewrite.java.tree.Statement;

import java.util.List;

import static java.util.stream.Collectors.toList;
import static lombok.AccessLevel.*;
import static org.openrewrite.java.tree.J.Modifier.Type.*;

Expand Down Expand Up @@ -66,40 +62,6 @@ static boolean isGetter(J.MethodDeclaration method) {
return false;
}

static boolean isEffectivelySetter(J.MethodDeclaration method) {
boolean isVoid = "void".equals(method.getType().toString());
List<Statement> actualParameters = method.getParameters().stream()
.filter(s -> !(s instanceof J.Empty))
.collect(toList());
boolean oneParam = actualParameters.size() == 1;
if (!isVoid || !oneParam)
return false;

J.VariableDeclarations variableDeclarations = (J.VariableDeclarations) actualParameters.get(0);
J.VariableDeclarations.NamedVariable param = variableDeclarations.getVariables().get(0);
String paramName = param.getName().toString();

boolean singularStatement = method.getBody() != null //abstract methods can be null
&& method.getBody().getStatements().size() == 1 &&
method.getBody().getStatements().get(0) instanceof J.Assignment;

if (!singularStatement) {
return false;
}
J.Assignment assignment = (J.Assignment) method.getBody().getStatements().get(0);

J.FieldAccess fieldAccess = (J.FieldAccess) assignment.getVariable();

return
// assigned value is exactly the parameter
assignment.getAssignment().toString().equals(paramName) // type of parameter and field have to match
&&

// type of parameter and field have to match
param.getType().equals(fieldAccess.getType());

}

private static boolean hasMatchingTypeAndName(J.MethodDeclaration method, @Nullable JavaType type, String simpleName) {
if (method.getType() == type) {
String deriveGetterMethodName = deriveGetterMethodName(type, simpleName);
Expand All @@ -121,8 +83,46 @@ private static String deriveGetterMethodName(@Nullable JavaType type, String fie
return "get" + StringUtils.capitalize(fieldName);
}

static String deriveSetterMethodName(JavaType.Variable fieldType) {
return "set" + StringUtils.capitalize(fieldType.getName());
static boolean isSetter(J.MethodDeclaration method) {
// Check return type: void
if (method.getType() != JavaType.Primitive.Void) {
return false;
}
// Check signature: single parameter
if (method.getParameters().size() != 1 || method.getParameters().get(0) instanceof J.Empty) {
return false;
}
// Check body: just an assignment
if (method.getBody() == null || //abstract methods can be null
method.getBody().getStatements().size() != 1 ||
!(method.getBody().getStatements().get(0) instanceof J.Assignment)) {
return false;
}
J.Assignment assignment = (J.Assignment) method.getBody().getStatements().get(0);
J.FieldAccess fieldAccess = (J.FieldAccess) assignment.getVariable();
if (!method.getSimpleName().equals(deriveSetterMethodName(fieldAccess))) {
return false;
}

// Check argument is assigned to field
J.VariableDeclarations variableDeclarations = (J.VariableDeclarations) method.getParameters().get(0);
J.VariableDeclarations.NamedVariable param = variableDeclarations.getVariables().get(0);
JavaType paramType = param.getType();
String paramName = param.getName().toString();


return
// assigned value is exactly the parameter
assignment.getAssignment().toString().equals(paramName) // type of parameter and field have to match
&&

// type of parameter and field have to match
param.getType().equals(fieldAccess.getType());

}

private static String deriveSetterMethodName(J.FieldAccess fieldAccess) {
return "set" + StringUtils.capitalize(fieldAccess.getSimpleName());
}

static AccessLevel getAccessLevel(J.MethodDeclaration methodDeclaration) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -42,12 +42,7 @@ public String getDisplayName() {
@Override
public String getDescription() {
//language=markdown
return "Convert trivial setter methods to `@Setter` annotations on their respective fields.\n\n" +
"Limitations:\n\n" +
" - Does not add a dependency to Lombok, users need to do that manually\n" +
" - Ignores fields that are declared on the same line as others, e.g. `private int foo, bar; " +
"Users who have such fields are advised to separate them beforehand with [org.openrewrite.staticanalysis.MultipleVariableDeclaration](https://docs.openrewrite.org/recipes/staticanalysis/multiplevariabledeclarations).\n" +
" - Does not offer any of the configuration keys listed in https://projectlombok.org/features/GetterSetter.";
return "Convert trivial setter methods to `@Setter` annotations on their respective fields.";
}

@Override
Expand All @@ -57,31 +52,18 @@ public Set<String> getTags() {

@Override
public TreeVisitor<?, ExecutionContext> getVisitor() {
return new MethodRemover();
}

@Value
@EqualsAndHashCode(callSuper = false)
private static class MethodRemover extends JavaIsoVisitor<ExecutionContext> {

@Override
public J.@Nullable MethodDeclaration visitMethodDeclaration(J.MethodDeclaration method, ExecutionContext ctx) {
if (LombokUtils.isEffectivelySetter(method)) {
J.Assignment assignment_ = (J.Assignment) method.getBody().getStatements().get(0);
J.FieldAccess fieldAccess = (J.FieldAccess) assignment_.getVariable();

Variable fieldType = fieldAccess.getName().getFieldType();
boolean nameMatch = method.getSimpleName().equals(LombokUtils.deriveSetterMethodName(fieldType));
if (nameMatch) {
doAfterVisit(new FieldAnnotator(
Setter.class,
fieldType,
LombokUtils.getAccessLevel(method)
));
return new JavaIsoVisitor<ExecutionContext>() {
@Override
public J.@Nullable MethodDeclaration visitMethodDeclaration(J.MethodDeclaration method, ExecutionContext ctx) {
if (LombokUtils.isSetter(method)) {
J.Assignment assignment_ = (J.Assignment) method.getBody().getStatements().get(0);
J.FieldAccess fieldAccess = (J.FieldAccess) assignment_.getVariable();
Variable fieldType = fieldAccess.getName().getFieldType();
doAfterVisit(new FieldAnnotator(Setter.class, fieldType, LombokUtils.getAccessLevel(method)));
return null; //delete
}
return method;
}
return method;
}
};
}
}

0 comments on commit 81c9699

Please sign in to comment.