Best approach for porting an existing Java library to Ruby (JRuby)

I am looking to post a ruby ​​(JRuby) wrapper over a medium-sized Java library, and I am looking for tips and articles on best practices for everything from packaging to strategy.

I found a relatively dated (2009) discussion on this topic here: http://www.ruby-forum.com/topic/188447 .

I want to use the latest version of JRuby.

+8
java jruby
source share
2 answers

I wrote several shells for the Java libraries ( Eurydice , HotBunnies , MessagePack , Rubydoop, and Mikka , among others). Some of them are just JRuby code that adapts the Java library, and some of them include Java code that interacts with the JRuby runtime ( MessagePack is actually written entirely in Java).

What I found is not very well decided - how to send a JAR file for the Java library. You do not want to include it in the gem, because in the end you will end up in JAR hell. Shared Java libraries such as Netty will be merged into many gems, and you will end up with gems that combine incompatible versions. I solved this problem with packing stones that only contain the JAR library (see, for example, scala-library-jars and ning-compress-jars ), and then my shell depends on this gem. This is not a very scalable solution, but at least it will be more manageable than if you bound the JAR in a wrapper shell.

In your question it is not clear what exactly you want to know, I suggest you review and clarify. However, here are a few random things from your head.

  • A quick way to make the Java API more accessible for Ruby is to add methods to Java classes and interfaces. It's as simple as opening a Ruby class (but Java interfaces are modules) and can greatly simplify working with Java objects in Ruby. These methods will only be visible to Ruby; they will not be visible in Java code.
  • Not java_import to global scope. This will cause a lot of trouble for everyone. Remember that java_import not like import in Java, where it is only local to the file, it actually creates an alias in the scope. Wrap java_import and include_package in modules.
  • Do not use import - it is incompatible with Rake.
+7
source share

Wiki page: JRuby's Java script (jruby 1.0+) contains great tips and ideas that you can use to get your wrapper

It seems interesting to me to use the module name to access the access area of ​​the imported Java class

Example: create a Ruby Module called JavaLangDemo, which includes classes in the Java package java.lang.

  module JavaLangDemo include_package "java.lang" # alternately, use the #import method import "java.lang" end 

Now you can prefix the desired Java class name with JavaLangDemo :: to access the included classes:

  version = JavaLangDemo::System.getProperties["java.runtime.version"] => "1.5.0_13-b05-237" processors = JavaLangDemo::Runtime.getRuntime.availableProcessors => 2 

The article also describes the following topics:

  • implementation of the Java interface in Ruby
  • Class Name Uncertainty Between Java and Ruby
  • "mixing" multiple Java interfaces with Jruby modules in JRuby
  • Exception Handling
  • Object synchronization for thread safety

and contains a list of useful links to "Related Articles" for more information on the Java Integration Level

+3
source share

All Articles