Issue Details (XML | Word | Printable)

Key: JDBC-632
Type: Bug Bug
Status: Closed Closed
Resolution: Fixed
Priority: Major Major
Assignee: Mark Rotteveel
Reporter: Anton Shchyrov
Votes: 0
Watchers: 0
Operations

If you were logged in you would be able to see more operations.
Jaybird JDBC Driver

Case sensitivity first letter in escape clause

Created: 11/Aug/20 12:45 PM   Updated: 17/Jan/21 09:46 AM
Component/s: JDBC driver
Affects Version/s: Jaybird 3.0.7, Jaybird 3.0.8, Jaybird 4.0.0, Jaybird 3.0.9, Jaybird 4.0.1
Fix Version/s: Jaybird 3.0.10, Jaybird 4.0.2, Jaybird 5


 Description  « Hide
When I try to create an object using escape syntax, provided the keyword is in uppercase, I get the exception

org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C

Code
try (Connection con = DriverManager.getConnection("jdbc:firebirdsql:localhost/3050:c:/db/employee.fdb", "SYSDBA", "masterkey")) {
  CallableStatement stmt = con.prepareCall("{CALL sp_test(?)}");
  stmt.close();
}

Call stack

Exception in thread "main" org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C
at org.firebirdsql.jdbc.escape.FBEscapedParser$ParserState$4.nextState(FBEscapedParser.java:461)
at org.firebirdsql.jdbc.escape.FBEscapedParser.parse(FBEscapedParser.java:114)
at org.firebirdsql.jdbc.FBConnection.nativeSQL(FBConnection.java:330)
at org.firebirdsql.jdbc.FBStatement.nativeSQL(FBStatement.java:904)
at org.firebirdsql.jdbc.AbstractCallableStatement.<init>(AbstractCallableStatement.java:80)
at org.firebirdsql.jdbc.FBCallableStatement.<init>(FBCallableStatement.java:43)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:811)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:777)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:297)
at test.DBTest.main(DBTest.java:10)


The problem is in method nextState of class ESCAPE_ENTER_STATE

ESCAPE_ENTER_STATE {
  protected FBEscapedParser.ParserState nextState(char inputChar) throws FBSQLParseException {
    switch(inputChar) {
      case '?':
      case 'c':
      case 'd':
      case 'e':
      case 'f':
      case 'l':
      case 'o':
      case 't':
        return NORMAL_STATE;
      default:
        throw new FBSQLParseException("Unexpected first character inside JDBC escape: " + inputChar);
    }
  }
}

This method assumes that the first letter of the keyword should be written in lowercase. Although later, when converting the escape command to native code, there is a forced conversion to lowercase

public final class FBEscapedParser {
    ...............
    private void escapeToNative(StringBuilder target, String escaped) throws SQLException {
        StringBuilder keyword = new StringBuilder();
        StringBuilder payload = new StringBuilder(Math.max(16, escaped.length()));
        this.processEscaped(escaped, keyword, payload);
        String keywordStr = keyword.toString().toLowerCase();

as a consequence, this code works

CallableStatement stmt = con.prepareCall("{сALL sp_test(?)}");
(first letter in lower case)


 All   Comments   Change History   Subversion Commits      Sort Order: Ascending order - Click to sort in descending order
Mark Rotteveel made changes - 11/Aug/20 03:02 PM
Field Original Value New Value
Fix Version/s Jaybird 3.0.10 [ 10932 ]
Fix Version/s Jaybird 4.0.2 [ 10950 ]
Fix Version/s Jaybird 5 [ 10871 ]
Affects Version/s Jaybird 4.0.1 [ 10921 ]
Affects Version/s Jaybird 3.0.9 [ 10917 ]
Affects Version/s Jaybird 3.0.8 [ 10916 ]
Affects Version/s Jaybird 3.0.7 [ 10910 ]
Description When I try to create an object using escape syntax, provided the keyword is in uppercase, I get the exception

{quote}
org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C
{quote}

Code

{code:java}
try (Connection con = DriverManager.getConnection("jdbc:firebirdsql:localhost/3050:c:/db/employee.fdb", "SYSDBA", "masterkey")) {
  CallableStatement stmt = con.prepareCall("{CALL sp_test(?)}");
  stmt.close();
}
{code}
Call stack
{code}
Exception in thread "main" org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C
at org.firebirdsql.jdbc.escape.FBEscapedParser$ParserState$4.nextState(FBEscapedParser.java:461)
at org.firebirdsql.jdbc.escape.FBEscapedParser.parse(FBEscapedParser.java:114)
at org.firebirdsql.jdbc.FBConnection.nativeSQL(FBConnection.java:330)
at org.firebirdsql.jdbc.FBStatement.nativeSQL(FBStatement.java:904)
at org.firebirdsql.jdbc.AbstractCallableStatement.<init>(AbstractCallableStatement.java:80)
at org.firebirdsql.jdbc.FBCallableStatement.<init>(FBCallableStatement.java:43)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:811)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:777)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:297)
at test.DBTest.main(DBTest.java:10)
{code}

The problem is in method nextState of class ESCAPE_ENTER_STATE

{code:java}
ESCAPE_ENTER_STATE {
  protected FBEscapedParser.ParserState nextState(char inputChar) throws FBSQLParseException {
    switch(inputChar) {
      case '?':
      case 'c':
      case 'd':
      case 'e':
      case 'f':
      case 'l':
      case 'o':
      case 't':
        return NORMAL_STATE;
      default:
        throw new FBSQLParseException("Unexpected first character inside JDBC escape: " + inputChar);
    }
  }
}{code}

This method assumes that the first letter of the keyword should be written in lowercase. Although later, when converting the escape command to native code, there is a forced conversion to lowercase

{code:java}
public final class FBEscapedParser {
    ...............
    private void escapeToNative(StringBuilder target, String escaped) throws SQLException {
        StringBuilder keyword = new StringBuilder();
        StringBuilder payload = new StringBuilder(Math.max(16, escaped.length()));
        this.processEscaped(escaped, keyword, payload);
        String keywordStr = keyword.toString().toLowerCase();
{code}
as a consequence, this code works
{code}
CallableStatement stmt = con.prepareCall("{сALL sp_test(?)}");
{code}(first letter in lower case)
When I try to create an object using escape syntax, provided the keyword is in uppercase, I get the exception

org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C

Code
try (Connection con = DriverManager.getConnection("jdbc:firebirdsql:localhost/3050:c:/db/employee.fdb", "SYSDBA", "masterkey")) {
  CallableStatement stmt = con.prepareCall("{CALL sp_test(?)}");
  stmt.close();
}

Call stack

Exception in thread "main" org.firebirdsql.jdbc.escape.FBSQLParseException: Unexpected first character inside JDBC escape: C
at org.firebirdsql.jdbc.escape.FBEscapedParser$ParserState$4.nextState(FBEscapedParser.java:461)
at org.firebirdsql.jdbc.escape.FBEscapedParser.parse(FBEscapedParser.java:114)
at org.firebirdsql.jdbc.FBConnection.nativeSQL(FBConnection.java:330)
at org.firebirdsql.jdbc.FBStatement.nativeSQL(FBStatement.java:904)
at org.firebirdsql.jdbc.AbstractCallableStatement.<init>(AbstractCallableStatement.java:80)
at org.firebirdsql.jdbc.FBCallableStatement.<init>(FBCallableStatement.java:43)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:811)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:777)
at org.firebirdsql.jdbc.FBConnection.prepareCall(FBConnection.java:297)
at test.DBTest.main(DBTest.java:10)


The problem is in method nextState of class ESCAPE_ENTER_STATE

ESCAPE_ENTER_STATE {
  protected FBEscapedParser.ParserState nextState(char inputChar) throws FBSQLParseException {
    switch(inputChar) {
      case '?':
      case 'c':
      case 'd':
      case 'e':
      case 'f':
      case 'l':
      case 'o':
      case 't':
        return NORMAL_STATE;
      default:
        throw new FBSQLParseException("Unexpected first character inside JDBC escape: " + inputChar);
    }
  }
}

This method assumes that the first letter of the keyword should be written in lowercase. Although later, when converting the escape command to native code, there is a forced conversion to lowercase

public final class FBEscapedParser {
    ...............
    private void escapeToNative(StringBuilder target, String escaped) throws SQLException {
        StringBuilder keyword = new StringBuilder();
        StringBuilder payload = new StringBuilder(Math.max(16, escaped.length()));
        this.processEscaped(escaped, keyword, payload);
        String keywordStr = keyword.toString().toLowerCase();

as a consequence, this code works

CallableStatement stmt = con.prepareCall("{сALL sp_test(?)}");
(first letter in lower case)
Mark Rotteveel made changes - 11/Aug/20 03:33 PM
Summary Case sensativity firs letter in escape clause Case sensitivity first letter in escape clause
Mark Rotteveel made changes - 11/Aug/20 03:50 PM
Status Open [ 1 ] Resolved [ 5 ]
Resolution Fixed [ 1 ]
Mark Rotteveel made changes - 17/Jan/21 09:46 AM
Status Resolved [ 5 ] Closed [ 6 ]