Home » Eclipse Projects » Equinox » How to add URLs to a plugin/bundle classloader 
| How to add URLs to a plugin/bundle classloader [message #47702] | 
Thu, 28 April 2005 12:31   | 
 
Eclipse User  | 
 | 
 | 
   | 
 
Hello, 
 
We have developed a plugin under Ecplise 2.1 which makes use of the internal 
class org.eclipse.core.internal.plugins.PluginClassLoader. 
 
This class is very useful since it has this method: 
public void addURLs(URL[] codePath, URLContentFilter[] codeFilters, URL[] 
resourcePath, URLContentFilter[] resourceFilters) 
 
The reason for using this method is that we are forced to load a given 
development-time class from our plugin classloader: this is because our 
plugin instantiates a class and then makes a typecast in order to manipulate 
it locally. The typecast will throw a java.lang.ClassCastException unless 
the casting and cast classes come from the same classloader. 
Because of the nature of the plugin, we cannot statically add the given 
classes to the plugin's classpath, as the plugin should be able to load and 
manipulate any class available at the workbench. 
 
The problem is that this class has been removed from Eclipse 3 (I don't 
complain, since the "internal" package name was a warning to that, but it 
was the only way we knew how to do the above thing). I have been reviewing 
the JavaDocs for the osgi and eclipse plugin infrastructure of Eclipse 3... 
and found no replacement for such a method. 
 
Is there some way we can do that with Ecplise 3? If not, what would be the 
workaround for that? 
 
Thank you very much for your help, 
 
    Luis.
 |  
 |  
  |  
| Re: How to add URLs to a plugin/bundle classloader [message #47791 is a reply to message #47702] | 
Fri, 29 April 2005 15:56    | 
 
Eclipse User  | 
 | 
 | 
   | 
 
Luis wrote: 
> Hello, 
>  
> We have developed a plugin under Ecplise 2.1 which makes use of the internal 
> class org.eclipse.core.internal.plugins.PluginClassLoader. 
>  
> This class is very useful since it has this method: 
> public void addURLs(URL[] codePath, URLContentFilter[] codeFilters, URL[] 
> resourcePath, URLContentFilter[] resourceFilters) 
>  
> The reason for using this method is that we are forced to load a given 
> development-time class from our plugin classloader: this is because our 
> plugin instantiates a class and then makes a typecast in order to manipulate 
> it locally. The typecast will throw a java.lang.ClassCastException unless 
> the casting and cast classes come from the same classloader. 
> Because of the nature of the plugin, we cannot statically add the given 
> classes to the plugin's classpath, as the plugin should be able to load and 
> manipulate any class available at the workbench. 
>  
> The problem is that this class has been removed from Eclipse 3 (I don't 
> complain, since the "internal" package name was a warning to that, but it 
> was the only way we knew how to do the above thing). I have been reviewing 
> the JavaDocs for the osgi and eclipse plugin infrastructure of Eclipse 3... 
> and found no replacement for such a method. 
>  
> Is there some way we can do that with Ecplise 3? If not, what would be the 
> workaround for that? 
>  
> Thank you very much for your help, 
>  
>     Luis. 
>  
>  
Have you tried using an interface instead of a class to manipulate the  
object?  This would eleminate the class cast exception. 
 
Ted :-)
 |  
 |  
  |  
| Re: How to add URLs to a plugin/bundle classloader [message #47821 is a reply to message #47791] | 
Mon, 02 May 2005 06:57    | 
 
Eclipse User  | 
 | 
 | 
   | 
 
Hi, 
 
I have been trying your suggestion and I still get a ClassCastException even 
when casting to an interface. 
After all, it makes sense since the interface I am casting to and the one 
that implements the loaded class are the same one, but they come from 
different classloaders. 
 
Yes, the ClassCastException name here is a bit misleading, purists may 
complain and say it should be called ClassOrInterfaceCastException ;-). 
 
Regards, 
 
    Luis. 
 
 
"Ted Habeck" <habeck@us.ibm.com> wrote in message 
news:d4u3pd$8kg$1@news.eclipse.org... 
 
 
> Have you tried using an interface instead of a class to manipulate the 
> object?  This would eleminate the class cast exception. 
> 
> Ted :-) 
 
 
> Luis wrote: 
> > Hello, 
> > 
> > We have developed a plugin under Ecplise 2.1 which makes use of the 
internal 
> > class org.eclipse.core.internal.plugins.PluginClassLoader. 
> > 
> > This class is very useful since it has this method: 
> > public void addURLs(URL[] codePath, URLContentFilter[] codeFilters, 
URL[] 
> > resourcePath, URLContentFilter[] resourceFilters) 
> > 
> > The reason for using this method is that we are forced to load a given 
> > development-time class from our plugin classloader: this is because our 
> > plugin instantiates a class and then makes a typecast in order to 
manipulate 
> > it locally. The typecast will throw a java.lang.ClassCastException 
unless 
> > the casting and cast classes come from the same classloader. 
> > Because of the nature of the plugin, we cannot statically add the given 
> > classes to the plugin's classpath, as the plugin should be able to load 
and 
> > manipulate any class available at the workbench. 
> > 
> > The problem is that this class has been removed from Eclipse 3 (I don't 
> > complain, since the "internal" package name was a warning to that, but 
it 
> > was the only way we knew how to do the above thing). I have been 
reviewing 
> > the JavaDocs for the osgi and eclipse plugin infrastructure of Eclipse 
3... 
> > and found no replacement for such a method. 
> > 
> > Is there some way we can do that with Ecplise 3? If not, what would be 
the 
> > workaround for that? 
> > 
> > Thank you very much for your help, 
> > 
> >     Luis. 
> > 
> > 
> Have you tried using an interface instead of a class to manipulate the 
> object?  This would eleminate the class cast exception. 
> 
> Ted :-)
 |  
 |  
  |  
| Re: How to add URLs to a plugin/bundle classloader [message #47851 is a reply to message #47821] | 
Thu, 05 May 2005 10:53   | 
 
Eclipse User  | 
 | 
 | 
   | 
 
Luis wrote: 
> Hi, 
>  
> I have been trying your suggestion and I still get a ClassCastException even 
> when casting to an interface. 
> After all, it makes sense since the interface I am casting to and the one 
> that implements the loaded class are the same one, but they come from 
> different classloaders. 
>  
> Yes, the ClassCastException name here is a bit misleading, purists may 
> complain and say it should be called ClassOrInterfaceCastException ;-). 
>  
> Regards, 
>  
>     Luis. 
>  
>  
> "Ted Habeck" <habeck@us.ibm.com> wrote in message 
> news:d4u3pd$8kg$1@news.eclipse.org... 
>  
>  
>  
>>Have you tried using an interface instead of a class to manipulate the 
>>object?  This would eleminate the class cast exception. 
>> 
>>Ted :-) 
>  
>  
>  
>>Luis wrote: 
>> 
>>>Hello, 
>>> 
>>>We have developed a plugin under Ecplise 2.1 which makes use of the 
>  
> internal 
>  
>>>class org.eclipse.core.internal.plugins.PluginClassLoader. 
>>> 
>>>This class is very useful since it has this method: 
>>>public void addURLs(URL[] codePath, URLContentFilter[] codeFilters, 
>  
> URL[] 
>  
>>>resourcePath, URLContentFilter[] resourceFilters) 
>>> 
>>>The reason for using this method is that we are forced to load a given 
>>>development-time class from our plugin classloader: this is because our 
>>>plugin instantiates a class and then makes a typecast in order to 
>  
> manipulate 
>  
>>>it locally. The typecast will throw a java.lang.ClassCastException 
>  
> unless 
>  
>>>the casting and cast classes come from the same classloader. 
>>>Because of the nature of the plugin, we cannot statically add the given 
>>>classes to the plugin's classpath, as the plugin should be able to load 
>  
> and 
>  
>>>manipulate any class available at the workbench. 
>>> 
>>>The problem is that this class has been removed from Eclipse 3 (I don't 
>>>complain, since the "internal" package name was a warning to that, but 
>  
> it 
>  
>>>was the only way we knew how to do the above thing). I have been 
>  
> reviewing 
>  
>>>the JavaDocs for the osgi and eclipse plugin infrastructure of Eclipse 
>  
> 3... 
>  
>>>and found no replacement for such a method. 
>>> 
>>>Is there some way we can do that with Ecplise 3? If not, what would be 
>  
> the 
>  
>>>workaround for that? 
>>> 
>>>Thank you very much for your help, 
>>> 
>>>    Luis. 
>>> 
>>> 
>> 
>>Have you tried using an interface instead of a class to manipulate the 
>>object?  This would eleminate the class cast exception. 
>> 
>>Ted :-) 
>  
>  
>  
Hi Louis, 
 
Sorry, I should have been more specific.   The solution outlined below 
works: 
 
In order to access the interface created by the second class loader, the 
associated interface must be defined to both classloaders in the same 
package. 
 
The Object & Interface can be defined one time in the Demo project. Use 
linked folder in the plug-in project, and then add the linked folder as 
a source folder to your plug-in project. Finally, add the ouput folder 
(/bin) as part of the build.properties (the linked folder /demo can not 
be added since the builder does not support linked folders). In this 
way, the code is maintained in one place, but compiled into both 
projects without requiring the two projects to be dependant, or have 
each other on their respective classpaths). 
 
In the example shown below, an object "DemoExample" is instantiated by a 
URL classloader through reflection, and its "getDemoObject" method 
returns an IDemoObject interface.  The attributes of the returned 
interface are then presented in a dialogbox. 
 
 
-------------- sample action ----------------------------------------- 
 
   /** 
    * The action has been activated. The argument of the method 
represents the 
    * 'real' action sitting in the workbench UI. 
    * 
    * @see IWorkbenchWindowActionDelegate#run 
    */ 
   public void run(IAction action) 
   { 
     URLClassLoader loader; 
     URL urls[] = new URL[1]; 
     ArrayList urlList = new ArrayList(); 
     try 
     { 
       urlList.add(new File("C:/jars/demo.jar").toURL()); 
     } catch (MalformedURLException e) 
     { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
     } 
     urls = (URL[]) urlList.toArray(urls); 
     loader = new URLClassLoader(urls, this.getClass().getClassLoader()); 
     try 
     { 
       // now load the DemoLoader through reflection. 
       Class c = loader.loadClass("org.eclipse.demo.objects.DemoExample"); 
       Object demoExample = c.newInstance(); 
       Method m = c.getDeclaredMethod("getDemoObject", null); 
       IDemoObject demoObjectInterface = (IDemoObject) 
m.invoke(demoExample, null); 
       MessageDialog.openInformation(window.getShell() 
           , "MultiLoaderDemo Plug-in", "demoObjectInterface: Line:"+ 
           demoObjectInterface.getLineNumber()+ 
           " Message"+demoObjectInterface.getMessage()+" 
Type:"+demoObjectInterface.getType()+" subType:" + 
demoObjectInterface.getSubType()); 
     } catch (Exception e) 
     { 
       // TODO Auto-generated catch block 
       e.printStackTrace(); 
     } 
 
 
   } 
 
-------------- DemoExample class--------- 
 
package org.eclipse.demo.objects; 
 
import org.eclipse.demo.shared.interfaces.DemoObject; 
import org.eclipse.demo.shared.interfaces.IDemoObject; 
 
/** 
  * DemoExample 
  * 
  */ 
public class DemoExample 
{ 
 
   /** 
    * 
    */ 
   public DemoExample() { 
     super(); 
 
   } 
 
   public IDemoObject getDemoObject() 
   { 
      DemoObject demoObject = new DemoObject(); 
      demoObject.setLineNumber(25); 
      demoObject.setMessage("Marker hover text goes here..."); 
      demoObject.setSubType("example.subType"); 
      demoObject.setType("demo.Type"); 
      IDemoObject iDemoObject =  demoObject; 
      return iDemoObject; 
   } 
 
} 
-------------- IDemoObject Interface ----------- 
 
package org.eclipse.demo.shared.interfaces; 
 
/** 
  * IDemoObject 
  * 
  */ 
public interface IDemoObject 
{ 
   public abstract int getLineNumber(); 
 
   public abstract String getMessage(); 
 
   public abstract String getSubType(); 
 
   public abstract String getType(); 
} 
 
-------------- DemoObject class ----------------------- 
 
package org.eclipse.demo.shared.interfaces; 
 
/** 
  * DemoObject 
  * 
  */ 
public class DemoObject implements IDemoObject 
{ 
 
   private String message; 
   private String type; 
   private String subType; 
   private int    lineNumber; 
   /** 
    * 
    */ 
   public DemoObject() { 
     super(); 
     // TODO Auto-generated constructor stub 
   } 
 
 
   public final int getLineNumber() 
   { 
     return lineNumber; 
   } 
   public final void setLineNumber(int lineNumber) 
   { 
     this.lineNumber = lineNumber; 
   } 
   public final String getMessage() 
   { 
     return message; 
   } 
   public final void setMessage(String message) 
   { 
     this.message = message; 
   } 
   public final String getSubType() 
   { 
     return subType; 
   } 
   public final void setSubType(String subType) 
   { 
     this.subType = subType; 
   } 
   public final String getType() 
   { 
     return type; 
   } 
   public final void setType(String type) 
   { 
     this.type = type; 
   } 
}
 |  
 |  
  |   
Goto Forum:
 
 Current Time: Mon Nov 03 20:43:16 EST 2025 
 Powered by  FUDForum. Page generated in 0.04107 seconds  
 |