Merge pull request #407 from kerie/type-resolve-only-once2

性能优化,自定义类型解析对于每个java文件只处理一次
This commit is contained in:
SeanCai
2018-11-06 19:32:11 +08:00
committed by GitHub

View File

@@ -15,12 +15,17 @@
*/ */
package com.alibaba.p3c.pmd.lang.java.rule; package com.alibaba.p3c.pmd.lang.java.rule;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import com.alibaba.p3c.pmd.I18nResources; import com.alibaba.p3c.pmd.I18nResources;
import com.alibaba.p3c.pmd.fix.FixClassTypeResolver; import com.alibaba.p3c.pmd.fix.FixClassTypeResolver;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.lang.ast.Node; import net.sourceforge.pmd.lang.ast.Node;
import net.sourceforge.pmd.lang.java.ast.ASTCompilationUnit; import net.sourceforge.pmd.lang.java.ast.ASTCompilationUnit;
import net.sourceforge.pmd.lang.java.rule.AbstractJavaRule; import net.sourceforge.pmd.lang.java.rule.AbstractJavaRule;
import org.apache.commons.lang3.StringUtils;
/** /**
* re calculate node type * re calculate node type
@@ -29,11 +34,29 @@ import net.sourceforge.pmd.lang.java.rule.AbstractJavaRule;
* @date 2016/11/20 * @date 2016/11/20
*/ */
public abstract class AbstractAliRule extends AbstractJavaRule { public abstract class AbstractAliRule extends AbstractJavaRule {
private static final Map<String, Boolean> TYPE_RESOLVER_MAP = new ConcurrentHashMap<>(16);
private static final String EMPTY_FILE_NAME = "n/a";
private static final String DELIMITER = "-";
@Override @Override
public Object visit(ASTCompilationUnit node, Object data) { public Object visit(ASTCompilationUnit node, Object data) {
FixClassTypeResolver classTypeResolver = new FixClassTypeResolver(AbstractAliRule.class.getClassLoader()); // Each CompilationUnit will be scanned only once by custom type resolver.
node.setClassTypeResolver(classTypeResolver); String sourceCodeFilename = ((RuleContext)data).getSourceCodeFilename();
node.jjtAccept(classTypeResolver, data);
// Do type resolve if file name is empty(unit tests).
if (StringUtils.isBlank(sourceCodeFilename) || EMPTY_FILE_NAME.equals(sourceCodeFilename)) {
resolveType(node, data);
return super.visit(node, data);
}
// If file name is not empty, use filename + hashcode to identify a compilation unit.
String uniqueId = sourceCodeFilename + DELIMITER + node.hashCode();
if (!TYPE_RESOLVER_MAP.containsKey(uniqueId)) {
resolveType(node, data);
TYPE_RESOLVER_MAP.put(uniqueId, true);
}
return super.visit(node, data); return super.visit(node, data);
} }
@@ -57,5 +80,11 @@ public abstract class AbstractAliRule extends AbstractJavaRule {
super.addViolationWithMessage(data, node, super.addViolationWithMessage(data, node,
String.format(I18nResources.getMessageWithExceptionHandled(message), args)); String.format(I18nResources.getMessageWithExceptionHandled(message), args));
} }
private void resolveType(ASTCompilationUnit node, Object data) {
FixClassTypeResolver classTypeResolver = new FixClassTypeResolver(AbstractAliRule.class.getClassLoader());
node.setClassTypeResolver(classTypeResolver);
node.jjtAccept(classTypeResolver, data);
}
} }