Why does jruby-openssl gem have strange folder structure?

497 views Asked by At

From my understanding, a gem's folder structer is supposed to have a folder called lib and inside that folder have a <gem-name>.rb file. However, when I used jruby 1.6.8 and do bundle install to install jruby-openssl, I open up C:\jruby-1.6.8\lib\ruby\gems\1.8\gems\jruby-openssl-0.8.2 and instead of seeing an rb file, I see more sub folders that look like this:

jruby-openssl-0.8.2\
+---lib\
|   +---1.8\
|   |   +---openssl\
|   |   +---openssl.rb
|   +---1.9\
|   |   +---openssl\
|   |   +---openssl.rb
|   +---ruby\
|   |   +---shared\
|   +---shared\
|       +---jopenssl\
|       +---openssl\
|       +---openssl.rb
+---test\
    +---java\

Is there a reason that jruby-openssl isn't following the standard gem folder structure? Specifically, I seem to be having trouble with a gem 'jruby-openssl' command working. Should the gem command find and load the gem correctly if the jruby-openssl folder is in the LOAD_PATH?



ERROR DETAILS:

Here is the error that appears in C:\apachetomcat632\logs\MyWebapp.log

--- Backtrace
LoadError: OpenSSL::Cipher requires the jruby-openssl gem
            (root) at file:/C:/apachetomcat632/shared/lib/jruby-complete.jar!/META-INF/jruby.home/lib/ruby/site_ruby/shared/jruby/openssl/autoloads/cipher.rb:8
  MessageEncryptor at file:/C:/apachetomcat632/shared/lib/jruby-complete.jar!/META-INF/jruby.home/lib/ruby/site_ruby/shared/jruby/openssl/autoloads/cipher.rb:24
     ActiveSupport at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/message_encryptor.rb:12
            (root) at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/message_encryptor.rb:4
           require at org/jruby/RubyKernel.java:1062
           require at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/dependencies.rb:251
   load_dependency at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/dependencies.rb:236
           require at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/dependencies.rb:251
   eager_autoload! at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/message_encryptor.rb:43
              each at org/jruby/RubyArray.java:1620
   eager_autoload! at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/activesupport-3.2.11/lib/active_support/dependencies/autoload.rb:43
         Bootstrap at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/application/bootstrap.rb:20
     instance_exec at org/jruby/RubyKernel.java:2091
               run at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/initializable.rb:30
  run_initializers at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/initializable.rb:55
              each at org/jruby/RubyArray.java:1620
  run_initializers at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/initializable.rb:54
       initialize! at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/application.rb:136
              send at org/jruby/RubyKernel.java:2105
    method_missing at file:C:/apachetomcat632/shared/lib/cfe-gems.jar!/gems/railties-3.2.11/lib/rails/railtie/configurable.rb:30
            (root) at C:/apachetomcat632/webapps/Bank62P/WEB-INF/rails/config/environment.rb:5
           require at org/jruby/RubyKernel.java:1062
  load_environment at C:/apachetomcat632/webapps/Bank62P/WEB-INF/rails/config/environment.rb:23
  load_environment at file:/C:/apachetomcat632/shared/lib/jruby-rack.jar!/jruby/rack/rails_booter.rb:65
            (root) at <script>:1

And here is entire cipher.rb file:

require 'rubygems'

# try to activate jruby-openssl gem for OpenSSL::SSL, raising error if gem not present
begin
  gem 'jruby-openssl'
  require 'openssl.rb'
rescue Gem::LoadError => e
  raise LoadError.new("OpenSSL::Cipher requires the jruby-openssl gem")
end
2

There are 2 answers

1
Kelvin On BEST ANSWER

To add to tadman's answer, if you look in the gemspec (gems/1.8/specifications/jruby-openssl-0.8.2.gemspec), you'll see this line:

s.require_paths = ["lib/shared"]

When you require 'openssl' in your code, it'll load the one in the shared dir. I believe that file will determine whether to load the 1.8 or 1.9 version.

With that said...

When I try to require 'openssl' with 0.8.2, I get an error:

LoadError: no such file to load -- openssl/dummy

When I use the latest (0.8.8) it works fine. Try upgrading.

0
tadman On

Prior to version 1.7.0 of JRuby, 1.9 support was so incomplete that you'd be better off using 1.8 code. This is probably why there needs to be two separate implementations of that particular library.

Bundling them together like this is a little unusual, often 1.8 installations will just lock to an older version of the gem. JRuby presents a challenge here, and this looks like a fairly reasonable solution.