Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Parameter order in connection string makes a difference #1853

Closed
Chrriis opened this issue Jun 24, 2022 · 3 comments
Closed

Parameter order in connection string makes a difference #1853

Chrriis opened this issue Jun 24, 2022 · 3 comments
Projects
Milestone

Comments

@Chrriis
Copy link

Chrriis commented Jun 24, 2022

Driver version

11.1.2

Problem description

When creating report for bug #1852, I simplified my my properties by putting them all into the connection string. I noticed that certain connections were not working depending on the order of parameters.

Here is a standalone test case that illustrate the problem, switching the first 2 parameters:

public class TestMsSqlJdbcConnectionStringParameterOrder {
    public static void main(String[] args) throws Exception {
        Class.forName(com.microsoft.sqlserver.jdbc.SQLServerDriver.class.getName());
        String connectionString1 = "jdbc:sqlserver://databaseName=xxxxx;serverName=localhost;userName=xxxxx;password=xxxxx;instanceName=SQLEXPRESS;packetSize=16384;prepareMethod=prepare;trustServerCertificate=true";
        String connectionString2 = "jdbc:sqlserver://serverName=localhost;databaseName=xxxxx;userName=xxxxx;password=xxxxx;instanceName=SQLEXPRESS;packetSize=16384;prepareMethod=prepare;trustServerCertificate=true";
        try {
            Connection conn = DriverManager.getConnection(connectionString1);
            conn.close();
            System.out.println("Connection 1: OK");
        } catch (SQLException e) {
            System.out.println("Connection 1: FAILED");
            e.printStackTrace();
        }
        try {
            Connection conn = DriverManager.getConnection(connectionString2);
            conn.close();
            System.out.println("Connection 2: OK");
        } catch (SQLException e) {
            System.out.println("Connection 2: FAILED");
            e.printStackTrace();
        }
    }
}

Simply replace the "xxxxx" by real data. The first call prints OK, the second call fails with "java.net.UnknownHostException: serverName=localhost" after a timeout of about 15s.

@tkyc
Copy link
Member

tkyc commented Jun 24, 2022

Hey @Chrriis that is strange. I recall from an example I saw (trying to find it again, it's been awhile), when explicitly defining all the connection properties like you have eg. jdbc:sqlserver://<prop>=<value>;......, you need to include a ; in front of the initial property like so jdbc:sqlserver://;serverName=localhost;..... I was able to connect using connectionString2 after making this change. It's weird that it wasn't the case for connectionString1. Definitely something is inconsistent here.

I'll need to look into this some more.

@Chrriis
Copy link
Author

Chrriis commented Jun 24, 2022

Another kind of URL which works and that seems more natural is with a ? e.g. jdbc:sqlserver://?serverName=localhost;... which happens to be the syntax I originally used when reporting #1852. I used that syntax in my code when I first tried this driver (more than 2 years ago) and a few days ago when giving it another try.
This syntax is more natural because it looks like a regular URL with parameters in the query string. Unfortunately, the bug also occurs with this syntax...

@tkyc
Copy link
Member

tkyc commented Jun 27, 2022

Just an update after some further investigation. It looks like it is absolutely necessary to have a delimiting ; before and after a connection property eg. ;property=value;. In the case of connectionString1, it succeeds but the databaseName property is never parsed. if any other property, like loginTimeout was leading in the connection string and was not delimited with ; in front as well, it would also not be parsed but the connection would still succeed. So it seems the bug is that we're not erroring out in such cases.

In the case of connection string 2, it errored out because since serverName was leading without a ; in front it was never parsed and without a serverName the connection failed.

The reason we need the ; in front of the first property is because right after jdbc:sqlserver:// is where server name is expected (not serverName=value).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
MSSQL JDBC
  
Closed Issues
Development

No branches or pull requests

3 participants