Bugs item #554437, was opened at 2002-05-10 09:51
You can respond by visiting:
http://sourceforge.net/tracker/?func=detail&atid=376685&aid=554437&group_id=22866
Category: JBossCMP
Group: v2.4 (stable)
Status: Open
Resolution: None
Priority: 5
Submitted By: Paul Nicklin (paulnicklin)
Assigned to: Nobody/Anonymous (nobody)
Summary: Finders methods not "concurrency Safe"?
Initial Comment:
Hi all,
We're seeing an occasional problem where two calls to
finder methods made 'simultaneously' from different
instances of a session bean result in each being
returned a different remote object, but referring to
the same data.
This would not ordinarily be a big problem (the
concurrency/ optimistic locking system will prevent
the second update conflicting)
But in our case this entity bean is supporting the
High-Low pattern for giving out unique IDs, so two
Customers with the same key fails! (Won't go into
detail, but basically you have a table with "UniqueID
Name", "Unique ID NextValue" and you use this and
another number to give all your objects a unique ID -
I'd give you a URL but I don't have one- sorry!)
A bit of digging in the entity cache code (Isn't open
source wonderful!) says to me that if the row isn't in
the cache then two threads will run through the code
both saying...
"Is the row in the cache?"
"NO! - I'll go fetch it"
"Here's the row from the database, lets put it in the
cache"
"Here you go client, have a reference to the entity"
now, both call the getNextValue method and get the
next value and update the database - but because they
are not the same instance in they both update the
database to the same next value.
Then my code uses the value to create "customer" rows,
but the second fails because of a constraint violation
(Extract from CMPPersistenceManager.java)
public Object findEntity(Method finderMethod, Object[]
args, EntityEnterpriseContext ctx)
throws Exception {
// For now only optimize fBPK
if (finderMethod.getName().equals("findByPrimaryKey"))
{
Object key = ctx.getCacheKey();
if (key == null)
{
key = ((EntityCache)con.getInstanceCache
()).createCacheKey(args[0]);
}
if (con.getInstanceCache().isActive(key))
{
return key; // Object is active -> it exists -> no
need to call finder
}
}
// The store will find the entity and return the
primaryKey
Object id = store.findEntity(finderMethod, args, ctx);
// We return the cache key
return ((EntityCache) con.getInstanceCache
()).createCacheKey(id);
}
I'd suggest we check after calling the finder that the
object is STILL Not in the cache, reducing the window
of opportunity for duplication... currently the window
of opportunity for this failure includes the database
fetch time, a few hundred ms possibly, doing my change
would reduce this to a few microseconds.
Thanks for your perseverance in reading this far - any
comments? Am I completely up the wrong tree?
Suggestions welcome...
Paul Nicklin
[EMAIL PROTECTED]
----------------------------------------------------------------------
You can respond by visiting:
http://sourceforge.net/tracker/?func=detail&atid=376685&aid=554437&group_id=22866
_______________________________________________________________
Have big pipes? SourceForge.net is looking for download mirrors. We supply
the hardware. You get the recognition. Email Us: [EMAIL PROTECTED]
_______________________________________________
Jboss-development mailing list
[EMAIL PROTECTED]
https://lists.sourceforge.net/lists/listinfo/jboss-development