Subject | Re: [firebird-support] update, foreign keys, locking |
---|---|
Author | Helen Borrie |
Post date | 2003-07-17T07:59:57Z |
At 07:36 AM 17/07/2003 +0100, you wrote:
tiConsistency) readers will continue to see the last-committed versions of
both the parent and the dependent sets inside *their* transactions.
cannot tell in advance which column(s) each transaction will update - it
might be the linking key, or the row might even be deleted. So - with
optimistic locking - if your transaction manages to get the lock on the
master record, it means it also has locks on the dependent records, as long
as the DML stays pending.
exception and tell the user that someone else is already updating this set
of data.
nothing to the lock status of any row in the output set. It simply causes
the server to send over one row at a time and wait to be asked for the next
one. It does have a purpose when the SELECT output is assigned to a named
cursor - it makes it valid for subsequent UPDATE and DELETE statements to
be applied to the current row pointed to by the cursor, via a WHERE CURRENT
OF <cursorname> construction.
first served. You can read the set for ever and a day. Once you pick row
x and successfully request *any* sort of DML change to it, then row x and
all of its dependencies are protected, for whatever you want to do to them,
until the transaction ends.
You're treating it as "inconvenient" that one transaction is prevented from
deleting or changing rows that depend on a row that another transaction is
working on. It would be a heck of lot more "inconvenient" if transactions
were allowed to ignore the integrity rules.
enforced by the ways in which rows are related. In an optimistic locking
system, where no locks exist until the moment that a DML request succeeds,
there is no room for the engine to guess the mind of the user. *You* are
choosing to crag up the dependencies by using pessimistic locking. That's
the price you pay for going against the optimistic model.
but force a pessimistic lock the moment a user starts editing a row -
apparently to avoid deadlocks!! - then you don't really understand how
optimistic locking works (or you do understand it but prefer to avoid
handling concurrency conflicts!). Pessimistic locking doesn't fit into the
optimistic locking model. Your client-side pess. locking is a hack for the
rare conditions when it is desirable. If you want to use it in unintended
ways so you don't have to handle any deadlocks, then you gets what you pays
for.
I've said it before and I'm saying it again - a deadlock is NOT a
problem. It is a database condition which the server conveniently signals
back to the client for immediate handling. Deadlocks are MEANT to
happen. Developers of client/server applications are MEANT to manage them.
Helen
>Unless I'm just off my rocker, I seem to remember that if you startYes. This is what referential integrity is for.
>updating a row, rows referenced
>by foreign key values will also get locked on that same transaction
> (or at least attempt to do so -- some sort of read-lock?)No: it's a write lock. Unless isolation is TABLE STABILITY (i.e.
tiConsistency) readers will continue to see the last-committed versions of
both the parent and the dependent sets inside *their* transactions.
>In our case, this meant that if you're in the middle of updatingTrue. Because the DB does not support column-level locking. The engine
>someone's SSN, and you try to also update their address (popup-screen of
>dependent record on a
>different transaction) you'll get a deadlock (we use NOWAIT, so it's at
>least not too irritating.)
cannot tell in advance which column(s) each transaction will update - it
might be the linking key, or the row might even be deleted. So - with
optimistic locking - if your transaction manages to get the lock on the
master record, it means it also has locks on the dependent records, as long
as the DML stays pending.
>(when someone starts editing, we explicitely do 'update {tablename} set idNOWAIT is correct for this - all the app has to do is catch the lock
>= id where id = {value}' -- this conflicts with parent records already
>being edited.
exception and tell the user that someone else is already updating this set
of data.
>as we've already selected the data, we don't bother reselecting 'for update'.)Selecting 'for update' in an ordinary SELECT statement does absolutely
nothing to the lock status of any row in the output set. It simply causes
the server to send over one row at a time and wait to be asked for the next
one. It does have a purpose when the SELECT output is assigned to a named
cursor - it makes it valid for subsequent UPDATE and DELETE statements to
be applied to the current row pointed to by the cursor, via a WHERE CURRENT
OF <cursorname> construction.
>We've not really minded ... but I was wondering if someone could give meIt's very simple - it's an optimistic row-level locking model: first come,
>the theory behind this?
first served. You can read the set for ever and a day. Once you pick row
x and successfully request *any* sort of DML change to it, then row x and
all of its dependencies are protected, for whatever you want to do to them,
until the transaction ends.
You're treating it as "inconvenient" that one transaction is prevented from
deleting or changing rows that depend on a row that another transaction is
working on. It would be a heck of lot more "inconvenient" if transactions
were allowed to ignore the integrity rules.
>Why would you automatically lock rows referenced (such as master records)"Related" is the key concept here. The integrity of relationships is
>when updating others (dependent records)? Is it necessary to reduce
>logical errors from multiple transactions competing for resources that
>aren't the identical, but related?
enforced by the ways in which rows are related. In an optimistic locking
system, where no locks exist until the moment that a DML request succeeds,
there is no room for the engine to guess the mind of the user. *You* are
choosing to crag up the dependencies by using pessimistic locking. That's
the price you pay for going against the optimistic model.
>In case it matters, methinks we're still running 1.0.2 ... and of course,I think if you have made it so that your DML requests never done anything
>again, I could just be remembering incorrectly.
but force a pessimistic lock the moment a user starts editing a row -
apparently to avoid deadlocks!! - then you don't really understand how
optimistic locking works (or you do understand it but prefer to avoid
handling concurrency conflicts!). Pessimistic locking doesn't fit into the
optimistic locking model. Your client-side pess. locking is a hack for the
rare conditions when it is desirable. If you want to use it in unintended
ways so you don't have to handle any deadlocks, then you gets what you pays
for.
I've said it before and I'm saying it again - a deadlock is NOT a
problem. It is a database condition which the server conveniently signals
back to the client for immediate handling. Deadlocks are MEANT to
happen. Developers of client/server applications are MEANT to manage them.
Helen