dbTalk Databases Forums  

dbms_lock.allocate_unique and autonomous transactions (long)

comp.databases.oracle.misc comp.databases.oracle.misc


Discuss dbms_lock.allocate_unique and autonomous transactions (long) in the comp.databases.oracle.misc forum.



Reply
 
Thread Tools Display Modes
  #1  
Old   
hasta_l3@hotmail.com
 
Posts: n/a

Default dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 04:05 AM






Dear group,

We have lists. Each list has thousands of
ordered lines. Lists are implemented with
the usual master/detail tables.

An operation O may process (a subset of the
fields of) the lines of a list.

Operations must be serialized, so that not
two of them process the same list at the
same time.

However, other transations may want to modify
other fields of the lines of a list being processed,
and must not be blocked more than 3 secs.
However, an operation may need a few minutes
to complete.

Operations process only active lists, and there
is at most 100 active lists in a given day. Lists
become inactive after one day after, and new
lists are created.

In the current design, an operation notably :

- acquires a list lock by setting a flag in the
list header row, then commits.

- processes each line and commits.

- resets the flag, and commits.

Of course, each operation first look (for update)
whether the flag is set.

This design fails miserably if the session
holding the flag crashes.

I though that a dbms_lock would be a perfect
replacement for the flag locking scheme, since :

- the lock can persist across transactions.

- it will be released if the session crashes.

The lock would be allocated the first time it
is needed by an operation O; named after the
(qualified) primary key of the serialized list
header row for easy retrieval; and have a retention
delay of one day.

The problem is that dbms_lock.allocate_unique
(understandably) does commit. That is troublesome,
because the beginning of an operation must be
atomic.

Therefore, I'm thinking of calling allocate_unique
in an autonomous transaction. The dbms_lock.request
would still be called in the enclosing transaction.

I cannot find a problem with this scheme :

- It is not a problem if the lock stays allocated,
should the enclosing transaction rollback. The lock
will likely be needed later on anyway.

- It is not a problem if a transaction creates
the lock and finds it already requested when
trying to request it.

- My tests show a slowdown of 0.1 ms when using an
autonomous transaction - negligeable in my context.

However, Tom Kytes is so suspicious of autonomous
transactions that I would like to have your opinion.

- Is this a valid use of autonomous transactions ?
- Any problems in the design ?
- Other caveats ?

Oracle 8.1.7 (yes :-) and later.

Thanks *a lot*

--- Raoul

P.S. While not our focus right now, we may revisit
the committing scheme later on, and opinions would
be welcomed too.


Reply With Quote
  #2  
Old   
vc
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 05:19 AM







hasta_l3 (AT) hotmail (DOT) com wrote:
Quote:
Dear group,

We have lists. Each list has thousands of
ordered lines. Lists are implemented with
the usual master/detail tables.

An operation O may process (a subset of the
fields of) the lines of a list.

Operations must be serialized, so that not
two of them process the same list at the
same time.

However, other transations may want to modify
other fields of the lines of a list being processed,
and must not be blocked more than 3 secs.
However, an operation may need a few minutes
to complete.

Operations process only active lists, and there
is at most 100 active lists in a given day. Lists
become inactive after one day after, and new
lists are created.

In the current design, an operation notably :

- acquires a list lock by setting a flag in the
list header row, then commits.
Why commit at this stage ? Just select for update would be enough.
All other concurrent sessions would wait when trying to select for
update.

Quote:
- processes each line and commits.

I assume it commits after processing all the lines. If not, then
you'd want to (select for update; process a line; commit


Quote:
- resets the flag, and commits.
No need to reset any flags, just commit.

Quote:
Of course, each operation first look (for update)
whether the flag is set.
Other concurrent sessions would wait on select for update.

Quote:
This design fails miserably if the session
holding the flag crashes.
If the session crashes, the select for update lock will be released.

Dbms_lock is not needed in this scenario.

Quote:
I though that a dbms_lock would be a perfect
replacement for the flag locking scheme, since :

- the lock can persist across transactions.

- it will be released if the session crashes.

The lock would be allocated the first time it
is needed by an operation O; named after the
(qualified) primary key of the serialized list
header row for easy retrieval; and have a retention
delay of one day.

The problem is that dbms_lock.allocate_unique
(understandably) does commit. That is troublesome,
because the beginning of an operation must be
atomic.

Therefore, I'm thinking of calling allocate_unique
in an autonomous transaction. The dbms_lock.request
would still be called in the enclosing transaction.

I cannot find a problem with this scheme :

- It is not a problem if the lock stays allocated,
should the enclosing transaction rollback. The lock
will likely be needed later on anyway.

- It is not a problem if a transaction creates
the lock and finds it already requested when
trying to request it.

- My tests show a slowdown of 0.1 ms when using an
autonomous transaction - negligeable in my context.

However, Tom Kytes is so suspicious of autonomous
transactions that I would like to have your opinion.

- Is this a valid use of autonomous transactions ?
- Any problems in the design ?
- Other caveats ?

Oracle 8.1.7 (yes :-) and later.

Thanks *a lot*

--- Raoul

P.S. While not our focus right now, we may revisit
the committing scheme later on, and opinions would
be welcomed too.


Reply With Quote
  #3  
Old   
hasta_l3@hotmail.com
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 06:55 AM



vc wrote :

Quote:
hasta_l3 (AT) hotmail (DOT) com wrote:
Dear group,

We have lists. Each list has thousands of
ordered lines. Lists are implemented with
the usual master/detail tables.

An operation O may process (a subset of the
fields of) the lines of a list.

Operations must be serialized, so that not
two of them process the same list at the
same time.

However, other transations may want to modify
other fields of the lines of a list being processed,
and must not be blocked more than 3 secs.
However, an operation may need a few minutes
to complete.

Operations process only active lists, and there
is at most 100 active lists in a given day. Lists
become inactive after one day after, and new
lists are created.

In the current design, an operation notably :

- acquires a list lock by setting a flag in the
list header row, then commits.

Why commit at this stage ?
Because the transactions that cannot wait more than
3 secs may also change some (unrelated) field of the
list header row.

I forgot to mention that, sorry.



Quote:
Just select for update would be enough.
All other concurrent sessions would wait when trying to select for
update.


- processes each line and commits.


I assume it commits after processing all the lines. If not, then
you'd want to (select for update; process a line; commit
No, an operation commits after having processed each line,
so that other unrelated transactions are not blocked.

However, the operation O must still be atomic with regard
to the other operations O (for a given list).

More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.


Quote:

- resets the flag, and commits.

No need to reset any flags, just commit.


Of course, each operation first look (for update)
whether the flag is set.

Other concurrent sessions would wait on select for update.


This design fails miserably if the session
holding the flag crashes.

If the session crashes, the select for update lock will be released.

Dbms_lock is not needed in this scenario.


I though that a dbms_lock would be a perfect
replacement for the flag locking scheme, since :

- the lock can persist across transactions.

- it will be released if the session crashes.

The lock would be allocated the first time it
is needed by an operation O; named after the
(qualified) primary key of the serialized list
header row for easy retrieval; and have a retention
delay of one day.

The problem is that dbms_lock.allocate_unique
(understandably) does commit. That is troublesome,
because the beginning of an operation must be
atomic.

Therefore, I'm thinking of calling allocate_unique
in an autonomous transaction. The dbms_lock.request
would still be called in the enclosing transaction.

I cannot find a problem with this scheme :

- It is not a problem if the lock stays allocated,
should the enclosing transaction rollback. The lock
will likely be needed later on anyway.

- It is not a problem if a transaction creates
the lock and finds it already requested when
trying to request it.

- My tests show a slowdown of 0.1 ms when using an
autonomous transaction - negligeable in my context.

However, Tom Kytes is so suspicious of autonomous
transactions that I would like to have your opinion.

- Is this a valid use of autonomous transactions ?
- Any problems in the design ?
- Other caveats ?

Oracle 8.1.7 (yes :-) and later.

Thanks *a lot*

--- Raoul

P.S. While not our focus right now, we may revisit
the committing scheme later on, and opinions would
be welcomed too.


Reply With Quote
  #4  
Old   
vc
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 09:15 AM




hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
Quote:
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.
So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?



Reply With Quote
  #5  
Old   
hasta_l3@hotmail.com
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 09:32 AM



vc wrote :

Quote:
hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.

So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?
Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.



Reply With Quote
  #6  
Old   
DA Morgan
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 10:04 AM



hasta_l3 (AT) hotmail (DOT) com wrote:
Quote:
vc wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.
So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?

Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.
Look up PRAGMA AUTONOMOUS_TRANSACTION. It may help.
--
Daniel A. Morgan
University of Washington
damorgan@x.washington.edu
(replace x with u to respond)
Puget Sound Oracle Users Group
www.psoug.org


Reply With Quote
  #7  
Old   
vc
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 10:28 AM




hasta_l3 (AT) hotmail (DOT) com wrote:
Quote:
vc wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.

So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?

Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.
If you want to increase concurrency *and* part (a) is independent from
part (b), then you can split the long transaction into two
transactions (obviously) with part (b) doing the same as your short
transactions in terms of updating the children table. If part(a) and
part(b) must be in the single transaction, then you have to live with
the fact that the smaller transactions may be blocked by the longer
ones. It just does not matter what locking mechanism you might want
use as long as the access needs to be serialized in order for the
changes to be consistent.



Reply With Quote
  #8  
Old   
hasta_l3@hotmail.com
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 10:42 AM



DA Morgan wrote :

Quote:
hasta_l3 (AT) hotmail (DOT) com wrote:
vc wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.
So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?

Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.

Look up PRAGMA AUTONOMOUS_TRANSACTION. It may help.
Yes, Daniel. Autonomous transactions were actually the
main question of my initial (very long :-) post.

But here you do suggest to (1) have the main transaction
lock the list header row, and (2) modify and commit each
list line row in its own autonomous transaction, right ?

It will work, I think, but I dont see how it is much different
from my proposed scheme to (1) lock the list header row with
a dbms_lock, and (2) modify and commit each list line
row in the main transaction(s).

One scheme may be better than the other, but I really cannot
see which or why.

Incidentally, reifying the list/line relationship into its own table
might perhaps be an appealling design. The short transactions
would modify the list line rows, and the long restructuring
transaction would modify the relationship table rows.

Unfortunatly, I cannot contemplate to make *that* kind of
change right now...



Reply With Quote
  #9  
Old   
DA Morgan
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 01:10 PM



hasta_l3 (AT) hotmail (DOT) com wrote:
Quote:
DA Morgan wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
vc wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.
So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?
Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.
Look up PRAGMA AUTONOMOUS_TRANSACTION. It may help.

Yes, Daniel. Autonomous transactions were actually the
main question of my initial (very long :-) post.

But here you do suggest to (1) have the main transaction
lock the list header row, and (2) modify and commit each
list line row in its own autonomous transaction, right ?

It will work, I think, but I dont see how it is much different
from my proposed scheme to (1) lock the list header row with
a dbms_lock, and (2) modify and commit each list line
row in the main transaction(s).

One scheme may be better than the other, but I really cannot
see which or why.

Incidentally, reifying the list/line relationship into its own table
might perhaps be an appealling design. The short transactions
would modify the list line rows, and the long restructuring
transaction would modify the relationship table rows.

Unfortunatly, I cannot contemplate to make *that* kind of
change right now...
The difference is that you can commit in the autonomous
transactions and not commit the main transaction. Something
that is different from what you get using DBMS_LOCK.
--
Daniel A. Morgan
University of Washington
damorgan@x.washington.edu
(replace x with u to respond)
Puget Sound Oracle Users Group
www.psoug.org


Reply With Quote
  #10  
Old   
hasta_l3@hotmail.com
 
Posts: n/a

Default Re: dbms_lock.allocate_unique and autonomous transactions (long) - 11-01-2006 , 01:39 PM



DA Morgan wrote :
Quote:
hasta_l3 (AT) hotmail (DOT) com wrote:
DA Morgan wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
vc wrote :

hasta_l3 (AT) hotmail (DOT) com wrote:
[...]
More concretely, the whole list structure is being changed,
and the change should be atomic with regard to other
operations that may also change the structure. However,
the short transactions - which dont care about the structure -
should not block.
So only the transactions modifying the entire list would select for
update the list header and therefore be executed serially, the
smaller transactions that do not care about the list structure would
proceed in the usual way without locking the header first. What is the
problem ?
Assume a (long) restructuring operation L modifies
(a) some fields of the list header row in the master table, then
(b) some fields of every list line row in the children table, including
-say - row R.

Assume that a short transaction S modifies
(a) some (other) fields of the list line row R.

If L is in a single long transaction, then it will block S if S happens
to want to modify R after L did it.
Look up PRAGMA AUTONOMOUS_TRANSACTION. It may help.

Yes, Daniel. Autonomous transactions were actually the
main question of my initial (very long :-) post.

But here you do suggest to (1) have the main transaction
lock the list header row, and (2) modify and commit each
list line row in its own autonomous transaction, right ?

It will work, I think, but I dont see how it is much different
from my proposed scheme to (1) lock the list header row with
a dbms_lock, and (2) modify and commit each list line
row in the main transaction(s).

One scheme may be better than the other, but I really cannot
see which or why.

Incidentally, reifying the list/line relationship into its own table
might perhaps be an appealling design. The short transactions
would modify the list line rows, and the long restructuring
transaction would modify the relationship table rows.

Unfortunatly, I cannot contemplate to make *that* kind of
change right now...

The difference is that you can commit in the autonomous
transactions and not commit the main transaction. Something
that is different from what you get using DBMS_LOCK.
--
Yes. While the difference is unimportant (as of now) in my context,
and using a lock minimizes the amount of changes, your suggestion
as a "smell" of rigor and elegance that I like a lot... I will very
seriously consider it. Thanks.

Any known caveat on a massive use of autonomous transactions ?
(8.1.7 and later...)

--- Raoul



Reply With Quote
Reply




Thread Tools
Display Modes

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

vB code is On
Smilies are On
[IMG] code is On
HTML code is Off



Powered by vBulletin Version 3.5.3
Copyright ©2000 - 2012, Jelsoft Enterprises Ltd.