Maybe I am missing something....but why not wait until the entire tree (collections and references) has been materialized before pushing the object on the cache?
Or, is there a problem with circular references by doing that? -Andrew -----Original Message----- From: Armin Waibel [mailto:[EMAIL PROTECTED] Sent: Thursday, January 29, 2004 1:31 PM To: OJB Users List Subject: Re: [PB API] concurrency problems Hi Sven, I can reproduce your problem. It's a really nasty concurrency materialization problem when using global/shared caches and an object was materialized first time: Say we have a class Account with reference to Buyer, Buyer has a reference to Address and Address has a reference to AddressType (similar to your test case) Account -1:1- Buyer -1:1- Address -1:1- AddressType We set autoretrieve true. Thread_1: PB lookup Account object. Object was not found in cache, PB start to materialize Account and push this to cache, then first reference was materialized and pushed to cache,... Thread_2: PB lookup Account object. Object was found in cache and returned. But the found object is the same pushed by thread_1, thus PB returns a not full materialized Account object. If a local cache was used, e.g. ObjectCachePerBrokerImpl this situation will not arise. Solution is to set attribute 'refresh="true"' in all reference-descriptor. This force OJB to lookup each reference for an object whether or not it was found in cache. regards, Armin Sven Efftinge wrote: > I just changed ObjectCacheClass from DefaultImpl to EmptyImpl. > Without caching the test doesn't fail. > I think this happens because the threads don't have to share the > objects in this case. > Sven > > Sven Efftinge wrote: > >> Hi Armin, >> I wrote a test for this, now. >> Unfortunately I wrote it against my application, because I haven't >> installed the OJB test suite yet ;( The test starts n threads. Each >> thread creates a PersistentBroker, retrieves 4 instances of an entity >> and then checks some references for each entity. >> When I run the test for 1 thread the test passes. >> When I run it for e.g. 30 threads the test fails(most of the time) >> because some references were null. >> Mmh... the test fails to RC4, also. >> I'm not sure if this is really the same problem because I don't get >> any errors from OJB directly. Only the null references. >> >> Here is the test (I used GroboUtils from SF): >> >> public void testConcurrentRead() throws Throwable { >> int numthreads = 30; >> TestRunnable[] tests = new TestRunnable[numthreads]; >> >> for (int i = 0; i < tests.length; i++) { >> tests[i] = new FetchPersistentObjects(); >> } >> MultiThreadedTestRunner testRunner = >> new MultiThreadedTestRunner(tests); >> >> testRunner.runTestRunnables(); >> >> } >> >> class FetchPersistentObjects extends TestRunnable { >> /* (non-Javadoc) >> * @see net.sourceforge.groboutils.junit.v1.TestRunnable#runTest() >> */ >> public void runTest() throws Throwable { >> PersistenceBroker broker = null; >> KontoIF konto = null; >> try { >> broker = >> PersistenceBrokerFactory.createPersistenceBroker(pbKey); >> Criteria crit = new Criteria(); >> crit.addEqualTo(KONTO.NAME, "test"); >> QueryByCriteria query = new >> QueryByCriteria(Konto.class, crit); >> // we have 4 kontos with name="test" in the database >> List kontos = (List) broker.getCollectionByQuery(query); >> for (Iterator iter = kontos.iterator(); iter.hasNext();) { >> konto = (KontoIF) iter.next(); >> assertEquals("test", konto.getName()); >> assertNotNull("All kontos have a reference to an >> interessent", konto.getInteressent()); >> assertNotNull("All interessents have a reference >> to an adresse", konto.getInteressent().getAdresse()); >> assertNotNull("All adresses have a reference to an >> adresseart", konto.getInteressent().getAdresse().getAdresseart()); >> assertNotNull("All adressearts have a varname", >> konto.getInteressent().getAdresse().getAdresseart().getVarname()); >> } >> } finally { >> broker.close(); >> } >> } >> >> } >> >> Armin Waibel wrote: >> >>> Hi Sven, >>> >>> I don't know if your problem rely on a concurrency problem. Between >>> rc4 and rc5 I changed handling of DB resources in RsIterator class. >>> Now OJB is very strict in closing used resources. All resources will >>> be released when >>> - PB instance was closed >>> - PB commit call is done >>> - PB abort call is done >>> This helps to avoid abandoned Statement/ResultSet instances. >>> >>> > org.apache.ojb.broker.PersistenceBrokerException: >>> > org.apache.ojb.broker.accesslayer.RsIterator$ResourceClosedException: >>> > Resources no longer reachable, RsIterator will be automatic >>> > cleaned up on PB.close/.commitTransaction/.abortTransaction >>> >>> The exception says that OJB has already closed the DB resources used >>> by the Iterator, e.g. one of the three events described above occur. >>> >>> Can you post the source code or some pseudo code where the exception >>> arise? >>> >>> regards, >>> Armin >>> >>> >>> Sven Efftinge wrote: >>> >>>> Hi, >>>> I just got some errors when using/retrieving the same >>>> persistentobjects in multiple threads (request cause it's a webapp). >>>> I tried many different configurations for class-descriptor, >>>> reference-descriptor, ... but the problem was still there. >>>> At the moment I only have proxy="dynamic" specified all other >>>> attributes are set to default. >>>> I only have the problem with OJB RC5. RC4 works fine. >>>> >>>> This is a sequence from the stacktraces: >>>> >>>> Caused by: org.apache.ojb.broker.PersistenceBrokerException: >>>> org.apache.ojb.broker.PersistenceBrokerException: >>>> org.apache.ojb.broker.accesslayer.RsIterator$ResourceClosedException: >>>> Resources no longer reachable, RsIterator will be automatic cleaned >>>> up on PB.close/.commitTransaction/.abortTransaction >>>> at >>>> org.apache.ojb.broker.accesslayer.IndirectionHandler.materializeSub >>>> ject(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.accesslayer.IndirectionHandler.getRealSubject >>>> (Unknown >>>> Source) >>>> ... 33 more >>>> Caused by: org.apache.ojb.broker.PersistenceBrokerException: >>>> org.apache.ojb.broker.accesslayer.RsIterator$ResourceClosedException: >>>> Resources no longer reachable, RsIterator will be automatic cleaned >>>> up on PB.close/.commitTransaction/.abortTransaction >>>> at >>>> org.apache.ojb.broker.core.QueryReferenceBroker.getCollectionByQuer >>>> y(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.core.QueryReferenceBroker.getCollectionByQuer >>>> y(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.core.PersistenceBrokerImpl.getCollectionByQue >>>> ry(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.accesslayer.BasePrefetcher.prefetchRelationsh >>>> ip(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.core.QueryReferenceBroker$PBPrefetchingListen >>>> er.prefetch(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.core.QueryReferenceBroker$PBMaterializationLi >>>> stener.beforeMaterialization(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.accesslayer.IndirectionHandler.beforeMaterial >>>> ization(Unknown >>>> Source) >>>> ... 35 more >>>> Caused by: >>>> org.apache.ojb.broker.accesslayer.RsIterator$ResourceClosedException: >>>> Resources no longer reachable, RsIterator will be automatic cleaned >>>> up on PB.close/.commitTransaction/.abortTransaction >>>> at >>>> org.apache.ojb.broker.accesslayer.RsIterator.getRsAndStmt(Unknown >>>> Source) >>>> at org.apache.ojb.broker.accesslayer.RsIterator.hasNext(Unknown >>>> Source) >>>> at >>>> org.apache.ojb.broker.core.QueryReferenceBroker.getCollectionByQuer >>>> y(Unknown >>>> Source) >>>> ... 42 more >>>> >>>> Does this has to do with the "prefetch and autoRetreive"-problem >>>> discussed on this list in november? >>>> >>>> regards, >>>> Sven >>>> >>>> ------------------------------------------------------------------- >>>> -- To unsubscribe, e-mail: [EMAIL PROTECTED] >>>> For additional commands, e-mail: [EMAIL PROTECTED] >>>> >>>> >>>> >>> >>> >>> >>> -------------------------------------------------------------------- >>> - To unsubscribe, e-mail: [EMAIL PROTECTED] >>> For additional commands, e-mail: [EMAIL PROTECTED] >> >> >> >> >> >> --------------------------------------------------------------------- >> To unsubscribe, e-mail: [EMAIL PROTECTED] >> For additional commands, e-mail: [EMAIL PROTECTED] > > > > > --------------------------------------------------------------------- > To unsubscribe, e-mail: [EMAIL PROTECTED] > For additional commands, e-mail: [EMAIL PROTECTED] > > > --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED] --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]
