Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Eclipse Projects » Rich Client Platform (RCP) » Link to external jars in plugin?(Link to external jars in plugin?)
Link to external jars in plugin? [message #1405200] Wed, 06 August 2014 20:36 Go to next message
i AqD is currently offline i AqDFriend
Messages: 8
Registered: July 2014
Location: Taipei
Junior Member
I'm trying to make my plugin working without shipping the system jfxswt.jar, which provides JavaFX integration into SWT.

Currently it only works if I put the jfxswt.jar into my plugin. Because the jfxswt.jar depends on SWT at runtime, it'd fail to find SWT classes when jfxswt.jar is inside system classpath or injected through adding URLClassLoader.addURL.

I don't really want to create a normal ClassLoaderHook like e(fx)clipse does, because that would require an additional bundle as osgi.framework.extension and installed in eclipse location. Do I have other choices? Can I just declare an external jar to be part of my plugin without actually including it?
Re: Link to external jars in plugin? [message #1405221 is a reply to message #1405200] Wed, 06 August 2014 21:45 Go to previous messageGo to next message
i AqD is currently offline i AqDFriend
Messages: 8
Registered: July 2014
Location: Taipei
Junior Member
Answering my own question. I got it work by hacking internal fields Rolling Eyes

import org.eclipse.osgi.internal.framework.EquinoxConfiguration;
import org.eclipse.osgi.internal.loader.ModuleClassLoader;
import org.eclipse.osgi.internal.loader.classpath.ClasspathEntry;
import org.eclipse.osgi.internal.loader.classpath.ClasspathManager;
import org.eclipse.osgi.storage.bundlefile.BundleFile;
import org.eclipse.osgi.storage.bundlefile.ZipBundleFile;

@SuppressWarnings("restriction")
public final class Internals
{
    public static void moduleClassLoader_addClasspathEntry(Class<?> klass, File jarFile)
    {
        try
        {
            ModuleClassLoader moduleClassLoader = (ModuleClassLoader) klass.getClassLoader();
            ClasspathManager classpathManager = moduleClassLoader.getClasspathManager();
            // Get Configuration
            Method getConfigurationMethod = ModuleClassLoader.class.getDeclaredMethod("getConfiguration");
            getConfigurationMethod.setAccessible(true);
            EquinoxConfiguration config = (EquinoxConfiguration) getConfigurationMethod.invoke(moduleClassLoader);
            // Get ClasspathManager.entries
            Field entriesField = ClasspathManager.class.getDeclaredField("entries");
            entriesField.setAccessible(true);
            ClasspathEntry[] oldEntries = (ClasspathEntry[]) entriesField.get(classpathManager);
            // Make ClasspathManager.entries writable (it's final field!)
            Field modifiersField = Field.class.getDeclaredField("modifiers");
            modifiersField.setAccessible(true);
            modifiersField.setInt(entriesField, entriesField.getModifiers() & ~Modifier.FINAL);
            // Create ClasspathEntry for the given jarFile
            BundleFile jarBundleFile = new ZipBundleFile(jarFile, null, null, config.getDebug());
            ClasspathEntry jarEntry = new ClasspathEntry(jarBundleFile, oldEntries[0].getDomain(), classpathManager.getGeneration());
            // Prepare new entries
            ClasspathEntry[] newEntries = new ClasspathEntry[oldEntries.length + 1];
            System.arraycopy(oldEntries, 0, newEntries, 0, oldEntries.length);
            newEntries[oldEntries.length] = jarEntry;
            // Set new entries to replace the old one
            entriesField.set(classpathManager, newEntries);
            System.out.println("added classpath: " + jarFile);
        }
        catch (IOException | ReflectiveOperationException e)
        {
            e.printStackTrace();
        }
    }
}


And calling it in RCP Application like:
    static
    {
        Internals.moduleClassLoader_addClasspathEntry(Activator.class,
                Paths.get(System.getProperty("java.home"), "lib", "jfxswt.jar").toFile());
    }





Still I hope there is some official way to do that......

[Updated on: Wed, 06 August 2014 21:52]

Report message to a moderator

Re: Link to external jars in plugin? [message #1405799 is a reply to message #1405221] Fri, 08 August 2014 07:56 Go to previous messageGo to next message
Marcel Austenfeld is currently offline Marcel AustenfeldFriend
Messages: 136
Registered: July 2009
Senior Member
Hello,

i have the same problem with the jfxswt.jar. I would like to load the javafx.embed.swt.FXCanvas

in a plugin and then make it available for the main RCP.

How do you get the FXCanvas class with your solution (so that e.g. the PDE recognizes the class)?

Another eventual solution is described here:


http://www.codetrails.com/blog/osgi-ify-your-tools-jar

But however i didn't tested it.
Re: Link to external jars in plugin? [message #1406874 is a reply to message #1405799] Mon, 11 August 2014 10:28 Go to previous message
Marcel Austenfeld is currently offline Marcel AustenfeldFriend
Messages: 136
Registered: July 2009
Senior Member
Hello,

I finally found a solution without using the classpath hack which i have described here:

https://www.eclipse.org/forums/index.php/t/796180/
Previous Topic:how to use -showSplash command line argument??
Next Topic:How to add shortcuts for Dynamic menus.
Goto Forum:
  


Current Time: Tue Jun 30 12:55:17 GMT 2015

Powered by FUDForum. Page generated in 0.01761 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software