none
Synchronizing data that was out of filter criteria but later moved in to the filter RRS feed

  • Question

  • I have on ORDER table with fields Id, State, ModifiedDate. State can be 'new', 'in process', 'complete', 'cancelled'.
    My filter criteria is: WHERE State <> 'complete' AND ModifiedDate > getdate()-1  (This means that I want to sync all orders to SQL CE 3.5 SP1 except for completed ones AND for the completed orders, I only want to sync those that have been modified today.) My Server is SQL Server 2008 and sync is bi-directional. 

    This works fine in normal scenario. I am facing issue in a specific scenario.
    Say Order 1 was 'complete' on day X. For existing users of the system, this order is synced through its lifecycle (new, in process, complete). However, if a new user of the system starts on day X+1, the filter criteria will prevent this order to be downloaded in that user's CE. This is as designed and expected. Now, if for some reason, another user who can see this order, modifies the order which results into ModifiedDate = getdate(); and hence the second part of the filter criteria is not satisfied. I would expect that on next sync for this table, this order should get synced to the new user.

    What  I observe instead is that sync framework is detecting this change as an 'update' and not as an 'insert' on local CE of the new user. And of course, the update query does not do anything since original order was never present for that user. Note that for other existing users this works fine.

    Any ideas on what I could be doing wrong OR how this can be achieved differently?







    Monday, January 11, 2010 11:39 AM

Answers

  • Please try to add this one before call Synchronize().

    clientProvider.ConflictResolver.ClientDeleteServerUpdateAction = ResolveAction.FireEvent;

    You may also use this kind of coding to handle other conflicts through event handler such as

    clientProvider.ConflictResolver.ClientUpdateServerUpdateAction = ResolveAction.FireEvent;
    clientProvider.ConflictResolver.ClientInsertServerInsertAction = ResolveAction.FireEvent;
    clientProvider.ConflictResolver.ClientUpdateServerDeleteAction = ResolveAction.FireEvent;

    Thanks.
    Leo Zhou ------ This posting is provided "AS IS" with no warranties, and confers no rights.
    Wednesday, January 13, 2010 5:58 PM
    Answerer

All replies

  • 1. What you observed is the right behavior, the enumeration should be update not insert.
    2. Therefore the practical question goes to how to make this update to become an insert on the client provider.  Have a DownloadChangeFailed event handler connected to the client provider.  In this event handler, please try 2 things
       a. set e.Action = ApplyAction.RetryWithForceWrite;
       or
       b. insert a dummy row with the PK of the [updated] row from server to the client and then do e.Action = ApplyAction.RetryApplyingRow;  make sure when doing insert, using the same transaction as e.Transaction.

    Thanks.

    Leo Zhou ------ This posting is provided "AS IS" with no warranties, and confers no rights.
    Monday, January 11, 2010 6:25 PM
    Answerer
  • I will try and let you know if any of the two worked for me.
    Tuesday, January 12, 2010 10:12 AM
  • It should be ApplyChangeFailed event.
    Leo Zhou ------ This posting is provided "AS IS" with no warranties, and confers no rights.
    Tuesday, January 12, 2010 7:58 PM
    Answerer
  • Hi Leo, I am working with Nitesh on this problem.
    We have tried option 'a', but in our case it does not work, becuase 'update' can not be forced  on CE as there was no row inserted into the CE database with the primary key that is coming as an update changeset only (never came as insert changeset from server).
    Similarly option 'b' suggested by you also doesn't work for us, as the sync doesn't raise 'ApplyChangeFailed' event in our scenario because it does not consider it as failure. I guess its because sync is able to run update query successfully though without any effect.

    Any idea, how I can catch this scenario in sync so that I can insert the dummy record to try out option 'b'.

    Thanks,
    Sumit 

    Wednesday, January 13, 2010 3:40 PM
  • Please try to add this one before call Synchronize().

    clientProvider.ConflictResolver.ClientDeleteServerUpdateAction = ResolveAction.FireEvent;

    You may also use this kind of coding to handle other conflicts through event handler such as

    clientProvider.ConflictResolver.ClientUpdateServerUpdateAction = ResolveAction.FireEvent;
    clientProvider.ConflictResolver.ClientInsertServerInsertAction = ResolveAction.FireEvent;
    clientProvider.ConflictResolver.ClientUpdateServerDeleteAction = ResolveAction.FireEvent;

    Thanks.
    Leo Zhou ------ This posting is provided "AS IS" with no warranties, and confers no rights.
    Wednesday, January 13, 2010 5:58 PM
    Answerer
  • Hi Leo,

    I have tried this with SyncFx2.0 and there the event type is LocalCleanedupDeleteRemoteUpdate, and it worked.

    Thanks
    Sumit
    Wednesday, January 27, 2010 7:05 PM