/** * BSD-style license; for more info see http://pmd.sourceforge.net/license.html */ package net.sourceforge.pmd.lang.java.symboltable; import static org.junit.Assert.assertEquals; import static org.junit.Assert.assertFalse; import static org.junit.Assert.assertTrue; import static org.junit.Assert.fail; import java.util.Iterator; import java.util.List; import java.util.Map; import org.junit.Test; import net.sourceforge.pmd.PMD; import net.sourceforge.pmd.lang.ast.Node; import net.sourceforge.pmd.lang.java.ast.ASTBlock; import net.sourceforge.pmd.lang.java.ast.ASTCatchStatement; import net.sourceforge.pmd.lang.java.ast.ASTEqualityExpression; import net.sourceforge.pmd.lang.java.ast.ASTInitializer; import net.sourceforge.pmd.lang.java.ast.ASTMethodDeclaration; import net.sourceforge.pmd.lang.java.ast.ASTVariableDeclaratorId; import net.sourceforge.pmd.lang.symboltable.NameDeclaration; import net.sourceforge.pmd.lang.symboltable.NameOccurrence; import net.sourceforge.pmd.lang.symboltable.Scope; public class AcceptanceTest extends STBBaseTst { @Test public void testClashingSymbols() { parseCode(TEST1); } @Test public void testInitializer() { parseCode(TEST_INITIALIZERS); ASTInitializer a = acu.findDescendantsOfType(ASTInitializer.class).get(0); assertFalse(a.isStatic()); a = acu.findDescendantsOfType(ASTInitializer.class).get(1); assertTrue(a.isStatic()); } @Test public void testCatchBlocks() { parseCode(TEST_CATCH_BLOCKS); ASTCatchStatement c = acu.findDescendantsOfType(ASTCatchStatement.class).get(0); ASTBlock a = c.findDescendantsOfType(ASTBlock.class).get(0); Scope s = a.getScope(); Map<NameDeclaration, List<NameOccurrence>> vars = s.getParent().getDeclarations(); assertEquals(1, vars.size()); NameDeclaration v = vars.keySet().iterator().next(); assertEquals("e", v.getImage()); assertEquals(1, (vars.get(v)).size()); } @Test public void testEq() { parseCode(TEST_EQ); ASTEqualityExpression e = acu.findDescendantsOfType(ASTEqualityExpression.class).get(0); ASTMethodDeclaration method = e.getFirstParentOfType(ASTMethodDeclaration.class); Scope s = method.getScope(); Map<NameDeclaration, List<NameOccurrence>> m = s.getDeclarations(); assertEquals(2, m.size()); for (Map.Entry<NameDeclaration, List<NameOccurrence>> entry : m.entrySet()) { NameDeclaration vnd = entry.getKey(); List<NameOccurrence> usages = entry.getValue(); if (vnd.getImage().equals("a") || vnd.getImage().equals("b")) { assertEquals(1, usages.size()); assertEquals(3, usages.get(0).getLocation().getBeginLine()); } else { fail("Unkown variable " + vnd); } } } @Test public void testFieldFinder() { parseCode(TEST_FIELD); // System.out.println(TEST_FIELD); ASTVariableDeclaratorId declaration = acu.findDescendantsOfType(ASTVariableDeclaratorId.class).get(1); assertEquals(3, declaration.getBeginLine()); assertEquals("bbbbbbbbbb", declaration.getImage()); assertEquals(1, declaration.getUsages().size()); NameOccurrence no = declaration.getUsages().get(0); Node location = no.getLocation(); assertEquals(6, location.getBeginLine()); // System.out.println("variable " + declaration.getImage() + " is used // here: " + location.getImage()); } @Test public void testDemo() { parseCode(TEST_DEMO); // System.out.println(TEST_DEMO); ASTMethodDeclaration node = acu.findDescendantsOfType(ASTMethodDeclaration.class).get(0); Scope s = node.getScope(); Map<NameDeclaration, List<NameOccurrence>> m = s.getDeclarations(); for (Iterator<NameDeclaration> i = m.keySet().iterator(); i.hasNext();) { NameDeclaration d = i.next(); assertEquals("buz", d.getImage()); assertEquals("ArrayList", ((TypedNameDeclaration) d).getTypeImage()); List<NameOccurrence> u = m.get(d); assertEquals(1, u.size()); NameOccurrence o = u.get(0); int beginLine = o.getLocation().getBeginLine(); assertEquals(3, beginLine); // System.out.println("Variable: " + d.getImage()); // System.out.println("Type: " + d.getTypeImage()); // System.out.println("Usages: " + u.size()); // System.out.println("Used in line " + beginLine); } } @Test public void testEnum() { parseCode(NameOccurrencesTest.TEST_ENUM); ASTVariableDeclaratorId vdi = acu.findDescendantsOfType(ASTVariableDeclaratorId.class).get(0); List<NameOccurrence> usages = vdi.getUsages(); assertEquals(2, usages.size()); assertEquals(5, usages.get(0).getLocation().getBeginLine()); assertEquals(9, usages.get(1).getLocation().getBeginLine()); } @Test public void testInnerOuterClass() { parseCode(TEST_INNER_CLASS); ASTVariableDeclaratorId vdi = acu.findDescendantsOfType(ASTVariableDeclaratorId.class).get(0); List<NameOccurrence> usages = vdi.getUsages(); assertEquals(2, usages.size()); assertEquals(5, usages.get(0).getLocation().getBeginLine()); assertEquals(10, usages.get(1).getLocation().getBeginLine()); } /** * Unit test for bug #1490 * * @see <a href="https://sourceforge.net/p/pmd/bugs/1490/">#1490 [java] PMD * Error while processing - NullPointerException</a> */ @Test public void testNullPointerEnumValueOfOverloaded() { parseCode("public enum EsmDcVoltageSensor {\n" + " A;\n" + " void bar(int ... args) {\n" + " int idx;\n" + " int startIdx;\n" + " String name = EsmDcVoltageSensor.valueOf((byte) (idx - startIdx)).getName();\n" + " }\n" // that's the overloaded method + " public EsmDCVoltageSensor valueOf(byte b) {\n" + " }\n" + "}\n"); } private static final String TEST_DEMO = "public class Foo {" + PMD.EOL + " void bar(ArrayList buz) { " + PMD.EOL + " buz.add(\"foo\");" + PMD.EOL + " } " + PMD.EOL + "}" + PMD.EOL; private static final String TEST_EQ = "public class Foo {" + PMD.EOL + " boolean foo(String a, String b) { " + PMD.EOL + " return a == b; " + PMD.EOL + " } " + PMD.EOL + "}" + PMD.EOL; private static final String TEST1 = "import java.io.*;" + PMD.EOL + "public class Foo {" + PMD.EOL + " void buz( ) {" + PMD.EOL + " Object o = new Serializable() { int x; };" + PMD.EOL + " Object o1 = new Serializable() { int x; };" + PMD.EOL + " }" + PMD.EOL + "}" + PMD.EOL; private static final String TEST_INITIALIZERS = "public class Foo {" + PMD.EOL + " {} " + PMD.EOL + " static {} " + PMD.EOL + "}" + PMD.EOL; private static final String TEST_CATCH_BLOCKS = "public class Foo {" + PMD.EOL + " void foo() { " + PMD.EOL + " try { " + PMD.EOL + " } catch (Exception e) { " + PMD.EOL + " e.printStackTrace(); " + PMD.EOL + " } " + PMD.EOL + " } " + PMD.EOL + "}" + PMD.EOL; private static final String TEST_FIELD = "public class MyClass {" + PMD.EOL + " private int aaaaaaaaaa; " + PMD.EOL + " boolean bbbbbbbbbb = MyClass.ASCENDING; " + PMD.EOL + " private int zzzzzzzzzz;" + PMD.EOL + " private void doIt() {" + PMD.EOL + " if (bbbbbbbbbb) {" + PMD.EOL + " }" + PMD.EOL + " }" + PMD.EOL + "}" + PMD.EOL; public static final String TEST_INNER_CLASS = "public class Outer {" + PMD.EOL + " private static class Inner {" + PMD.EOL + " private int i;" + PMD.EOL + " private Inner(int i) {" + PMD.EOL + " this.i = i;" + PMD.EOL + " }" + PMD.EOL + " }" + PMD.EOL + " public int modify(int i) {" + PMD.EOL + " Inner in = new Inner(i);" + PMD.EOL + " return in.i;" + PMD.EOL + " }" + PMD.EOL + "}" + PMD.EOL; public static junit.framework.Test suite() { return new junit.framework.JUnit4TestAdapter(AcceptanceTest.class); } }