Compartir a través de


Aplicar los cambios

Una vez que el proveedor de destino obtiene un lote de cambios y trata los conflictos, los cambios se deben aplicar a la réplica de destino. Esto normalmente se hace en el método ProcessChangeBatch (en el código administrado) o en el método ProcessChangeBatch (en el código no administrado) del proveedor de destino y se puede llevar a cabo con facilidad utilizando un objeto aplicador de cambios que proporciona Sync Framework.

Cómo se aplican los cambios

Una vez que el proveedor de destino obtiene el lote de cambios del proveedor de origen, aplica los cambios en la réplica de destino. Para obtener un objeto aplicador de cambios que Sync Framework proporciona, se puede crear un objeto NotifyingChangeApplier (en el código administrado) o llamar al método IProviderSyncServices::CreateChangeApplier (en el código no administrado). El método ApplyChanges (en el código administrado) o el método ApplyChanges (en el código no administrado) detecta los conflictos y llama a los métodos en el proveedor de destino para aplicar los cambios a la réplica de destino.

Procesar un elemento de cambio

Para procesar un elemento de cambio típico, el aplicador de cambios primero llama al método ISynchronousDataRetriever::LoadChangeData (en el código administrado) o al método LoadChangeData (en el código no administrado) en el proveedor de origen con el fin de iniciar la transferencia de datos. Este método devuelve una interfaz IUnknown (en el código administrado) o object (en el código no administrado) que representa el mecanismo de transferencia de datos. A continuación, el aplicador de cambios llama al método ISynchronousNotifyingChangeApplierTarget::SaveChange (en el código administrado) o al método SaveItemChange (en el código no administrado) en el proveedor de destino y pasa el objeto de transferencia de datos como parte del contexto para guardar el cambio. El proveedor de destino puede entonces transferir los datos a la réplica de destino. Cualquier error al obtener los datos o procesar los cambios se indica utilizando el método ISaveChangeContext::SetRecoverableErrorOnChange (en el código administrado) o el método RecordRecoverableErrorForItem (en el código no administrado). Este método registra un error recuperable para este elemento en el objeto de conocimientos aprendidos que se incluye en el lote de cambios. Alternativamente, cuando se usan los conflictos de restricción, llame a RecordConstraintConflictForItem (para el código administrado) o a ISaveChangeContext2::SetConstraintConflictOnChange (para el código no administrado) para informar de un conflicto de restricción. Después se podrá resolver el conflicto de restricción tal como lo especifique la aplicación o el proveedor.

Actualizar los conocimientos aprendidos

Mientras se aplican los cambios, el aplicador de cambios actualiza los conocimientos aprendidos que el lote de cambios incluye. Los conocimientos aprendidos son los de la réplica de origen proyectados en los cambios del lote de cambios y representan lo que la réplica de destino aprenderá cuando aplique todos los cambios en el lote de cambios. Los conocimientos aprendidos se actualizan de las maneras siguientes:

  • Si solo se aplicó un subconjunto de cambios debido a interrupciones o cancelaciones, el aplicador de cambios utiliza el operador de proyecto para restringir el conocimiento únicamente al conjunto de cambios que se aplicó.

  • Si no se pueden aplicar algunos cambios, el aplicador de cambios también los excluye de los conocimientos.

Tenga en cuenta que los implementadores del proveedor no tienen que realizar estas operaciones de proyecto, unión y exclusión manualmente. Esto se debe a que el aplicador de cambios los realiza en nombre del proveedor.

Guardar el conocimiento del destino actualizado

Una vez actualizados los conocimientos aprendidos, se combinan con los conocimientos de la réplica de destino. El proveedor de destino debe reemplazar los conocimientos de la réplica de destino con estos conocimientos de forma indivisible. Esta atomicidad se puede lograr guardando los conocimientos actualizados solo una vez para cada lote si todos los cambios de un lote se aplican dentro de una única transacción. El aplicador del cambio ayuda llamando al método ISynchronousNotifyingChangeApplierTarget::SaveKnowledge (en el código no administrado) o al método StoreKnowledgeForScope (en el código administrado) en el proveedor de destino al final de cada lote. Los conocimientos que se pasan a este método son los conocimientos actualizados que se van a aplicar a la réplica de destino. O bien, el proveedor de destino puede llamar al método ISaveChangeContext::GetKnowledgeForScope (en el código administrado) o al método GetUpdatedDestinationKnowledge (en el código no administrado) para obtener el conocimiento actualizado.

Cuando los proveedores utilizan unidades de cambio para representar los subelementos, hay algunas diferencias en la manera en que se aplican los cambios. Para obtener más información, vea Sincronizar las unidades de cambio.

Consideraciones especiales para las réplicas jerárquicas

La sincronización de réplicas jerárquicas puede encontrar ciertas complicaciones que se deben al procesamiento por lotes de los conjuntos de cambios del origen al destino. Sync Framework no admite el concepto de jerarquía de datos. Por consiguiente, toda la responsabilidad de tratar estas situaciones correctamente recae en los proveedores.

La complicación más común es el orden de las relaciones entre elementos primarios y secundarios en las operaciones de actualización. Por ejemplo, considere el escenario siguiente:

  1. La réplica de origen ha creado una carpeta nueva y un conjunto de elementos nuevos dentro de ella.

  2. El proveedor de destino solicita los cambios del proveedor de origen. El proveedor de origen envía su lista de cambios en dos lotes. Sin embargo, el lote de cambios que contiene la creación de la carpeta primaria llega después del lote de cambios que contiene los elementos secundarios.

  3. El proveedor de destino debe decidir dónde almacenar el conjunto de elementos que han llegado en el primer lote, porque la información sobre dónde almacenarlos no llegará hasta el segundo lote.

Reducir las actualizaciones jerárquicas

Si hay actualizaciones, la manera más simple de reducir las complejidades de las relaciones entre los elementos primarios y secundarios es hacer que el proveedor de origen sea el responsable de ordenar los identificadores globales. De esta manera, los elementos primarios siempre llegan antes que sus elementos secundarios.

Cuando los proveedores de destino se ocupen de la transmisión de las actualizaciones que se realizan en un almacén jerárquico, podrían recibir desordenadas las relaciones entre los elementos primarios y secundarios. Los proveedores de destino deben poder recuperarse de esta situación quitando el cambio desordenado y anotando una excepción en sus conocimientos, o poniendo en la cola el cambio que se va a aplicar después. Dado que el tamaño de los elementos podría ser grande, la solución más efectiva probablemente sea quitar el cambio y anotar excepciones de conocimiento.

Reducir las eliminaciones jerárquicas

Los proveedores de destino determinan si un elemento es un elemento contenedor. En los contenedores vacíos, las eliminaciones se pueden producir inmediatamente. Sin embargo, si el contenedor tiene elementos que no han sido marcados para eliminarse, el proveedor tiene las opciones siguientes:

  • Poner en la cola las eliminaciones para procesarlas después. Una vez que todos los elementos secundarios del contenedor se hayan marcado para eliminarse, se puede activar la eliminación real.

  • Quitar esta solicitud y establecer una excepción en los conocimientos para indicar la recepción desordenada de un elemento.

Para tratar escenarios en los que primero se elimina un elemento principal de la jerarquía y posteriormente se agrega un elemento secundario, se sigue la regla siguiente: las eliminaciones en cola solo son válidas hasta el final de una sesión de procesamiento de pares y no se mantienen entre los participantes.

Vea también

Referencia

Interfaz ISynchronousNotifyingChangeApplier
ISynchronousNotifyingChangeApplierTarget::SaveKnowledge
Interfaz ISynchronousDataRetriever
Interfaz ISaveChangeContext
NotifyingChangeApplier
StoreKnowledgeForScope
IChangeDataRetriever
SaveChangeContext

Conceptos

Implementar un proveedor estándar personalizado