Hi, This is my take on the problem - If we register a URL handler, it will handle all cases. And it will not require any changes to JRuby itself. Consider this scenario. The URL created looks like this:
bundleresource://9/./some_script.rb This URL is being dealt with inside JRuby. When JRuby tries to access this URL using the usual approach of url.openConnection() or url.getContents(), the actual work is passed to the URL handler registered for the protocol returned by url.getProtocol() which is 'bundleresource'. When not in equinox, there will be no registered protocol handler, so these URL's are invalid and will not work, which is correct behaviour, as JRuby should have no knowledge of equinox. However, when inside equinox, the JVM search for a protocol handler for 'bundleresource' should succeed if the classloaders are correctly setup, as described in http://wiki.eclipse.org/index.php/Context_Class_Loader_Enhancements. Then what will happen is the JVM will pass the thread that called url.openConnection() to the equinox bundle URL handler, which will be able to understand what is meant by the '9'. So the trick here is: - Make sure that the 'bundleresource' protocol handler is in fact registered in an equinox environment, as I believe it must be. (I did a quick google search and found that the class should be * org.eclipse.osgi.framework.internal.core.BundleURLConnection*) - Make sure that code running in JRuby has the correct classloader arrangement to ensure that the JVM actually does find this URL handler. (This is probably the only trick here, and probably requires a combination of setting the context classloader on the thread starting JRuby, as well as appropriate buddy classloader settings on the plugins). - Make sure that the URL handler does understand the path, including the numerical references, like the '9' above. This should be the case, since this code should be part of equinox already (ie. * org.eclipse.osgi.framework.internal.core.BundleURLConnection* should just work). So, my theory here is that all the code already exists, and this is mainly a classloader issue. A variation on the same classloader issue we have seen repeatedly in using JRuby in eclipse. To learn more about protocol handlers, read http://java.sun.com/developer/onlineTraining/protocolhandlers/. This covers also how to write them, which I believe should not be necessary in this case. Hopefully you can find here the information necessary to investigate what protocol handlers exist in various contexts (different plugins, inside and outside the JRuby runtime, etc.) Then you can work out how to make sure the right handler does exist inside JRuby. Does this make sense? Any comments? Cheers, Craig On Mon, Jun 22, 2009 at 7:40 PM, Nick Sieger <nicksie...@gmail.com> wrote: > On Mon, Jun 22, 2009 at 11:26 AM, Lagutko Nikolay < > nikolay.lagu...@gersis-software.com> wrote: > >> Hi, >> >> >> >> I have a problem with working with JRuby in Eclipse. If required scripts >> stored not in classpath directories but in other plugins JRuby cannot find >> them. As I see the problem in Equinox environment. When JRuby calculates >> path to required script it uses Equinox BundleClassLoader to load this >> script and it will return path to file in bundle-dependent format, for >> example >> >> bundleresource://9/./some_script.rb >> >> And in further calculations JRuby cannot correctly interpret this path. >> For example function File.expand_path will return “/./some_script” instead >> of full path “D:/path_to_plugin/some_script”. >> >> >> >> I find out how to resolve this problem with using FileLocator class from >> org.eclipse.core.runtime plugin but I don’t want to have dependencies to >> other plugins in my org.jruby plugin. >> >> >> >> Are there other ways to resolve this problem? >> > We'd rather not take on additional dependencies to custom classloader > resource URLs and schemes either. Is there any standard JDK API that gives > you what you want? By chance does the Eclipse API implement > getSchemeSpecificPart or getFile in a sane way on the URL returned by > ClassLoader.getResource? > > /Nick > >