Community
Participate
Working Groups
User-Agent: Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.1.5) Gecko/20091102 Firefox/3.5.5 Build Identifier: When the IJavaModel is created, it should register itself with OSGI as a service. This will allow an easy way to lookup the IJavaModel and allow interoperability with declarative services. Reproducible: Always
This is an enhancement. What do you want to do with the java model?
I would like to add a Java element change listener using JavaCore#addElementChangedListener(). I am using declarative services, so my plugin is started/activated before the JDT core plugin is activated. Just by referencing JavaCore as an import causes the class to be loaded, and then the JDT core plugin is activated and started - unnecessarily. Really, I just want to add my listener whenever the JavaCore starts, but not cause the plugin to be activated. This is doubly bad because I'm activated before the ResourcesPlugin is fully initialized. Actually - the ResourcesPlugin is causing me to be activated. When it registered the IWorkspace with OSGI it triggered me to start - but the start() method is not done yet. Since JavaCore uses ResourcesPlugin classes that may not have been loaded yet, deadlock would result. Except that OSGI works around this by allowing class loads to work without a fully activated plugin after a 5second delay. This causes very slow startup - but it does eventually finish. The message that is printed is similar to: !ENTRY org.eclipse.osgi 2 0 2009-11-13 11:35:25.843 !MESSAGE While loading class "org.eclipse.core.resources.IContainer", thread "Thread[main,6,main]" timed out waiting (5000ms) for thread "Thread[Component Resolve Thread,5,main]" to finish starting bundle "org.eclipse.core.resources_3.6.0.v20091019 [1160]". To avoid deadlock, thread "Thread[main,6,main]" is proceeding but "org.eclipse.core.resources.IContainer" may not be fully initialized. !STACK 0 org.osgi.framework.BundleException: State change in progress for bundle "reference:file:/D:/dev/targets2/RAD76-20091103_0403/eclipse/plugins/org.eclipse.core.resources_3.6.0.v20091019.jar" by thread "Component Resolve Thread". I have a poor workaround. What I do is install a bundle listener that listens for when the JavaCore plugin is activated, and then I call the JavaCore method I need. Unfortunately, the class that is being activated can not have any references in any imports to any JDT classes (since resolving/loading a class will resolve/load all its imports). So I have to create a proxy that uses reflection to invoke JDT methods. In OSGI services, you can specify multiple dependencies. Right now I can only specify IWorkspace. Ideally, I would specify IWorkspace and IJavaModel. Then, my service will only be activated when both those services have been registered. === my workaround === updater = new JDTListenerProxy(); // workaround, until we get a proper osgi service for IJavaModel // don't activate the jdt core plugin! final Bundle b = Platform.getBundle("org.eclipse.jdt.core"); //$NON-NLS-1$ if (b != null) { final BundleContext c = b.getBundleContext(); if (c != null) { if (b.getState() != Bundle.ACTIVE) { c.addBundleListener(new BundleListener() { public void bundleChanged(BundleEvent event) { if (b.equals(event.getBundle()) && event.getType() == BundleEvent.STARTED) { updater.start(); c.removeBundleListener(this); } } }); } else { updater.start(); } } }