Hi  Vijay,

regarding keeping transactions as short as possible the following example:

execute() {
   Database db = jdo.getDatabase();
   db.begin();
   // query objects from database with read only
   db.commit();
   db. close();

   // do some time consuming processing with the data

   Database db = jdo.getDatabase();
   db.begin();
   // use db.load() to load the objects you need to change again
   // create, update or delete some objects
   db.commit();
   db. close();
}

It doesn't make sense to make a own transaction for every change you want to do to an object as this will slow down your application. On the other hand if you have transactions with lots of objects involved taking an valuable amonth of time you may consider to split this transactions to reduce the time an object is locked.

Ralf


Nick Stuart schrieb:

As far as the way you handle the JDO class that is the correct way to do things.

I'll let Ralf comment on what he meant by that. :)

-Nick

On 4/27/05, Vijayanand Sukumar <[EMAIL PROTECTED]> wrote:


Ralf,

Thanks for your advice. I will do the changes you suggested.

Regarding not re-using database instances...

This is what we do. Please correct me if this is not the right approach.

When the application starts, we instantiate a JDO object and keep it in the
context.

...
jdo = new JDO();
JDO.loadConfiguration(getClass().getClassLoader().getResource(DATABASE_FILE_
NAME).toString());
jdo.setDatabaseName(jdoDatabaseName);
jdo.setTransactionManager(txmgr);
initContext.bind(jdoJndiName, jdo);
...

And in our struts action class , inside the execute method we do

Database db = jdo.getDatabase();
db.open();
xxDB.getObject(someparameters, db);

db.commit();

Where jdo is a instance object in the Action class and the value is set in
the init() method.

So each time the execute is called , a new database is obtained. Is this
approach right ?

Since the transaction is opened and committed in the execute method, the
number of SQL statements executed in that transaction are fairly more.
Is this what you meant by



5. Keep your transactions as short as possible. If you have an open
transaction that holds a write lock on an object no other transaction
can get a write lock on the same object which will lead to a
LockNotGrantedException.


Thanks again for all your help.

Vijay


-----Original Message----- From: Ralf Joachim [mailto:[EMAIL PROTECTED] Sent: Wednesday, April 27, 2005 6:13 AM To: [email protected] Subject: Re: [castor-user] Transaction locks and muti threaded access

Hi Mike,

for queries:

String oql = "select o from FooBar o";
Query query = db.getOQLQuery(oql);
QueryResults results = query.execute(Database.ReadOnly);

to load an object by its identity:

Integer id = new Integer(7);
Foo foo = (Foo) db.load(Foo.class, id, Database.ReadOnly);

Ralf

Mike Wannamaker schrieb:


Ralf,  How do I do this?  Make a query read only that is?

6. Query or load your objects read only whenever possible. Even if
castor creates a lock on them this does not prevent other threads from
reading or writing them. Read only queries are also about 7 times
faster compared with default shared mode.

--ekiM

Ralf Joachim wrote:



Hi Vijay,

I know that Gregory Block (another castor commiter) is using castor
in a high-volume application. Even if I would call my appliaction a
low-volume one, I also had to resolve some locking problems that I
could track down to negligences at backgroud threads of my
application. There are also some performance bottlenecks we are aware
of and are working to solve them at our next refactoring steps at
castor. For some of them we have working patches or workarounds
available (will come to them later).

I'll start with some general suggestions that you should have a look
at. Please don't feel upset if some are really primitive but there
may be users listening that are not aware of them.


1. Switch to version 0.9.6 of castor as we have fixed some bugs that may cause some of your problems.

2. Initialize your JDO or JDO2 (will be renamed to JDOManager at next
release) instance once and reuse it all over your application. Don't
reuse the Database instances.

3. Use a Datasource instead of a Driver configuration as they enable
connection pooling which gives you a great performance improvement.

4. Always commit or rollback your transactions and close your
Database instances properly also in fail situations as suggested by
Nick previously.

5. Keep your transactions as short as possible. If you have an open
transaction that holds a write lock on an object no other transaction
can get a write lock on the same object which will lead to a
LockNotGrantedException.

6. Query or load your objects read only whenever possible. Even if
castor creates a lock on them this does not prevent other threads
from reading or writing them. Read only queries are also about 7
times faster compared with default shared mode.

7. If there is a possibility you should prefer db.load(Class, object)
over db.execute(String). I suggest that as db.load() first tries to
load the requested object from cache and only retrieves it from
database when it is not availble there. When executing queries with
db.execute() the object will always be loaded from database without
looking at the cache. You may gain a improvement by a factor of 10
and more when changing from db.execute() to db.load().


I hope above suggestions help you to resolve the problems you have. If you still need more performance there are 2 areas of improvement that are more difficult to resolve.

a. If you have a look at http://jira.codehaus.org/browse/CASTOR-1085
where a patch to TransactionContext is attached that improves
read/write performance with a factor of 3. Even if the patch passes
all tests of castor test framework it requires more testing before we
will integrate it in our next major release. As stated in the comment
Gregory will use the patch in his production environment sooon.

b. I will attache a test that shows how read only performance can be
improved to http://jira.codehaus.org/browse/CASTOR-732 this evening.

Hope I could help you with that information.

Regards
Ralf



Vijayanand Sukumar schrieb:



All,

Nick, Thanks for your explanation.  We are using 0.9.5.3 .
I will do a rollback on all the transactions when a
PersistenceException is thrown.

I am really interested to know if anyone is using castor in a high
volume , mission critical application and the problems they faced if
any and how solved it.
Thanks

Vijay



-----Original Message-----
From: Nick Stuart [mailto:[EMAIL PROTECTED] Sent: Tuesday, April
26,
2005 4:32 PM
To: [email protected]
Subject: Re: [castor-user] Transaction locks and muti threaded
access

Will try my best to explain some of these issues in line.
On 4/26/05, Vijayanand Sukumar <[EMAIL PROTECTED]> wrote:



We have been using castor-struts for about 2 years now and we are
having some issues related to the castor. we are at a stage where
due to performance issues we are thinking of moving away from castor.

Any explanations/solutions for the given problems will be greatly
appreciated.

1. When more than 1 thread access the same object, is multiple
copies of the same object is created or is the same instance of the
object is used across multiple
transactions. If it the same object then wouldn't it affect
performance as in our case we have about a hundred users using the
same record.




Yes its the same object. But no you shouldn't see a performance hit
because its serving it out of the Cache. In fact, if the object is
used enough, and is always in the cache you would see a performance
gain. This assumes most of your actions are read only, as several
threads acting on the same object and trying to do changes will
cause problems.




2. when a transaction fails , the locks on all the objects related
to that transaction are not released.
we have had instances where a LockNotGrantedException:
WriteTimeOut occurs on a JDO object and the lock on the object is
not released until the server is re-started.
How can I release a lock on that object ? This problem kills
all the mission critical applications where the application cannot
be restarted. Can this be overcome if an explicit rollback is called ?




If you have a PersistenceExcpetion during a transaction (between
db.begin and db.commit) you should always do a rollback. This will
release the objects and locks. If you dont do this my best guess as
to what could happen to your data is as good as yours.





3. when a commit fails and rollback is not explicitly called are
all locks on the objects in that transaction released ?




They should be yes. If they are not my guess is that its a bug. You
never mentioned what version of castor you are using.




4. A lock is obtained on an object even if it stated in the mapping
as read-only. This slows down all the queries even if they are
read-only , how can I overcome this ?





Not sure about this one myself....never ran into any problems with it.




Based on my experience so far, I have a feeling that castor is not
suited for high-volume, mission critical applications.





All my apps are well used, but not considered high volume so my
experince in
that area is limited. Although I'm pretty sure other people on the
list will
share their experinces about this.




Has anyone used castor in a high-volume, mission critical
application and have success story?


ANY HELP WOULD BE GREATLY APPRECIATED. Thanks

Vijay



Hope this helps some. Anyone else want to throw something this way?
-Nick





--

Syscon Ingenieurb�ro f�r
Me�- und Datentechnik GmbH
Ralf Joachim
Raiffeisenstra�e 11
D-72127 Kusterdingen
Germany

Tel.   +49 7071 3690 52
Mobil: +49 173 9630135
Fax    +49 7071 3690 98

Email: [EMAIL PROTECTED]
Web:   www.syscon-world.de










Reply via email to