Partilhar via


Como filtrar unidades de alteração enumeradas

Este tópico descreve como usar uma linguagem gerenciada para filtrar as unidades de alteração enumeradas por um provedor de sincronização do Sync Framework que sincroniza dados de um repositório de dados personalizado.

Este tópico pressupõe uma familiaridade básica com os conceitos de C# e do Microsoft .NET Framework.

Os exemplos deste tópico se concentram nas classes e membros do Sync Framework a seguir:

Entendendo a filtragem de unidade de alteração

Os filtros de unidade de alteração restringem os dados de sincronização a um subconjunto de unidades de alteração, como sincronizar apenas os campos de nome e número de telefone de um contato, ignorando as unidades de alteração restantes. Um filtro de unidade de alteração é útil quando uma réplica armazenar apenas um subconjunto das unidades de alteração definido para os itens no escopo.

O Sync Framework fornece o objeto ChangeUnitListFilterInfo para definir a lista de unidades de alteração a serem incluídas em uma enumeração de alteração. O filtro pode ser definido pelo aplicativo de sincronização usando qualquer mecanismo apropriado entre o aplicativo e o provedor, ou pode ser negociado entre os dois provedores. Para obter mais informações sobre negociação de filtros, consulte Filtrando dados de sincronização.

Quando um filtro de unidade de alteração é definido, o Sync Framework solicita dados apenas para as unidades de alteração que estão no filtro quando chama o LoadChangeData do provedor de origem.

O provedor de destino recebe e aplica alterações da mesma forma que era feito para um lote de alterações padrão, a não ser que os dados enviados a SaveChangeWithChangeUnits contenham somente as unidades de alteração que estão no filtro.

Requisitos de compilação

Exemplo

O código de exemplo neste tópico mostra como usar o serviço de armazenamento de metadados para gerar um lote de alterações que filtra unidades de alteração que são incluídas no lote de alterações. A réplica deste exemplo é um arquivo de texto que armazena informações de contato como uma lista de valores separados por vírgula. Os itens a serem sincronizados são os contatos contidos nesse arquivo. O filtro é definido para incluir apenas os campos nome e número de telefone do contato.

Definindo o filtro

O provedor de origem implementa um método público que permite ao aplicativo estabelecer um filtro de unidade de alteração que define quais campos de contato incluir ao enumerar alterações.

public void SetContactFieldsToInclude(Contact.ChangeUnitFields[] includedFields)
{
    // Translate the array of fields to a list of IDs.
    _includedChangeUnits = new List<SyncId>(includedFields.Length);
    for (int iField = 0; iField < includedFields.Length; iField++)
    {
        _includedChangeUnits.Add(new SyncId((byte)includedFields[iField]));
    }

    _isFiltered = true;
}

O aplicativo de sincronização cria o provedor de origem como o provedor local e usa o método SetContactFieldsToInclude para especificar que apenas os campos nome e número de telefone sejam incluídos ao enumerar alterações. O aplicativo também cria o provedor de destino e executa a sincronização.

private void SynchronizeWithChangeUnitFiltering(ContactStore localStore, ContactStore remoteStore, SyncDirectionOrder syncDir)
{
    // Create the local provider and set the change unit filter.
    // The filter is ignored when the provider is the destination provider.
    SyncProvider localProvider = new ContactsProviderChangeUnitFiltering(localStore);
    // Only include name and phone number fields.
    Contact.ChangeUnitFields[] includedFields = new Contact.ChangeUnitFields[2];
    includedFields[0] = Contact.ChangeUnitFields.NameCU;
    includedFields[1] = Contact.ChangeUnitFields.PhoneCU;
    ((ContactsProviderChangeUnitFiltering)localProvider).SetContactFieldsToInclude(includedFields);

    // Create the remote provider and do not set a filter.
    SyncProvider remoteProvider = new ContactsProviderChangeUnitFiltering(remoteStore);

    // Create the synchronization orchestrator and set the providers and synchronization direction.
    SyncOrchestrator orchestrator = new SyncOrchestrator();
    orchestrator.LocalProvider = localProvider;
    orchestrator.RemoteProvider = remoteProvider;
    orchestrator.Direction = syncDir;

    string msg;
    try
    {
        // Synchronize data between the two providers.
        SyncOperationStatistics stats = orchestrator.Synchronize();

        // Display statistics for the synchronization operation.
        msg = "Synchronization succeeded!\n\n" +
            stats.DownloadChangesApplied + " download changes applied\n" +
            stats.DownloadChangesFailed + " download changes failed\n" +
            stats.UploadChangesApplied + " upload changes applied\n" +
            stats.UploadChangesFailed + " upload changes failed";
    }
    catch (Exception ex)
    {
        msg = "Synchronization failed! Here's why: \n\n" + ex.Message;
    }
    MessageBox.Show(msg, "Synchronization Results");
}

Enumerando um lote de alterações filtrado

O provedor de origem implementa GetChangeBatch de forma que, quando um filtro tiver sido especificado, ele usará o serviço de armazenamento de metadados para gerar um lote de alterações filtrado. Isso é feito pela criação de um objeto ChangeUnitListFilterInfo e inicializando-o com a lista especificada de unidades de alteração a serem incluídas. As informações do filtro são transmitidas ao método GetFilteredChangeBatch do objeto ReplicaMetadata. O serviço de armazenamento de metadados não precisa retornar a chamada ao provedor para determinar o que incluir no filtro, assim um null é especificado para o parâmetro filterCallback.

public override ChangeBatch GetChangeBatch(uint batchSize, SyncKnowledge destinationKnowledge, out object changeDataRetriever)
{
    // Return this object as the IChangeDataRetriever object that is called to retrieve item data.
    changeDataRetriever = this;

    ChangeBatch retrievedBatch;
    if (_isFiltered)
    {
        // Use the metadata storage service to get a filtered batch of changes.
        ChangeUnitListFilterInfo filterInfo = new ChangeUnitListFilterInfo(IdFormats, _includedChangeUnits, true);
        retrievedBatch = _ContactStore.ContactReplicaMetadata.GetFilteredChangeBatch(batchSize, destinationKnowledge,
            filterInfo, null);
    }
    else
    {
        // Use the metadata storage service to get a batch of changes.
        retrievedBatch = _ContactStore.ContactReplicaMetadata.GetChangeBatch(batchSize, destinationKnowledge);
    }

    return retrievedBatch;
}

Próximas etapas

Em seguida, você pode adicionar a negociação de filtro ao provedor, de forma que ele possa se comunicar com o provedor de destino a fim de estabelecer o filtro que deve ser usado para a enumeração de alterações. Para obter mais informações sobre como negociar filtros, consulte Como negociar um filtro.

Consulte também

Outros recursos

Programando tarefas comuns do provedor personalizado padrão

Filtrando dados de sincronização