I find one reason of this exception.  It's actually caused by spring-dm's
thread context class loader, and could be illustrated as following scenario

1. spring osgi extender switch context class loader to current bundle
2. starting spring application of current bundle
3. spring application may allocate thread from thread pool (shared between
multi application/bundle. etc: jetty server's thread).
3.1: if the allocated thread is a new created one, it will inherit the
parent's context class loader. It's just class loader for current bundle.
4. After stop and uninstall the application bundle, the thread will return
back to pool, But unfortunately, it thread context class loader still point
to the uninstalled bundle; 

So while start a new application bundle, it may get a thread with a bad
context class loader from pool.

I hate the thread context class loader. For a temporary fix, I change the
source code of spring-dm's BundleDelegatingClassloader to check if bundle
still available, before using it to get resource or class;


> -----original -----
> Sender: Johan Edstrom [mailto:[email protected]]
> Date: 2011/6/3 12:46
> Receiver: [email protected]
> Subject: Re: IllegalStateException of ServiceMix4.3
> 
> The most likely issue is that spring-dm provides a
threadcontextclassloader
> as well as monitoring of all activated bundles, combine that with
classpath
> scanning
> and you have one of the reasons why Apache Aries Blueprint is popular :)
> 
> 
> On Jun 2, 2011, at 10:27 PM, ext2 wrote:
> 
> > Thanks Johan Edstrom
> >
> > I think  it should be a  timing issume,  not a visibility issue. I have
> > traced the source code of  DocumentBuilderFactoy where the exception
occurs;
> > it not try use a un-exists class or resource, but just try to find a
> > resource in bundle's delegate class loader , then a exception raised;
> >
> > Now I still feel puzzled that which thing caused such a timing issue?
> >
> > To find the answer I tracking the source code of spring-dm and  the hot
> > deploy application(felix.fileinstall bundle); (the summarized logic will
> > list at following.) It seems nothing is wrong.
> >
> > Hot deploy logic: org.apache.felix.fileinstall.internal.DirectoryWatcher
> >     Bundle = Context.getBundle(id);//find the old bundle
> >     Bundle.stop(transient); //stop the bundle
> >     Bundle.update(inputstream);//update the bundle;
> >     PackageAdmin.refreshPackages(null);//force updated bundle to be
> > refreshed; until now the updated bundle should be resolved and ready for
the
> > updated content;
> >     Bundle.start();//restart the bundle; then spring dm will receive
> > start event synchronized; and start a new thread to build
> > spring-application-context;
> >
> > Spring DM:
> > a summarized logic as( only asynchronized-start logical):
> >     1)get bundle from event using synchronized event listener;
> >     2)create OsgiBundleXmlapplicationContext();
> >     3)if asynchronized, allocate a idle thread to refresh the
> > application context;
> >     3.1) in the thread: create a BundleDelegateClassLoader for the
> > bundle
> >     3.2)in the new thread:  switch thread context class loader to
> > BundleDelegateClassLoader
> >     3.3) in the new thread: do spring's context building
> > (
> > while building spring context, the bean is created; in my problem:
> > DocumentBuilderFactory will using the thread context class loader(here
is
> > Bundle Delegate Class Loader) to locate a DocumentBuilderFactory
> > implementation; but the bundle is not valide; so a exception throwed;
> > )
> >
> >     3.4)switch thread context class loader back to original, the ;
> >
> > Now it seems everything is ok, but which is the exactly reason caused
such
> a
> > timing  issue?
> >
> >
> > Maybe I should write a simplified program to simulate such a usage to
see
> if
> > this problem still exists; But because it's a timing issue, I am not
sure
> > if such a problem  will reappear in the simplified program;
> >
> >
> > Following is some fragments of code of spring dm:
> >
> > org....extender.internal.activator.ContextLoaderListener
> >     ContextBundleListener{ //this is synchronized listener;
> >             on BundleEvent.started:
> >                     mayBeCreateApplicationContext for bundle
> > (event.getBundle());
> >     }
> >
> > maybeCreateApplicationContext()
> > {
> >     //now create a application context using the bundle's context
> > (received from start event)
> >
> > OsgiApplicationContextCreator.createApplicationContext(bundleContext);
> >
> >     If(asynchroniz)
> >             start a new thread to run: applicationContex.refresh()
> > }
> >
> > AbstractDelegatedExecutionApplicationContext.startRefresh(){
> >     Do switch thread context;
> >     invoke building spring
> >     do switch back
> > }
> >
> >
> >> ----Original -----
> >> Sender: Johan Edstrom [mailto:[email protected]]
> >> Time: 2011/6/3 0:52
> >> Receiver: [email protected]
> >> Subject: Re: IllegalStateException of ServiceMix4.3
> >>
> >> Where you really have a problem is here :
> >>
> >> org.springframework.osgi.util.BundleDelegatingClassLoader
> >>
> >> It looks like you have a timing/visibility issue in spring-dm.
> >>
> >> On Jun 1, 2011, at 11:17 PM, ext2 wrote:
> >>
> >>> org.springframework.osgi.util.BundleDelegatingClassLoader.getResource(
> >
> >
> >



Reply via email to