I investigated it a bit, the problem should be we need to register the TranqlDataSource.SelfObjectFactory as a service somewhere, maybe it should be done by tranql itself, or be done while Geronimo binds the datasource into the jndi tree.
2011/4/14 Shenghao Fang <[email protected]> > Actually I thought the problem is caused by that we use > OSGiObjectFactoryBuilder to initialize the object, and > OSGiObjectFactoryBuilder tries to initialize the object by OSGi > services, but the jdbc driver (tranql) is not a bundle (it is not > required to be a bundle), so the initialization fails and the > Reference itself returned. > > I debugged into the following method, it uses OSGi services to > initialize the object, but since the jdbc driver is not a bundle, > ServiceReference[] refs is null, and the initialization fails. > > org.apache.aries.jndi.ObjectFactoryHelper: 196 > > private Object getObjectInstanceUsingClassName(Object reference, > String className, > Object obj, > Name name, > Context nameCtx, > Hashtable<?, ?> > environment) > throws Exception { > ServiceReference serviceReference = null; > > try { > ServiceReference[] refs = > defaultContext.getServiceReferences(className, null); > if (refs != null && refs.length > 0) { > serviceReference = refs[0]; > } > } catch (InvalidSyntaxException e) { > // should not happen > throw new RuntimeException("Invalid filter", e); > } > > Object result = null; > > if (serviceReference != null) { > ObjectFactory factory = (ObjectFactory) > defaultContext.getService(serviceReference); > try { > result = factory.getObjectInstance(reference, name, > nameCtx, environment); > } finally { > defaultContext.ungetService(serviceReference); > } > } > > return (result == null) ? obj : result; > } > > And in doGetObjectInstance method, the methods > 'getObjectInstanceUsingRefAddress', > 'getObjectInstanceUsingObjectFactoryBuilders', > 'getObjectInstanceUsingObjectFactories' also use the OSGi way as what > getObjectInstanceUsingClassName does. > > org.apache.aries.jndi.ObjectFactoryHelper: 62 > > private Object doGetObjectInstance(Object obj, > Name name, > Context nameCtx, > Hashtable<?, ?> environment) > throws Exception { > > // Step 1 > if (obj instanceof Referenceable) { > obj = ((Referenceable) obj).getReference(); > } > > Object result = obj; > > // Step 2 > if (obj instanceof Reference) { > Reference ref = (Reference) obj; > String className = ref.getFactoryClassName(); > > if (className != null) { > // Step 3 > result = getObjectInstanceUsingClassName(obj, > className, obj, name, nameCtx, environment); > } else { > // Step 4 > result = > getObjectInstanceUsingRefAddress(ref.getAll(), obj, name, nameCtx, > environment); > } > } > > // Step 5 > if (result == null || result == obj) { > result = getObjectInstanceUsingObjectFactoryBuilders(obj, > name, nameCtx, environment); > } > > // Step 6 > if (result == null || result == obj) { > if ((obj instanceof Reference && ((Reference) > obj).getFactoryClassName() == null) || > !(obj instanceof Reference)) { > result = getObjectInstanceUsingObjectFactories(obj, > name, nameCtx, environment); > } > } > > return (result == null) ? obj : result; > } > > The solution in mind currently is setting a different > ObjectFactoryBuilder instead of OSGiObjectFactoryBuilder on > NamingManager for those plain jars. But where shall I do this? Any > idea? > > 2011/4/14 Shenghao Fang <[email protected]>: > > Hi Ivan, > > > > Thanks for your hits. > > > > 2011/4/14 Ivan <[email protected]>: > >> From the codes in DataSourceBuilder, the jndi reference is with prefix > >> aries:service, so there should be something like an ObjectFactory would > take > >> care of it. I could see a service > org\apache\aries\jndi\url\Activator.class > >> support this schema is registered in the activator, I simply compared > that > >> Java file between 0.2 and 0.3 seems that some logic is changed, think > this > >> should be a place to begin the debugging. > >> Hope it helps. > >> > >> 2011/4/14 Shenghao Fang <[email protected]> > >>> > >>> Hi, > >>> > >>> When I did the enablement for the monitoring portlet, I lookup the > >>> datasource from JNDI and got an object of type javax.naming.Reference > >>> instead of javax.sql.DataSource. > >>> > >>> I debugged into JNDI related modules and found the following clues: > >>> > >>> 1. If the object to be bound is of type javax.naming.Referenceable, > >>> then the object of type javax.naming.Reference retrieved by > >>> Referenceable.getReference() will be bound. And the object should be > >>> dereferenced automatically when lookup. > >>> > >>> 2. When lookup from JNDI, javax.naming.spi.NamingManager tries to use > >>> the ObjectFactoryBuilder set to dereference. In current > >>> implementation, we set org.apache.aries.jndi.OSGiObjectFactoryBuilder > >>> to ObjectFactoryBuilder. > >>> > >>> 3. Since the datasource is not packaged as an OSGi bundle, > >>> OSGiObjectFactoryBuilder returns the Reference directly. > >>> > >>> > >>> I have no idea on how to fix this, any idea? Thanks. > >>> > >>> > >>> -- > >>> Michael > >> > >> > >> > >> -- > >> Ivan > >> > > > > > > > > -- > > Michael > > > > > > -- > Michael > -- Ivan
