Hi Charles, Thanks for your idea and code snippets. I'll try if this helps in my cases. I have a feeling it won't, though. In the A->B example reorder() doesn't change the initial order, so calling it twice won't either. But now I have a whole weekend ahead to spoil with thinking about this problem :-)
Cheers, Gerhard Charles Anthony <[EMAIL PROTECTED]> 17.10.2003 14:49 Bitte antworten an "OJB Users List" An: 'OJB Users List' <[EMAIL PROTECTED]> Kopie: Thema: RE: ODMG: ObjectEnvelopeTable.reorder Hi, I, too, have had problems with this algorithm - and, it is not just deletes that have a problem - my FK violations actually happen on an insert update. My particular scenario was solved by calling re-order twice. I then patched my local copy to call re-order until no changes were performed. This worked absolutely fine - until we found a 1-1 relationship in our app( A<->B in your example) - this caused the ObjectEnvelope.commit() to hang. Our workaround - and it's working for us - follows. We've changed reorder() to return true if any changes occured when during the reorder.We then changed commit to repeatedly call reorder until either a) no more changes occured or b) reorder had be called 'N' times. So far, N=5 is OK for our application. The General Gist of the changes are here : if you'd like a copy of the .java file, just give me a shout : the apache mailing list s/w will reject it as an attachment. Hoever, I don't think this the *right* solution in general - but I know the right solution/algorithm is almost certainly very complex, and I'm not bright enough to spot/design/write it. Cheers, Charles ObjectEnvelope.java : public void commit(){ ... // 2. Repeatedly reorder objects until no changes occur OR we've sorted more than the maximum number of times. // If you get a foreign-key constraint error when the tx is committed, try increasing the MAX_SORT_COUNT. int sortCount = 0; boolean changeOccured = false; do { changeOccured = reorder(); sortCount++; } while(changeOccured && sortCount < MAX_SORT_COUNT); if (log.isDebugEnabled() && changeOccured){ log.debug("Changes still occurring after "+ MAX_SORT_COUNT + " reorders. Committing anyway."); } ... } private boolean reorder() throws IllegalAccessException { boolean orderChanged = false; if(needsCommit){ [... As Before ...] /* Let's find out if anything changed places */ for(int i=0; i< vNewVector.size() && !orderChanged; i++){ Identity id = (Identity) vNewVector.get(i); Integer oldPosition = (Integer) htOldVectorPosition.get(id); if(oldPosition.intValue()!=i){ orderChanged=true; } } mvOrderOfIds = vNewVector; mhtObjectEnvelopes = htNewHashtable; } return orderChanged; } > -----Original Message----- > From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] > Sent: 17 October 2003 13:26 > To: 'OJB Users List' > Subject: ODMG: ObjectEnvelopeTable.reorder > > > Hi, > > Since I am having problems with referential integrity violations when > deleting objects I tried to understand the reorder() method in > org.apache.ojb.odmg.ObjectEnvelopeTable. > > From what I understand, the way this reordering is > implemented leads to a > strong bias of the final order towards the initial order. And > the initial > order results from the order in which TransactionImpl.register() adds > objects to the ObjectEnvelopeTable. This initial order is > good for inserts > and updates, but bad for deletes. And the current reorder > method cannot > resolve this anymore. > > A simple example: > > Say object A has a reference to object B: > A->B. > When A receives a write lock, TransactionImpl will first add its > references and then the object itself to the > ObjectEnvelopeTable. So we > have the order > [B,A]. > Now we say db.deletePersistent(A) and db.deletePersistent(B) (in any > order) and commit. The reorder method now first takes B, > finds it needs > deleting and that it has no references. So it just puts it > first into the > reordered list: > [B] > Now reorder() takes A, finds it also needs deleting and that it has a > reference to B. So it 'knows' that A should be deleted first > and adds A to > the vector. > [B,A] > Then it would add B after A to the vector, but B has already > been handled, > so it leaves it where it is. So we end up with the same order as > initially, which is the wrong order for deletes. > > I understand that in general there is no unique solution for > ordering the > objects so that no referential integrity contraints are violated (the > simple case A<->B is unsolvable). But my feeling is that > there should be a > better solution, which would at least resolve the simple A->B case > correctly. > > Is this a known problem? Are there any plans to improve on this? I'm > thinking of trying to work out a better solution, but > currently I'm not > sure how complex this would be. > > I'm looking forward to hearing opinions about this. > Gerhard > > This email and any attachments are strictly confidential and are intended solely for the addressee. If you are not the intended recipient you must not disclose, forward, copy or take any action in reliance on this message or its attachments. If you have received this email in error please notify the sender as soon as possible and delete it from your computer systems. Any views or opinions presented are solely those of the author and do not necessarily reflect those of HPD Software Limited or its affiliates. At present the integrity of email across the internet cannot be guaranteed and messages sent via this medium are potentially at risk. All liability is excluded to the extent permitted by law for any claims arising as a re- sult of the use of this medium to transmit information by or to HPD Software Limited or its affiliates. --------------------------------------------------------------------- To unsubscribe, e-mail: [EMAIL PROTECTED] For additional commands, e-mail: [EMAIL PROTECTED]