The following example catches an optimistic locking failure, identifies the enterprise objects involved in the failure, identifies the values of the enterprise objects involved in the failure, and attempts to commit those values to the database.
Listing 8-4 Managing an optimistic locking failure by last write wins
//Deal with an optimistic locking failure. |
public void handleOptimisticLockingFailureByLastWriteWins(EOGeneralAdaptorException lockingException) { |
//Get the info dictionary that is created when the exception is thrown. |
NSDictionary info = lockingException.userInfo(); |
//Determine the adaptor operation that triggered the optimistic locking failure. |
EOAdaptorOperation adaptorOperation = (EOAdaptorOperation)info.objectForKey(EOAdaptorChannel.FailedAdaptorOperationKey); |
int operationType = adaptorOperation.adaptorOperator(); |
//Determine the database operation that triggered the failure. |
EODatabaseOperation dbOperation = (EODatabaseOperation)info.objectForKey(EODatabaseContext.FailedDatabaseOperationKey); |
//Retrieve the enterprise object that triggered the failure. |
EOEnterpriseObject failedEO = (EOEnterpriseObject)dbOperation.object(); |
//Retrieve the dictionary of values involved in the failure. |
NSDictionary valuesInFailedSave = adaptorOperation.changedValues();// 1 |
NSLog.out.appendln("valuesInFailedSave: " + valuesInFailedSave); |
//Take action based on the type of adaptor operation that triggered the optimistic locking failure. |
if (operationType == EODatabaseOperation.AdaptorUpdateOperator) { |
//Recover by essentially ignoring the optimistic locking failure and committing the |
//changes that originally failed. This is a last write wins policy. |
//Overwrite any changes in the database with the eo's values. |
failedEO.reapplyChangesFromDictionary(valuesInFailedSave); // 2 |
} else { //The optimistic locking failure was causes by another type of adaptor operation, not an update. |
throw new NSForwardException(lockingException, "Unknown adaptorOperator " + operationType + " in optimistic locking exception."); |
} |
session().defaultEditingContext().saveChanges(); |
} |
“Listing 9-4” differs from “Listing 9-3” only in code line 1 and code line 2. Code line 1 of “Listing 9-4” retrieves the values of the enterprise object that were involved in the optimistic locking failure. For example, if the enterprise object represents the Listing entity in the Real Estate model and the bedrooms attribute of that enterprise object had changes, the dictionary of changes retrieved in code line 1 contains a key called bedrooms and its changed in-memory value (not the attribute’s value in the database).
This dictionary is used in code line 2, which attempts to reapply the changes that failed to be committed. This approach is referred to as a “last write wins” approach because code line 2 commits the changes regardless of the values in the database. So if the optimistic locking failure was caused because another user or process changed the data in the database that corresponds to the edited enterprise object, code line 2 disregards those changes and writes the changes that failed in their place. This may or may not be a reasonable approach for your application.
Last updated: 2007-07-11