We used to throw the best parties in our Coolidge Corner bachelor pad. The recipe was simple: we’d blast an eVite to the city of Boston, pick up a keg of Good Decision, break out the Beirut table, and ask the local police to turn a blind eye.
In the midst of one of our more smashing affairs, conversation turned to concurrent polygamy and if any of us were fortunate enough to have practiced the art firsthand.
Josh had. Of course, Josh had.
And he offered us this advice: “You don’t go looking for it. It’s given to you, so don’t ask questions and just take advantage of the opportunity.”
Don’t you know it, opportunity knocked upon my roommate Jon’s door not three hours later. With a couple of part-time models. Two models at the same time.
While the next morning’s brunchtime report was entertaining enough, my inner geek preferred to explore how some of the same themes might be applied to component architecture.
* Are not necessarily mutually exclusive
* Should be encouraged to focus on their own domains
* May share in some concerns, each from a different angle
* Combined are worth more than the sum of their parts
Shoot forward a few years, when an enabling technology caught up with my musings in the form of JBoss Microcontainer.
My first impression of MC was that it was “another DI Container”. And at its core, sure, it provides the kind of POJO autowiring that we’ve come to expect from this class of framework. Over the past year, however, I’ve come to appreciate MC for its extensibility, a truly differenciating characteristic from other offerings.
DI is all very nice, but I’m accustomed to having some greater utilities available to create my runtime environment. A quick glance at the MC feature list boasts Virtual Deployment Framework (VDF), a filesystem abstraction (VFS) and aspectized classloading facilities. Armed with these, I was set to kick the tires in hopes of discovering some deficiencies in the design and thus gaining bragging rights over Ales.
Mission: Provide @EJB injection into MC Beans
In short, I want MC Beans to be able to inject references to EJB3 proxies. This will be our integration point for interacting with EJB from MC-based Services.
MC applies a metadata-collecting vistor to beans that are installed, and this is passed along to an AnnotationPlugin whose responsibility is to apply the requisite info to the visitor. By implementing an AnnotationPlugin to handle javax.ejb.EJB, we’ve got our hook. This process is eased by abstract support from FieldAnnotationPlugin, and the main goal here is to supply a ValueMetaData describing the injection value.:
* Create @EJB value meta data.
* @param annotation
* @return @EJB metadata
protected ValueMetaData createValueMetaData(FieldInfo propInfo, EJB annotation)
// Get properties from the annotation
String beanName = annotation.beanName();
String beanInterface = annotation.beanInterface().getName();
String mappedName = annotation.mappedName();
// Supply beanInterface from reflection if not explicitly-defined
if (beanInterface == null || beanInterface.equals(Object.class.getName()))
String reflectType = propInfo.getType().getName();
beanInterface = reflectType;
// Create a reference
EjbReference reference = new EjbReference(beanName, beanInterface, mappedName);
log.debug("Found @EJB reference " + reference);
// Return a new ValueMetaData w/ the reference
return new AbstractEjbReferenceValueMetadata(this.getResolver(), reference, this.getNamingContext());
The “EjbReference” above is a value object used by the EJB3 Reference Resolver, responsible for finding the JNDI Name to which a reference is bound.
The return value is AbstractEjbReferenceValueMetadata, an implementation of ValueMetaData able to:
1) Declare a dependency upon the JNDI target value. This ensures our MC Bean will not deploy until the referenced EJB has
2) Obtain the EJB Proxy from JNDI so that it may be injected
From here, the only thing left to do is let MC know that it should consider our new AnnotationPlugin upon installation of new beans. For this task I’ll create a simple POJO which, installed, will alter MC’s behaviour. The key here is in the lifecycle “@Start”:
public void start() throws Exception
// Install the BeanAnnotationAdapter w/ callback to add annotation plugins on install
BeanAnnotationAdapter beanAnnotationAdapter = BeanAnnotationAdapterFactory.getInstance()
String beanAnnotationAdapterBindName = MC_NAMESPACE_EJB3 + "BeanAnnotationAdapter";
BeanMetaDataBuilder bmdb = BeanMetaDataBuilder.createBuilder(beanAnnotationAdapterBindName, beanAnnotationAdapter
catch (Throwable e)
throw new RuntimeException("Could not install " + beanAnnotationAdapter, e);
Here we get at the BeanAnnotationAdapter and install it into the KernelController along with some callbacks to automatically add AnnotationPlugins when they, in turn, are installed. From here on out, all we need is to throw EjbReferenceAnnotationPlugin into MC.
Unfortunately, I’m left with nothing to hold aver Ales’ head as MC provided me, as a framework developer, with all the tools needed to extend the provided groundwork. In fact, I’m even at a deficit because I needed to consult the Microcontainer Users’ Forum for some suggestions.
I’d like some input from application developers – in what situations would you like to call an EJB from a POJO? Managed objects within Microcontainer act as singletons within the confines of the system, so there should be plenty of occasions to call upon a pooled/cached distributed component. This is the goal we address by providing integration between component models.
Because nothing catches on without a proper title, I’ll name our approach right now: Concurrent Polyforma.
So now we’ve put JBoss MC to a real-world test, proving that it can wrap your favorite model. As an additional exercise, I also did this quite literally:
This is how we’ll help you bridge two models. You just can’t Eiffel Tower them.