-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
- Loading branch information
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,210 @@ | ||
/******************************************************************************* | ||
* Copyright (c) 2021 Carsten Hammer. | ||
* | ||
* This program and the accompanying materials | ||
* are made available under the terms of the Eclipse Public License 2.0 | ||
* which accompanies this distribution, and is available at | ||
* https://www.eclipse.org/legal/epl-2.0/ | ||
* | ||
* SPDX-License-Identifier: EPL-2.0 | ||
* | ||
* Contributors: | ||
* Carsten Hammer | ||
*******************************************************************************/ | ||
package org.sandbox.jdt.internal.corext.fix.helper; | ||
|
||
import java.util.Map.Entry; | ||
import java.util.Set; | ||
|
||
import org.eclipse.jdt.core.dom.AST; | ||
import org.eclipse.jdt.core.dom.ASTNode; | ||
import org.eclipse.jdt.core.dom.CompilationUnit; | ||
import org.eclipse.jdt.core.dom.ITypeBinding; | ||
import org.eclipse.jdt.core.dom.MethodDeclaration; | ||
import org.eclipse.jdt.core.dom.SingleVariableDeclaration; | ||
import org.eclipse.jdt.core.dom.TypeDeclaration; | ||
import org.eclipse.jdt.core.dom.rewrite.ASTRewrite; | ||
import org.eclipse.jdt.core.dom.rewrite.ImportRewrite; | ||
import org.eclipse.jdt.core.dom.rewrite.ListRewrite; | ||
import org.eclipse.jdt.internal.corext.fix.CompilationUnitRewriteOperationsFixCore.CompilationUnitRewriteOperationWithSourceRange; | ||
import org.eclipse.jdt.internal.corext.refactoring.structure.CompilationUnitRewrite; | ||
import org.eclipse.text.edits.TextEditGroup; | ||
import org.sandbox.jdt.internal.common.HelperVisitor; | ||
import org.sandbox.jdt.internal.common.ReferenceHolder; | ||
import org.sandbox.jdt.internal.corext.fix.JUnitCleanUpFixCore; | ||
|
||
/** | ||
* | ||
* | ||
*/ | ||
public class ExternalResourceJUnitPlugin extends AbstractTool<ReferenceHolder<Integer, JunitHolder>> { | ||
|
||
private static final String ORG_JUNIT_JUPITER_API_EXTENSION_EXTENSION_CONTEXT = "org.junit.jupiter.api.extension.ExtensionContext"; | ||
private static final String ORG_JUNIT_RULE = "org.junit.Rule"; | ||
private static final String ORG_JUNIT_RULES_EXTERNAL_RESOURCE = "org.junit.rules.ExternalResource"; | ||
private static final String ORG_JUNIT_JUPITER_API_EXTENSION_BEFORE_EACH_CALLBACK = "org.junit.jupiter.api.extension.BeforeEachCallback"; | ||
private static final String ORG_JUNIT_JUPITER_API_EXTENSION_AFTER_EACH_CALLBACK = "org.junit.jupiter.api.extension.AfterEachCallback"; | ||
private static final String ORG_JUNIT_JUPITER_API_EXTENSION_EXTEND_WITH = "org.junit.jupiter.api.extension.ExtendWith"; | ||
|
||
|
||
@Override | ||
public void find(JUnitCleanUpFixCore fixcore, CompilationUnit compilationUnit, | ||
Set<CompilationUnitRewriteOperationWithSourceRange> operations, Set<ASTNode> nodesprocessed) { | ||
ReferenceHolder<Integer, JunitHolder> dataholder = new ReferenceHolder<>(); | ||
HelperVisitor.callTypeDeclarationVisitor(ORG_JUNIT_RULES_EXTERNAL_RESOURCE,compilationUnit, dataholder, nodesprocessed, | ||
(visited, aholder) -> processFoundNode(fixcore, operations, visited, aholder)); | ||
} | ||
|
||
private boolean processFoundNode(JUnitCleanUpFixCore fixcore, | ||
Set<CompilationUnitRewriteOperationWithSourceRange> operations, TypeDeclaration node, | ||
ReferenceHolder<Integer, JunitHolder> dataholder) { | ||
JunitHolder mh = new JunitHolder(); | ||
mh.minv = node; | ||
dataholder.put(dataholder.size(), mh); | ||
operations.add(fixcore.rewrite(dataholder)); | ||
return false; | ||
} | ||
|
||
@Override | ||
public void rewrite(JUnitCleanUpFixCore upp, final ReferenceHolder<Integer, JunitHolder> hit, | ||
final CompilationUnitRewrite cuRewrite, TextEditGroup group) { | ||
ASTRewrite rewriter = cuRewrite.getASTRewrite(); | ||
AST ast = cuRewrite.getRoot().getAST(); | ||
ImportRewrite importrewriter = cuRewrite.getImportRewrite(); | ||
for (Entry<Integer, JunitHolder> entry : hit.entrySet()) { | ||
JunitHolder mh = entry.getValue(); | ||
TypeDeclaration node = mh.getTypeDeclaration(); | ||
modifyExternalResourceClass(node,rewriter,ast,group); | ||
importrewriter.addImport(ORG_JUNIT_JUPITER_API_EXTENSION_EXTEND_WITH); | ||
importrewriter.addImport(ORG_JUNIT_JUPITER_API_EXTENSION_AFTER_EACH_CALLBACK); | ||
importrewriter.addImport(ORG_JUNIT_JUPITER_API_EXTENSION_BEFORE_EACH_CALLBACK); | ||
importrewriter.removeImport(ORG_JUNIT_RULES_EXTERNAL_RESOURCE); | ||
importrewriter.removeImport(ORG_JUNIT_RULE); | ||
importrewriter.addImport(ORG_JUNIT_JUPITER_API_EXTENSION_EXTENSION_CONTEXT); | ||
} | ||
} | ||
|
||
private void modifyExternalResourceClass(TypeDeclaration node, ASTRewrite rewriter,AST ast, TextEditGroup group) { | ||
ITypeBinding binding = node.resolveBinding(); | ||
if (isExternalResource(binding)&& hasDefaultConstructorOrNoConstructor(node)) { | ||
if(isDirect(binding)) { | ||
rewriter.remove(node.getSuperclassType(), group); | ||
} | ||
ListRewrite listRewrite = rewriter.getListRewrite(node, TypeDeclaration.SUPER_INTERFACE_TYPES_PROPERTY); | ||
listRewrite.insertLast(ast.newSimpleType(ast.newName("BeforeEachCallback")), group); | ||
listRewrite.insertLast(ast.newSimpleType(ast.newName("AfterEachCallback")), group); | ||
for (MethodDeclaration method : node.getMethods()) { | ||
if (method.getName().getIdentifier().equals("before")) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
rewriter.replace(method.getName(), ast.newSimpleName("beforeEach"), group); | ||
extracted(rewriter, ast, method, group); | ||
} | ||
if (method.getName().getIdentifier().equals("after")) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
rewriter.replace(method.getName(), ast.newSimpleName("afterEach"), group); | ||
extracted(rewriter, ast, method, group); | ||
} | ||
} | ||
} | ||
} | ||
|
||
private boolean isDirect(ITypeBinding fieldTypeBinding) { | ||
ITypeBinding binding =fieldTypeBinding; | ||
ITypeBinding superClass = binding.getSuperclass(); | ||
|
||
boolean isDirectlyExtendingExternalResource = false; | ||
boolean isIndirectlyExtendingExternalResource = false; | ||
Check warning Code scanning / PMD Avoid unused local variables such as 'element'. Warning
Avoid unused local variables such as 'isIndirectlyExtendingExternalResource'.
Check notice Code scanning / Pmd (reported by Codacy) Avoid unused local variables such as 'isIndirectlyExtendingExternalResource'. Note
Avoid unused local variables such as 'isIndirectlyExtendingExternalResource'.
|
||
|
||
// Prüfen, ob die Klasse direkt oder indirekt von ExternalResource erbt | ||
while (superClass != null) { | ||
if (superClass.getQualifiedName().equals("org.junit.rules.ExternalResource")) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
if (binding.getSuperclass().getQualifiedName().equals("org.junit.rules.ExternalResource")) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
isDirectlyExtendingExternalResource = true; | ||
} else { | ||
isIndirectlyExtendingExternalResource = true; | ||
} | ||
break; | ||
} | ||
superClass = superClass.getSuperclass(); | ||
} | ||
return isDirectlyExtendingExternalResource; | ||
} | ||
|
||
private void extracted(ASTRewrite rewriter, AST ast, MethodDeclaration method, TextEditGroup group) { | ||
ListRewrite listRewrite; | ||
boolean hasExtensionContext = false; | ||
for (Object param : method.parameters()) { | ||
if (param instanceof SingleVariableDeclaration) { | ||
SingleVariableDeclaration variable = (SingleVariableDeclaration) param; | ||
if (variable.getType().toString().equals("ExtensionContext")) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
hasExtensionContext = true; | ||
break; | ||
} | ||
} | ||
} | ||
|
||
if (!hasExtensionContext) { | ||
// Adding the ExtensionContext parameter to the method | ||
|
||
SingleVariableDeclaration newParam = ast.newSingleVariableDeclaration(); | ||
newParam.setType(ast.newSimpleType(ast.newName("ExtensionContext"))); | ||
newParam.setName(ast.newSimpleName("context")); | ||
|
||
listRewrite = rewriter.getListRewrite(method, MethodDeclaration.PARAMETERS_PROPERTY); | ||
listRewrite.insertLast(newParam, group); | ||
} | ||
} | ||
|
||
private boolean hasDefaultConstructorOrNoConstructor(TypeDeclaration classNode) { | ||
boolean hasConstructor = false; | ||
for (Object bodyDecl : classNode.bodyDeclarations()) { | ||
if (bodyDecl instanceof MethodDeclaration) { | ||
MethodDeclaration method = (MethodDeclaration) bodyDecl; | ||
if (method.isConstructor()) { | ||
hasConstructor = true; | ||
if (method.parameters().isEmpty() && method.getBody() != null && method.getBody().statements().isEmpty()) { | ||
return true; | ||
} | ||
} | ||
} | ||
} | ||
return !hasConstructor; | ||
} | ||
|
||
private boolean isExternalResource(ITypeBinding typeBinding) { | ||
while (typeBinding != null) { | ||
if (typeBinding.getQualifiedName().equals(ORG_JUNIT_RULES_EXTERNAL_RESOURCE)) { | ||
Check warning Code scanning / PMD Position literals first in String comparisons Warning
Position literals first in String comparisons
|
||
return true; | ||
} | ||
typeBinding = typeBinding.getSuperclass(); | ||
Check notice Code scanning / Pmd (reported by Codacy) Avoid reassigning parameters such as 'typeBinding' Note
Avoid reassigning parameters such as 'typeBinding'
|
||
} | ||
return false; | ||
} | ||
|
||
@Override | ||
public String getPreview(boolean afterRefactoring) { | ||
if (afterRefactoring) { | ||
return | ||
""" | ||
private String testName; | ||
@BeforeEach | ||
void init(TestInfo testInfo) { | ||
this.testName = testInfo.getDisplayName(); | ||
} | ||
@Test | ||
public void test(){ | ||
System.out.println("Test name: " + testName); | ||
} | ||
"""; //$NON-NLS-1$ | ||
} | ||
return | ||
""" | ||
@Rule | ||
public TestName tn = new TestName(); | ||
@Test | ||
public void test(){ | ||
System.out.println("Test name: " + tn.getMethodName()); | ||
} | ||
"""; //$NON-NLS-1$ | ||
} | ||
} |