Missing comments - only class level required.
- Required
+ Required
Ignored
Ignored
Ignored
@@ -61,7 +61,7 @@ public class Foo {
Too many comments - all comments are unwanted.
- Unwanted
+ Unwanted
Unwanted
Unwanted
Unwanted
@@ -505,5 +505,23 @@ public class CommentRequired {
]]>
+
+ #1683 [java] CommentRequired property names are inconsistent - use deprecated property
+ Unwanted
+ 1
+
+
+
+ #1683 [java] CommentRequired property names are inconsistent - use new property
+ Unwanted
+ 1
+
+
diff --git a/pmd-javascript/pom.xml b/pmd-javascript/pom.xml
index 11fb5fd85e..7d7011d3da 100644
--- a/pmd-javascript/pom.xml
+++ b/pmd-javascript/pom.xml
@@ -39,7 +39,7 @@
-
+
diff --git a/pmd-jsp/pom.xml b/pmd-jsp/pom.xml
index ecb2101690..d1499f1c77 100644
--- a/pmd-jsp/pom.xml
+++ b/pmd-jsp/pom.xml
@@ -40,7 +40,7 @@
-
+
diff --git a/pmd-jsp/src/test/java/net/sourceforge/pmd/lang/jsp/ast/XPathJspRuleTest.java b/pmd-jsp/src/test/java/net/sourceforge/pmd/lang/jsp/ast/XPathJspRuleTest.java
index 11f3bc77e9..3597fa8496 100644
--- a/pmd-jsp/src/test/java/net/sourceforge/pmd/lang/jsp/ast/XPathJspRuleTest.java
+++ b/pmd-jsp/src/test/java/net/sourceforge/pmd/lang/jsp/ast/XPathJspRuleTest.java
@@ -16,9 +16,9 @@ import net.sourceforge.pmd.Report;
import net.sourceforge.pmd.Rule;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.RuleSet;
-import net.sourceforge.pmd.RuleSetFactory;
import net.sourceforge.pmd.RuleSets;
import net.sourceforge.pmd.RuleViolation;
+import net.sourceforge.pmd.RulesetsFactoryUtils;
import net.sourceforge.pmd.lang.LanguageRegistry;
import net.sourceforge.pmd.lang.jsp.JspLanguageModule;
import net.sourceforge.pmd.lang.rule.XPathRule;
@@ -28,14 +28,14 @@ public class XPathJspRuleTest extends RuleTst {
/**
* Test matching a XPath expression against a JSP source.
- * @throws PMDException
+ * @throws PMDException
*/
@Test
public void testExpressionMatching() throws PMDException {
Rule rule = new XPathRule(XPATH_EXPRESSION);
rule.setMessage("Test");
rule.setLanguage(LanguageRegistry.getLanguage(JspLanguageModule.NAME));
- RuleSet rules = new RuleSetFactory().createSingleRuleRuleSet(rule);
+ RuleSet rules = RulesetsFactoryUtils.defaultFactory().createSingleRuleRuleSet(rule);
RuleContext ctx = new RuleContext();
Report report = new Report();
diff --git a/pmd-matlab/pom.xml b/pmd-matlab/pom.xml
index 73b9d0f7eb..d49731c5b8 100644
--- a/pmd-matlab/pom.xml
+++ b/pmd-matlab/pom.xml
@@ -34,7 +34,7 @@
-
+
diff --git a/pmd-objectivec/pom.xml b/pmd-objectivec/pom.xml
index e43873e5dd..70732c4667 100644
--- a/pmd-objectivec/pom.xml
+++ b/pmd-objectivec/pom.xml
@@ -34,7 +34,7 @@
-
+
diff --git a/pmd-plsql/etc/grammar/PldocAST.jjt b/pmd-plsql/etc/grammar/PldocAST.jjt
index f01524dc45..da37ca0f3d 100644
--- a/pmd-plsql/etc/grammar/PldocAST.jjt
+++ b/pmd-plsql/etc/grammar/PldocAST.jjt
@@ -227,6 +227,9 @@ public class PLSQLParser {
/**
* Semantic lookahead to check if the next identifier is a
* specific keyword.
+ *
+ *
+ * Usage: LOOKAHEAD({isKeyword("WAIT")}) KEYWORD("WAIT")
*/
private boolean isKeyword(String keyword) {
return getToken(1).kind == IDENTIFIER && getToken(1).image.equalsIgnoreCase(keyword);
@@ -259,13 +262,13 @@ ASTInput Input(String sourcecode) : {}
| LOOKAHEAD(6) Directory()
| LOOKAHEAD(6) DatabaseLink()
| LOOKAHEAD(6) Global()
- | LOOKAHEAD(6) DDLCommand() //Ignore any other DDL Event
+ | (LOOKAHEAD(6) DDLCommand())+
| LOOKAHEAD(2) SqlPlusCommand()
| UpdateStatement()
| DeleteStatement()
| InsertStatement()
- | SelectStatement() (";")?
- |(|||||) SkipPastNextTokenOccurrence(SQLPLUS_TERMINATOR) //Ignore SQL statements in scripts
+ | SelectStatement() [";"]
+ |(|||||) ReadPastNextOccurrence(";") //Ignore SQL statements in scripts
)
("/")*
)*
@@ -279,8 +282,15 @@ ASTDDLCommand DDLCommand() :
}
{
(
- simpleNode = DDLEvent()
- SkipPastNextTokenOccurrence(SQLPLUS_TERMINATOR)
+ (
+ LOOKAHEAD({isKeyword("COMMENT")})
+ simpleNode = Comment()
+ )
+ |
+ (
+ simpleNode = DDLEvent()
+ ReadPastNextOccurrence(";")
+ )
)
{ jjtThis.setImage(simpleNode.getImage()) ; return jjtThis ; }
}
@@ -315,7 +325,7 @@ ASTSqlPlusCommand SqlPlusCommand() :
|
|
// DDL that might be encountered
- |
+ | LOOKAHEAD({isKeyword("COMMENT")}) KEYWORD("COMMENT")
|
|
|
@@ -1121,6 +1131,7 @@ ASTRead2NextOccurrence Read2NextOccurrence(String target) :
{
nextToken = getNextToken();
sb.append(nextToken.image);
+ sb.append(' ');
nextToken = getToken(1);
}
}
@@ -1133,10 +1144,11 @@ ASTRead2NextOccurrence Read2NextOccurrence(String target) :
*/
ASTReadPastNextOccurrence ReadPastNextOccurrence(String target) :
{
+ ASTRead2NextOccurrence skipped = Read2NextOccurrence(target);
+
StringBuilder sb = new StringBuilder();
- Token t = null;
- sb.append(Read2NextOccurrence(target)) ;
- t = getNextToken(); // Chomp this one
+ sb.append(skipped.getImage()) ;
+ Token t = getNextToken(); // Chomp this one
sb.append(t.image);
}
{
@@ -3425,54 +3437,10 @@ ASTLiteral Literal() :
}
ASTStringLiteral StringLiteral() :
+{}
{
- Token thisToken = null;
- StringBuilder literal = new StringBuilder() ;
- char startDelimiter ;
- char endDelimiter ;
- String terminator = null;
-}
-{
- //Essentially unchanged
- (
- thisToken =
- {
- literal.append(thisToken.image);
- /*
- This might be Q-Quoted string and this might be only a partial string
- The token will only match up to the first single quote.
- The code below appends any remaining part, theh returns the complete string
- */
- if (thisToken.image.toUpperCase().startsWith("Q'")
- && thisToken.image.length() > 2
- )
- {
- // Get the first token of the string so that the delimiter can be identified
-
- startDelimiter= thisToken.image.charAt(2) ;
- /*
- if the start delimiter is one of [, {, <, or (, the end delimiter
- is the corresponding closing character
- */
- switch (startDelimiter)
- {
- case '<' : endDelimiter = '>' ; break ;
- case '{' : endDelimiter = '}' ; break ;
- case '(' : endDelimiter = ')' ; break ;
- case '[' : endDelimiter = ']' ; break ;
- default: endDelimiter = startDelimiter ;
- }
-
- terminator = new String(endDelimiter + "'");
- if (!thisToken.image.endsWith(terminator))
- {
- //Loop until we find atoken that ends with a single-quote precede by the terminator
- literal.append(ReadPastNextOccurrence(terminator));
- }
- }
- }
- )
- { jjtThis.setImage(literal.toString()) ; jjtThis.value = literal.toString() ; return jjtThis ; }
+
+ { jjtThis.setImage(token.image); return jjtThis ; }
}
@@ -3904,19 +3872,22 @@ ASTViewColumn ViewColumn() :
{ return jjtThis ; }
}
+/**
+ * https://docs.oracle.com/en/database/oracle/oracle-database/18/sqlrf/COMMENT.html#GUID-65F447C4-6914-4823-9691-F15D52DB74D7
+ */
ASTComment Comment() :
{
}
{
- (
+ LOOKAHEAD({isKeyword("COMMENT")}) KEYWORD("COMMENT") { jjtThis.setImage(token.image); }
+ (
(( | | ) [LOOKAHEAD(2) ID()"."] ID()) |
( [LOOKAHEAD(ID()"."ID()"."ID()) ID()"."] ID() "." ID())
)
-
- [";"]
- { return jjtThis ; }
+ StringLiteral()
+ ";"
+ { return jjtThis ; }
}
-// SRT * /
@@ -4489,23 +4460,26 @@ ASTNonDMLTrigger NonDMLTrigger() :
{ return jjtThis ; }
}
-
+/**
+ * https://docs.oracle.com/en/database/oracle/oracle-database/18/sqlrf/Types-of-SQL-Statements.html#GUID-FD9A8CB4-6B9A-44E5-B114-EFB8DA76FC88
+ */
ASTDDLEvent DDLEvent(): {}
{
(
|
|
|
- |
+ | LOOKAHEAD({isKeyword("COMMENT")}) KEYWORD("COMMENT")
|
|
|
+ // |
|
|
+ // |
|
|
|
- |
)
{ jjtThis.setImage(token.toString()) ; jjtThis.value = token ; return jjtThis ; }
}
@@ -4741,7 +4715,6 @@ TOKEN [IGNORE_CASE]:
|
|
|
- |
|
|
|
@@ -4997,7 +4970,6 @@ TOKEN [IGNORE_CASE]:
| //11G Trigger Syntax
| //11G Trigger Syntax
| //11G Trigger Syntax
-| //11G Trigger Syntax
| //11G Trigger Syntax
| //11G Trigger Syntax
| //11G Trigger Syntax
@@ -5109,26 +5081,9 @@ TOKEN :
|
< #INTEGER_LITERAL: ( )+ >
|
-
-< #_WHATEVER_CHARACTER_WO_ASTERISK: (~["'"]) >
+< #_WHATEVER_CHARACTER_WO_APOSTROPHE: (~["'"]) >
|
-< CHARACTER_LITERAL: "'" (<_WHATEVER_CHARACTER_WO_ASTERISK> | )? "'" >
-//|< STRING_LITERAL:
-// (["q","Q"])* "'" (<_WHATEVER_CHARACTER_WO_ASTERISK> | | "''")* "'"
-//> //Cope with Q-quoted stringswithout single quotes in them
-|< STRING_LITERAL:
-// Hard-code the most likely q-quote strings
- "'" (<_WHATEVER_CHARACTER_WO_ASTERISK> | | "''")* "'"
-|(["n","N"]) "'" (<_WHATEVER_CHARACTER_WO_ASTERISK> | | "''")* "'" //National Character Set String
-|(["q","Q"]) "'" (<_WHATEVER_CHARACTER_WO_ASTERISK> | | "''")* "'" // Bug 160632
-|(["q","Q"]) "'[" (~["[","]"])* "]'"
-|(["q","Q"]) "'{" (~["{","}"])* "}'"
-|(["q","Q"]) "'<" (~["<",">"])* ">'"
-|(["q","Q"]) "'(" (~["(",")"])* ")'"
-|(["q","Q"]) "'/" (~["/"])* "/'"
-|(["q","Q"]) "'!" (~["!"])* "!'"
-|(["q","Q"]) "'#" (~["#"])* "#'"
-> //Cope with Q-quoted stringswithout single quotes in them
+< CHARACTER_LITERAL: "'" (<_WHATEVER_CHARACTER_WO_APOSTROPHE> | )? "'" >
|
< #_WHATEVER_CHARACTER_WO_QUOTE: (~["\""]) >
|
@@ -5143,10 +5098,43 @@ TOKEN :
< JAVA_INTERFACE_CLASS: ( "SQLData" | "CustomDatum" | "OraData" ) >
//|
//< #BOOLEAN_LITERAL: "TRUE" | "FALSE" >
-|
-
}
+/**
+ * https://docs.oracle.com/en/database/oracle/oracle-database/18/sqlrf/Literals.html#GUID-1824CBAA-6E16-4921-B2A6-112FB02248DA
+ */
+ MORE :
+{
+ < #_ALTERNATIVE_QUOTING_STRING_LITERAL:
+ (["q","Q"]) "'[" (~["]"] | "]" ~["'"] )* "]"
+ | (["q","Q"]) "'{" (~["}"] | "}" ~["'"] )* "}"
+ | (["q","Q"]) "'<" (~[">"] | ">" ~["'"] )* ">"
+ | (["q","Q"]) "'(" (~[")"] | ")" ~["'"] )* ")"
+ >
+ | <(["n","N"])? "'" (<_WHATEVER_CHARACTER_WO_APOSTROPHE> | | "''")*> : IN_STRING_LITERAL_TOKENIZE
+ | <(["n","N"])? <_ALTERNATIVE_QUOTING_STRING_LITERAL>> : IN_STRING_LITERAL_TOKENIZE
+
+ // special handling for custom quote delimiters
+ | <(["n","N"])? (["q","Q"]) "'" (~[" ", "\t", "\r", "\n", "[", "{", "<", "("])> : IN_STRING_LITERAL
+}
+ MORE : {
+ <~["'"]>
+ | <"'"> {
+ int quoteDelimiter = image.charAt(2);
+ if (image.charAt(0) == 'n' || image.charAt(0) == 'N') {
+ quoteDelimiter = image.charAt(3);
+ }
+ int beforeQuote = image.charAt(image.length() - 2);
+ if (quoteDelimiter == beforeQuote) {
+ input_stream.backup(1);
+ image.setLength(image.length() - 1);
+ SwitchTo(IN_STRING_LITERAL_TOKENIZE);
+ }
+ }
+}
+ TOKEN : { : DEFAULT }
+
+
/**
* PL/SQL Reserved words
*
@@ -5386,7 +5374,6 @@ ASTKEYWORD_UNRESERVED KEYWORD_UNRESERVED (): {}
//|
//|
//|
-|
|
//|
//|
@@ -5447,7 +5434,6 @@ ASTKEYWORD_UNRESERVED KEYWORD_UNRESERVED (): {}
//|
//|
|
-|
//|
//|
|
@@ -6352,7 +6338,7 @@ ASTID ID(): {}
| KEYWORD_UNRESERVED() //SRT 2011-04-17
/*KEYWORDS_UNRESERVED
| | | | | | | | |
- | | | |
+ | | |
*/
//20120501 |
| |
@@ -6615,7 +6601,6 @@ ASTQualifiedID QualifiedID(): {}
//
//|
//20120501 |
- //|
//|
//
//
diff --git a/pmd-plsql/pom.xml b/pmd-plsql/pom.xml
index 56abfd1d71..76401058aa 100644
--- a/pmd-plsql/pom.xml
+++ b/pmd-plsql/pom.xml
@@ -40,7 +40,7 @@
-
+
diff --git a/pmd-plsql/src/main/ant/alljavacc.xml b/pmd-plsql/src/main/ant/alljavacc.xml
index d22c66587a..c161ad16ca 100644
--- a/pmd-plsql/src/main/ant/alljavacc.xml
+++ b/pmd-plsql/src/main/ant/alljavacc.xml
@@ -67,6 +67,7 @@
+
diff --git a/pmd-plsql/src/main/java/net/sourceforge/pmd/lang/plsql/ast/ASTStringLiteral.java b/pmd-plsql/src/main/java/net/sourceforge/pmd/lang/plsql/ast/ASTStringLiteral.java
new file mode 100644
index 0000000000..d66683fafc
--- /dev/null
+++ b/pmd-plsql/src/main/java/net/sourceforge/pmd/lang/plsql/ast/ASTStringLiteral.java
@@ -0,0 +1,43 @@
+/*
+ * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
+ */
+
+
+package net.sourceforge.pmd.lang.plsql.ast;
+
+public final class ASTStringLiteral extends net.sourceforge.pmd.lang.plsql.ast.AbstractPLSQLNode {
+
+
+ ASTStringLiteral(int id) {
+ super(id);
+ }
+
+
+ ASTStringLiteral(PLSQLParser p, int id) {
+ super(p, id);
+ }
+
+
+ @Override
+ public Object jjtAccept(PLSQLParserVisitor visitor, Object data) {
+ return visitor.visit(this, data);
+ }
+
+ /**
+ * Gets the plain string from the string literal.
+ * @return the plain string value from the string literal.
+ */
+ public String getString() {
+ String image = getImage();
+ if (image.charAt(0) == 'N' || image.charAt(0) == 'n') {
+ image = image.substring(1);
+ }
+
+ if (image.charAt(0) == '\'') {
+ image = image.substring(1, image.length() - 1);
+ } else if (image.charAt(0) == 'Q' || image.charAt(0) == 'q') {
+ image = image.substring("q'x".length(), image.length() - 2);
+ }
+ return image;
+ }
+}
diff --git a/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/MultipleDDLStatementsTest.java b/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/MultipleDDLStatementsTest.java
new file mode 100644
index 0000000000..cbd5a74497
--- /dev/null
+++ b/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/MultipleDDLStatementsTest.java
@@ -0,0 +1,29 @@
+/*
+ * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
+ */
+
+package net.sourceforge.pmd.lang.plsql.ast;
+
+import java.nio.charset.StandardCharsets;
+import java.util.List;
+
+import org.apache.commons.io.IOUtils;
+import org.junit.Assert;
+import org.junit.Test;
+
+import net.sourceforge.pmd.lang.plsql.AbstractPLSQLParserTst;
+
+public class MultipleDDLStatementsTest extends AbstractPLSQLParserTst {
+
+ @Test
+ public void parseDDLCommands() throws Exception {
+ String code = IOUtils.toString(this.getClass().getResourceAsStream("DDLCommands.sql"),
+ StandardCharsets.UTF_8);
+ ASTInput input = parsePLSQL(code);
+ List ddlcommands = input.findDescendantsOfType(ASTDDLCommand.class);
+ Assert.assertEquals(4, ddlcommands.size());
+ List comments = input.findDescendantsOfType(ASTComment.class);
+ Assert.assertEquals(3, comments.size());
+ Assert.assertEquals("'abbreviated job title'", comments.get(0).getFirstChildOfType(ASTStringLiteral.class).getImage());
+ }
+}
diff --git a/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/StringLiteralsTest.java b/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/StringLiteralsTest.java
new file mode 100644
index 0000000000..fcc7777e03
--- /dev/null
+++ b/pmd-plsql/src/test/java/net/sourceforge/pmd/lang/plsql/ast/StringLiteralsTest.java
@@ -0,0 +1,54 @@
+/**
+ * BSD-style license; for more info see http://pmd.sourceforge.net/license.html
+ */
+
+package net.sourceforge.pmd.lang.plsql.ast;
+
+import java.nio.charset.StandardCharsets;
+import java.util.List;
+
+import org.apache.commons.io.IOUtils;
+import org.junit.Assert;
+import org.junit.Test;
+
+import net.sourceforge.pmd.lang.plsql.AbstractPLSQLParserTst;
+
+public class StringLiteralsTest extends AbstractPLSQLParserTst {
+
+
+ @Test
+ public void parseStringLiterals() throws Exception {
+ String code = IOUtils.toString(this.getClass().getResourceAsStream("StringLiterals.pls"),
+ StandardCharsets.UTF_8);
+ ASTInput input = parsePLSQL(code);
+ List strings = input.findDescendantsOfType(ASTStringLiteral.class);
+ Assert.assertEquals(20, strings.size());
+
+ assertString("'Hello'", "Hello", 0, strings);
+ assertString("N'nchar literal'", "nchar literal", 4, strings);
+ assertString("nQ'[ab']cd]'", "ab']cd", 11, strings);
+ assertString("Q'{SELECT * FROM employees WHERE last_name = 'Smith';}'",
+ "SELECT * FROM employees WHERE last_name = 'Smith';", 13, strings);
+ assertString("q'{\n" + " also multiple\n" + " lines\n" + " }'",
+ "\n" + " also multiple\n" + " lines\n" + " ", 15, strings);
+ }
+
+ @Test
+ public void parseMultilineVarchar() throws Exception {
+ String code = IOUtils.toString(this.getClass().getResourceAsStream("MultilineVarchar.pls"),
+ StandardCharsets.UTF_8);
+ ASTInput input = parsePLSQL(code);
+ List strings = input.findDescendantsOfType(ASTStringLiteral.class);
+ Assert.assertEquals(1, strings.size());
+ Assert.assertTrue(normalizeEol(strings.get(0).getString()).startsWith("\ncreate or replace and"));
+ }
+
+ private static void assertString(String quoted, String plain, int index, List strings) {
+ Assert.assertEquals(quoted, normalizeEol(strings.get(index).getImage()));
+ Assert.assertEquals(plain, normalizeEol(strings.get(index).getString()));
+ }
+
+ private static String normalizeEol(String s) {
+ return s.replaceAll("\r\n|\n\r|\n|\r", "\n");
+ }
+}
diff --git a/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/DDLCommands.sql b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/DDLCommands.sql
new file mode 100644
index 0000000000..5833689339
--- /dev/null
+++ b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/DDLCommands.sql
@@ -0,0 +1,7 @@
+COMMENT ON COLUMN employees.job_id IS 'abbreviated job title';
+
+COMMENT ON COLUMN employees.job_id IS 'abbreviated job title';
+
+DROP TABLE employees;
+
+COMMENT ON COLUMN employees.job_id IS 'abbreviated job title';
diff --git a/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/MultilineVarchar.pls b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/MultilineVarchar.pls
new file mode 100644
index 0000000000..dad51aed4f
--- /dev/null
+++ b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/MultilineVarchar.pls
@@ -0,0 +1,37 @@
+--
+-- From https://github.com/pmd/pmd/pull/1988
+--
+declare
+
+ w_java_source clob := q'%
+create or replace and compile java source named PdfUtils as
+ /** BLOB encryption class using AES 128bit
+ * Load class to oracle db. Class file is on the oracle serever:
+ * sql script:
+ * exec sys.dbms_java.loadjava('-v -r /tsfa/tia7400/PdfPassword.class');
+ * command line:
+ * loadjava -user tia -resolve -verbose -r /tsfa/tia7400/PdfPassword.java
+ * dropjava -user tia -resolve -verbose -r /tsfa/tia7400/PdfPassword.java
+ */
+ /**
+ * Function reads input blob, encrypts and returns it to the caller
+ * @author Karol Wozniak
+ * @param secret password key
+ * @param fortuneBLOB blob var
+ * @return oracle.sql.BLOB
+ */
+ public static BLOB encryptPdf(String secret, Blob blobVar) throws Exception {
+ System.out.println("Start readBlob");
+ blobfile = writeToBlob(boas.toByteArray());
+ is.close();
+ reader.close();
+ System.out.println("encrypted using password " + secret);
+ System.out.println("End readBlob");
+ return blobfile;
+ }
+};
+%';
+
+begin
+ null;
+end;
\ No newline at end of file
diff --git a/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/StringLiterals.pls b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/StringLiterals.pls
new file mode 100644
index 0000000000..66118495ad
--- /dev/null
+++ b/pmd-plsql/src/test/resources/net/sourceforge/pmd/lang/plsql/ast/StringLiterals.pls
@@ -0,0 +1,45 @@
+--
+-- See https://github.com/pmd/pmd/issues/2008
+-- [plsql] In StringLiteral using alternative quoting mechanism single quotes cause parsing errors
+--
+-- https://docs.oracle.com/en/database/oracle/oracle-database/18/sqlrf/Literals.html#GUID-1824CBAA-6E16-4921-B2A6-112FB02248DA
+--
+
+declare
+
+ literal1 clob := 'Hello';
+ literal2 clob := 'ORACLE.dbs';
+ literal3 clob := 'Jackie''s raincoat';
+ literal4 clob := '09-MAR-98';
+ literal5 clob := N'nchar literal';
+
+ -- alternative quoting mechanism
+ qliteral1a clob := q'[abc]';
+ qliteral1b clob := q'[ab']cd]';
+ qliteral1c clob := q'[ab[cd]';
+ qliteral1d clob := q'[ab]cd]';
+ qliteral1e clob := q'[ab
+ cd]';
+ qliteral1f clob := Nq'[a"b"c]';
+ qliteral1g clob := nQ'[ab']cd]';
+
+ qliteral1 clob := q'!name LIKE '%DBMS_%%'!';
+ qliteral2 clob := Q'{SELECT * FROM employees WHERE last_name = 'Smith';}';
+ qliteral1a clob := q'! test !';
+ qliteral2a clob := q'{
+ also multiple
+ lines
+ }';
+ qliteral3a clob := q'% test abc %';
+ qliteral3b clob := q'% test % abc %';
+
+
+ qliteral3c clob := q'% test'test %';
+ qliteral4 clob := nq'!name LIKE '%DBMS_%%'!';
+
+
+
+begin
+ null;
+end;
+/
diff --git a/pmd-python/pom.xml b/pmd-python/pom.xml
index 37cecb5d6b..92b9798e44 100644
--- a/pmd-python/pom.xml
+++ b/pmd-python/pom.xml
@@ -34,7 +34,7 @@
-
+
diff --git a/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/ScalaRuleTest.java b/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/ScalaRuleTest.java
index e3d0b2fd37..8c7cc39599 100644
--- a/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/ScalaRuleTest.java
+++ b/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/ScalaRuleTest.java
@@ -19,8 +19,8 @@ import net.sourceforge.pmd.Report;
import net.sourceforge.pmd.Rule;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.RuleSet;
-import net.sourceforge.pmd.RuleSetFactory;
import net.sourceforge.pmd.RuleSets;
+import net.sourceforge.pmd.RulesetsFactoryUtils;
import net.sourceforge.pmd.internal.util.IteratorUtil;
import net.sourceforge.pmd.lang.LanguageRegistry;
import net.sourceforge.pmd.lang.LanguageVersionHandler;
@@ -77,7 +77,7 @@ public class ScalaRuleTest {
Report report = new Report();
ctx.setReport(report);
ctx.setSourceCodeFile(new File("test.scala"));
- RuleSet rules = new RuleSetFactory().createSingleRuleRuleSet(r);
+ RuleSet rules = RulesetsFactoryUtils.defaultFactory().createSingleRuleRuleSet(r);
p.getSourceCodeProcessor().processSourceCode(new StringReader(test), new RuleSets(rules), ctx);
return report;
}
diff --git a/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/XPathRuleTest.java b/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/XPathRuleTest.java
index 31de1124f4..5c64d291df 100644
--- a/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/XPathRuleTest.java
+++ b/pmd-scala/src/test/java/net/sourceforge/pmd/lang/scala/rule/XPathRuleTest.java
@@ -19,9 +19,9 @@ import net.sourceforge.pmd.Report;
import net.sourceforge.pmd.Rule;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.RuleSet;
-import net.sourceforge.pmd.RuleSetFactory;
import net.sourceforge.pmd.RuleSets;
import net.sourceforge.pmd.RuleViolation;
+import net.sourceforge.pmd.RulesetsFactoryUtils;
import net.sourceforge.pmd.lang.LanguageRegistry;
import net.sourceforge.pmd.lang.rule.XPathRule;
import net.sourceforge.pmd.lang.rule.xpath.XPathRuleQuery;
@@ -57,7 +57,7 @@ public class XPathRuleTest extends RuleTst {
Report report = new Report();
ctx.setReport(report);
ctx.setSourceCodeFile(new File("test.scala"));
- RuleSet rules = new RuleSetFactory().createSingleRuleRuleSet(r);
+ RuleSet rules = RulesetsFactoryUtils.defaultFactory().createSingleRuleRuleSet(r);
p.getSourceCodeProcessor().processSourceCode(new StringReader(test), new RuleSets(rules), ctx);
return report;
}
diff --git a/pmd-test/src/main/java/net/sourceforge/pmd/AbstractLanguageVersionTest.java b/pmd-test/src/main/java/net/sourceforge/pmd/AbstractLanguageVersionTest.java
index ff5343edb3..c9984f1b0b 100644
--- a/pmd-test/src/main/java/net/sourceforge/pmd/AbstractLanguageVersionTest.java
+++ b/pmd-test/src/main/java/net/sourceforge/pmd/AbstractLanguageVersionTest.java
@@ -141,7 +141,7 @@ public class AbstractLanguageVersionTest {
String rulesetFilenames = props.getProperty("rulesets.filenames");
assertNotNull(rulesetFilenames);
- RuleSetFactory factory = new RuleSetFactory();
+ RuleSetFactory factory = RulesetsFactoryUtils.defaultFactory();
if (rulesetFilenames.trim().isEmpty()) {
return;
diff --git a/pmd-test/src/main/java/net/sourceforge/pmd/AbstractRuleSetFactoryTest.java b/pmd-test/src/main/java/net/sourceforge/pmd/AbstractRuleSetFactoryTest.java
index 16f9f85c25..752fe19afd 100644
--- a/pmd-test/src/main/java/net/sourceforge/pmd/AbstractRuleSetFactoryTest.java
+++ b/pmd-test/src/main/java/net/sourceforge/pmd/AbstractRuleSetFactoryTest.java
@@ -261,7 +261,7 @@ public abstract class AbstractRuleSetFactoryTest {
}
private RuleSet loadRuleSetByFileName(String ruleSetFileName) throws RuleSetNotFoundException {
- RuleSetFactory rsf = new RuleSetFactory();
+ RuleSetFactory rsf = RulesetsFactoryUtils.defaultFactory();
return rsf.createRuleSet(ruleSetFileName);
}
@@ -360,7 +360,7 @@ public abstract class AbstractRuleSetFactoryTest {
// System.out.println("xml2: " + xml2);
// Read RuleSet from XML, first time
- RuleSetFactory ruleSetFactory = new RuleSetFactory();
+ RuleSetFactory ruleSetFactory = RulesetsFactoryUtils.defaultFactory();
RuleSet ruleSet2 = ruleSetFactory.createRuleSet(createRuleSetReferenceId(xml2));
// Do write/read a 2nd time, just to be sure
diff --git a/pmd-test/src/main/java/net/sourceforge/pmd/testframework/PMDTestRunner.java b/pmd-test/src/main/java/net/sourceforge/pmd/testframework/PMDTestRunner.java
index 0f9b6d310f..a0e05007bf 100644
--- a/pmd-test/src/main/java/net/sourceforge/pmd/testframework/PMDTestRunner.java
+++ b/pmd-test/src/main/java/net/sourceforge/pmd/testframework/PMDTestRunner.java
@@ -66,7 +66,7 @@ public class PMDTestRunner extends Runner implements Filterable, Sortable {
try {
unitTests.filter(filter);
} catch (NoTestsRemainException e) {
- noUnitTests = false;
+ noUnitTests = true;
}
if (noRuleTests && noUnitTests) {
diff --git a/pmd-test/src/main/java/net/sourceforge/pmd/testframework/RuleTst.java b/pmd-test/src/main/java/net/sourceforge/pmd/testframework/RuleTst.java
index 0522d5238b..d134ebe6c1 100644
--- a/pmd-test/src/main/java/net/sourceforge/pmd/testframework/RuleTst.java
+++ b/pmd-test/src/main/java/net/sourceforge/pmd/testframework/RuleTst.java
@@ -41,10 +41,10 @@ import net.sourceforge.pmd.Report;
import net.sourceforge.pmd.Rule;
import net.sourceforge.pmd.RuleContext;
import net.sourceforge.pmd.RuleSet;
-import net.sourceforge.pmd.RuleSetFactory;
import net.sourceforge.pmd.RuleSetNotFoundException;
import net.sourceforge.pmd.RuleSets;
import net.sourceforge.pmd.RuleViolation;
+import net.sourceforge.pmd.RulesetsFactoryUtils;
import net.sourceforge.pmd.lang.Language;
import net.sourceforge.pmd.lang.LanguageRegistry;
import net.sourceforge.pmd.lang.LanguageVersion;
@@ -101,7 +101,7 @@ public abstract class RuleTst {
*/
public Rule findRule(String ruleSet, String ruleName) {
try {
- Rule rule = new RuleSetFactory().createRuleSets(ruleSet).getRuleByName(ruleName);
+ Rule rule = RulesetsFactoryUtils.defaultFactory().createRuleSets(ruleSet).getRuleByName(ruleName);
if (rule == null) {
fail("Rule " + ruleName + " not found in ruleset " + ruleSet);
} else {
@@ -282,7 +282,7 @@ public abstract class RuleTst {
ctx.setSourceCodeFile(new File("n/a"));
ctx.setLanguageVersion(languageVersion);
ctx.setIgnoreExceptions(false);
- RuleSet rules = new RuleSetFactory().createSingleRuleRuleSet(rule);
+ RuleSet rules = RulesetsFactoryUtils.defaultFactory().createSingleRuleRuleSet(rule);
p.getSourceCodeProcessor().processSourceCode(new StringReader(code), new RuleSets(rules), ctx);
} catch (Exception e) {
throw new RuntimeException(e);
diff --git a/pmd-visualforce/pom.xml b/pmd-visualforce/pom.xml
index 2df2b60785..3a00d97ae3 100644
--- a/pmd-visualforce/pom.xml
+++ b/pmd-visualforce/pom.xml
@@ -40,7 +40,7 @@
-
+
diff --git a/pmd-vm/pom.xml b/pmd-vm/pom.xml
index 2ec5f0b9ac..f8effb5cf7 100644
--- a/pmd-vm/pom.xml
+++ b/pmd-vm/pom.xml
@@ -40,7 +40,7 @@
-
+
diff --git a/pom.xml b/pom.xml
index f422e593ae..75144d261d 100644
--- a/pom.xml
+++ b/pom.xml
@@ -107,6 +107,7 @@ Objective-C, Perl, PHP, PLSQL, Python, Ruby, Salesforce.com Apex, Scala, Swift a
5
6.19.0
+ ${settings.localRepository}/net/java/dev/javacc/javacc/${javacc.version}/javacc-${javacc.version}.jar