OSGi + Hibernate

2019-03-14 01:42发布

Instead of having database actions scattered in four (osgi) bundles, all doing there slightly different things. I want to create a (simple) OSGi bundle that is responsible for all persistance issues. I feel that this is not as simple as it sounds because of the "unique classloader per bundle" thing. So what I really would appreciate is if someone knows the solution(s) to this kind of problem.

5条回答
Explosion°爆炸
2楼-- · 2019-03-14 02:19

(If you are using Hibernate Annotations)

Save all the Entities class loaders when the Hibernate bundle is informed about an annotated class.

Then do something like this before building your SessionFactory.

ClassLoad cl = Thread.currentThread().getContextClassLoader();
try {
 Thread.currentThread().setContextClassLoader(yourClassLoader);
 factory = cfg.buildSessionFactory(); 
}finally {
 Thread.currentThread().setContextClassLoader(cl);  // restore the original class loader
}
查看更多
放荡不羁爱自由
3楼-- · 2019-03-14 02:20

There are two ways I can think of to solve the classloading-issue.

  • Are you tied to a specific OSGi-Framework, or do you want to stay as compatible as possible? Or can you use equinox for your implementation? In Equinox you have a mechanism called Buddy Classloading. This addition allows you to increase the visibility of certain classes between different OSGi-Bundles. If you are interested in this topic, I would like to direct you to these two articles: Understanding how Eclipse plug-ins work with OSGi, Eclipse - a tale of two VMs (and many classloaders).
  • If you prefere to stay OSGi-implementation independent, then you might considre extracting your classes, that you wish to persist, into a separate bundle on which both the Hibernate-Bundle and your other bundles depend. That way, they all have access to the class definition of the persisted classes.
查看更多
Root(大扎)
4楼-- · 2019-03-14 02:22
兄弟一词,经得起流年.
5楼-- · 2019-03-14 02:28

I'm going to recommend to stay away from buddy class loading as it's specific to Eclipse's Equinox implementation and, in my opinion, people get it to work but they don't understand why and everyone ends up as a buddy of everyone else. This stops you gaining a proper understanding of how OSGi classloading works and the patterns you need to use (composite class loaders, context class loading, OSGi services, ...) to work with it.

If your persistence bundle knows ahead-of-time what types it needs to persist, then the bundle can import all required packages (Require-Bundle is evil) that contain your domain classes.

Managing the context class loader (as in Roger's reply) can help with Hibernate, though I'd suggest using something like Spring dm to hide that behind an OSGi service.

查看更多
我只想做你的唯一
6楼-- · 2019-03-14 02:33

Just found an interesting method in the Bundle class/api.

public java.lang.Class loadClass(java.lang.String name) throws java.lang.ClassNotFoundException

This must solve some class loader issues?

查看更多
登录 后发表回答