rubyjrubywarblerjdbc-postgres

JRuby - jdbc-postgres no suitable driver found for jdbc:postgresql when running from JAR


I am getting a 'No suitable driver found' error when running my jar generated with warbler. However when I run it as ruby the code succeeds. The command to load the driver returns true, leading me to believe it can still load the driver while in the jar. However I am unable to figure out why DriverManager.get_connection is erroring with No driver found. Especially since when running from Ruby it succeeds.

Ruby function being called

def self.connect(opts)
    connection = nil
    begin
      driver = Jdbc::PostgreSQL.load_driver

      connection = DriverManager.get_connection("jdbc:postgresql://host:port/postgres", opts[:username], opts[:password])
      connection.auto_commit = false
    rescue
       puts $!, $@
       ... 
    end
    connection
  end

Running Ruby

Test Connection Succeeded

Running JAR

No suitable driver found for jdbc:postgresql://host:port/postgres java.sql.DriverManager.getConnection(DriverManager.java:602) java.sql.DriverManager.getConnection(DriverManager.java:185)

warbler.rb

Gems to include

config.gems += ["trollop", "builder", "jdbc-postgres"]

Ruby imports

require, java_import

# All support libraries required to be included
[
  'java',
  'ostruct',
  'trollop',
  'logger',
  'fileutils',
  'yaml',
  'jdbc/postgres'
].each do |require_name|
  require require_name
end


 # All java imported namespaces
    [
        'java.sql.DriverManager'
    ].each do |namespace|
      java_import namespace
    end

It seems like something is not making it into the JAR which is causing the failure. Any suggestions would be greatly appreciated.


Solution

  • I got this working by removing the jdbc-postgres Gem, then specifically including the PostgreSQL JDBC JAR. I extracted the relative parts and left out the general error handling and functions.

    require postgresql-9.3-1101.jdbc4.jar
    
    Java::JavaClass.for_name "org.postgresql.Driver"
    Java::JavaClass.for_name "java.util.Properties"
    
    props = java.util.Properties.new
    props.set_property :user, opts[:username]
    props.set_property :password, opts[:password]
    
    connection = org.postgresql.Driver.new.connect(get_jdbcurl(opts), props)