I know the EJB 1.1 and 2.0 specs avoid (finesse?) the issue of bean
inheritance, but has anyone tried doing anything that mimics inheritance
using Orion? If so, can you share how you accomplished it?
EJB does not directly support inheritance - the main reason being that the
Home interface for a bean could not fit into an inheritance model.
There are however some alternatives.
Firstly, suppose you have a Person EJB and want to extend it to become an
Employee. You would create (and deploy) your Person EJB as normal, then have
the remote interface and EJB implementation of Employee extend those of the
Person.
The home interface for EmployeeHome cannot extend PersonHome as it has a
different return type for findByPrimaryKey() etc.
Upon deployment, the EJB must be treated as a seperate entity, with a
seperate JNDI lookup and all the appropriate fields redefined.
This solution allows behaviours of beans to be reused, and once a entity has
been found it is seen to the client as a 'is a' relationship and exhibits
polymorphism. The problem lies in that find the EJB two seperate home
interfaces need to be looked up. A solution to this is to create a session
EJB that has reference to both beans and can use the finder methods of both
entities and return an appropriate one.
Another solution is to use the State (or Strategy) design pattern (see the
GoF Design Patterns book - or just trawl the web for what it is). The
advantage of this is that an object can change it's state at any time
without having to be recreated and all the different states can be used in
one entity. The best way to do implement this is to determine
behaviours/fields that are common across all implementations of the
inheritance model and place them in the main EJB, then place
behaviours/fields that vary in your ConcreteState/Strategy classes.
The problem with this approach is how to map keep a reference to the which
state/strategy is being used and how to store the individual fields.
Solution 1 is to simply serialize the class and store it as a field in the
main EJB. This solves both problems but may not be ideal, particularly
because the data is just stored as a bunch of binary data only recognizable
to java (useless for finder methods). If you happen to be using an Java
Object database you can perform write finder methods that use these
objects - but most people aren't.
Solution 2 to this is to create your own way of serializing/deserializing
the objects. For example, the ejbStore() method could convert the state into
an XML representation which could be stored in a normal text field, and the
ejbLoad() could recreate it again. Another idea is to store the various
properties for the state/strategy in a Map on ejbStore() - Orion can easily
map a Map to a database with it's sophisticated OR features, and the table
is easily queryable.
If all else fails, use bean managed persistance.
I'm sure there are many other methods and I would be interested to hear
them. Inheritance is one of the draw-backs to EJB and if you are using it
purely for object-relational (OR) mapping purposes, EJB may not necessarily
be your best answer - but EJB will probably solve every other problem you
have, so don't stray :)
Relevant info:
http://monsoon.wirestation.co.uk/or/ - Advanced OR mapping with Orion
http://www.ambysoft.com/mappingObjects.html - Tips for OR mapping and
creating own persistance layer
http://www.helsinki.fi/~jplindfo/pattern/State.html - Diagram of state
pattern
http://www.helsinki.fi/~jplindfo/pattern/Strategy.html - blah
-Joe Walnes