Software7

Personal Developer Notebook

MySQL JDBC Driver Licensing

I’m writing an application for a client. The software should support different database backends but should be designed database agnostic. This facilitates selling the software to companies who already have a specific database in use.

For the developer that means reading the licenses of the different database drivers. Among the databases to support is MySQL.

In early versions of MySQL the corresponding JDBC driver was available under LGPL, which allowed the use in a commercial closed source application. It seems that changed with version 4 (unnoticed by me). Meanwhile the MySQL JDBC driver ‘MySQL Connector/J’ is offered under a dual license model with a commercial and an open source variant (GPL 2 with FOSS License Exception).

That means if you want to embed the the Connector/J JDBC driver into your application, you need either to

  • make your whole application open source, or
  • buy a commercial license, or
  • use a different driver.

I didn’t find an official price list, but as I read on different sites the licensing costs are rather high for what we wanted, at least several thousands dollars. As far as I understand you can then also embed the MySQL database, but we only wanted the ability to use different database backends and not to bundle a database itself.

Forked from the popular MySQL database there is Drizzle, optimized for Cloud infrastructure and Web applications. They also offer the Drizzle-JDBC driver, a driver for both Drizzle and MySQL. It is published under the BSD license, which allows embedding the driver into a closed source commercial application.

It can be downloaded here:

http://www.drizzle.org/content/download{.broken_link}

One hint if you want to go that road: for common connection, access right, or configuration problems it’s not a good idea to show a raw exception to the end user. Since such checks are not part of the JDBC API this usually means to parse exceptions texts (unfortunately with all the associated drawbacks). Intensive testing with different client/server configurations brought up situations with a rather unusual exception if there are access right problem.

Caused by:  java.nio.BufferUnderflowException
	    at java.nio.Buffer.nextGetIndex(Buffer.java:480)
	    at java.nio.HeapByteBuffer.getInt(HeapByteBuffer.java:336)
	    at org.drizzle.jdbc.internal.common.packet.buffer.Reader.readInt(Reader.java:80)
	    at org.drizzle.jdbc.internal.mysql.packet.MySQLGreetingReadPacket.<init>(MySQLGreetingReadPacket.java:54)
	    at org.drizzle.jdbc.internal.mysql.MySQLProtocol.<init>(MySQLProtocol.java:159)
	    at org.drizzle.jdbc.DrizzleDriver.connect(DrizzleDriver.java:88)
	    ...

A check for such a situation could look like:

private boolean isMySQLAccessProblem(Exception exception)
    {
        boolean isMySQLAccessProblem = false;
        if(exception.getMessage() != null) {
            Pattern pattern1 = Pattern.compile(".*Access denied for user.*", Pattern.DOTALL);
            Matcher matcher1 = pattern1.matcher(exception.getMessage());
            isMySQLAccessProblem = matcher1.matches();
        }
        
        if(!isMySQLAccessProblem) {
            Pattern pattern2 = Pattern.compile(".*Buffer.nextGetIndex.*Reader.readInt.*MySQLGreetingReadPacket.*", Pattern.DOTALL);
            Matcher matcher2 = pattern2.matcher(ExceptionUtil.exceptionAsText(exception));
            isMySQLAccessProblem = matcher2.matches();
        }

        return isMySQLAccessProblem;
    }