I'm using Seam and have many long running conversations running at the same time; each conversation is basically a windowed application. For example, I have a search component that lists entities. The user can select an entity and edit it in an editor component. More than that, they can open the same entity in multiple different conversations for editing. Also you can have multiple search components running with different search criteria.
I'm using gravity to push all updates from the server back to each client (i have no-local set to false) so i don't have to rely on the conversations merging their results into the global context (and subsequently all child contexts). I've extended the DataObserver class to force a new session id for each update so my local updates are not ignored and treated as external data:
override protected function messageHandler(event:MessageEvent):void {
log.debug("destination {0} message received {1}", meta_name, event.toString());
// Save the call context because data has not been requested by the current user
var savedCallContext:Object = _context.meta_saveAndResetCallContext();
var receivedSessionId:String = event.message.headers["GDSSessionID"] as String;
var updates:Array = event.message.body as Array;
_context.meta_handleUpdates(receivedSessionId + "_forceNew", updates);
_context.meta_handleUpdateEvents(updates);
_context.meta_restoreCallContext(savedCallContext);
}
What I would like to do is update the search contexts with the newest data but not the editing
contexts. Currently, every context gets updated if the entity is not dirty and I'd like to be able to ignore that on a per context basis. I would like to defer any updates to the context until the user hits "save" and gets an optimistic lock exception and is told to refresh the entity.
Temporarily I've added a property to BaseContext:
public function get meta_ignoreExternal () : Boolean
{
return _ignoreExternal;
}
public function set meta_ignoreExternal (ignoreExternal : Boolean) : void
{
_ignoreExternal = ignoreExternal;
}
and modified the EntityManager to take this into consideration when the external version is increased:
if (_mergeContext.externalData && _context.meta_ignoreExternal)
{
ignore = true;
}
else if (_mergeContext.externalData && _dirtyCheckContext.isEntityChanged(IEntity(dest)))
{
...
Then, somewhere in the conversational component:
context.meta_ignoreExternal = true;
Is this a possible feature to have? Am I missing anything that would break anything else? It also might be neat to have the user be able to turn this on or off.
One thing I did notice before adding this: accepting all server conflicts seems to be a little buggy with merging lists. I haven't found the exact cause but I also didn't see any test cases involving merging remote data with versioning into a conversation context. I was still getting an optimistic lock exception even after accepting all conflicts or if the local data wasn't dirty at all.