@Override
    public void setGemPaths(final String gemHome, final String gemPath) throws JRubyInvalidRuntimeException {
        final String[] gemArgs;

        // An empty string in GEM_PATH is still effective as GEM_PATH.
        // https://svn.ruby-lang.org/cgi-bin/viewvc.cgi/tags/v2_6_2/lib/rubygems/path_support.rb?revision=67232&view=markup#l34
        // https://svn.ruby-lang.org/cgi-bin/viewvc.cgi/tags/v2_6_2/lib/rubygems/path_support.rb?revision=67232&view=markup#l51
        if (gemPath != null) {
            // It is believed that Ruby's File::PATH_SEPARATOR is the same with Java's File.pathSeparator.
            // https://github.com/jruby/jruby/blob/9.2.6.0/core/src/main/java/org/jruby/RubyFile.java#L122-L125
            final String[] gemPaths = gemPath.split("\\" + File.pathSeparator);
            gemArgs = new String[gemPaths.length + 1];
            gemArgs[0] = gemHome;
            for (int i = 0; i < gemPaths.length; ++i) {
                gemArgs[i + 1] = gemPaths[i];
            }
        } else {
            gemArgs = new String[2];
            if (gemHome != null) {
                gemArgs[0] = gemHome;
                gemArgs[1] = gemHome;
            } else {
                gemArgs[0] = null;
                gemArgs[1] = null;
            }
        }

        this.callMethodArray(this.runScriptlet("Gem"), "use_paths", gemArgs);
    }
Indirects onto JRuby not to require JRuby classes directly.

It calls methods of ScriptingContainer through reflection.

This trick enables Embulk:

<ul>
<li>To load a JRuby runtime (jruby-complete-*.jar) specified at runtime out of embulk-*.jar.
<li>To switch versions of JRuby without releasing or repackaging.
<li>To distribute Embulk without JRuby runtimes embedded.
</ul>
embulk-core/src/main/java/org/embulk/jruby/ScriptingContainerDelegateImpl.java