Partilhar via


Importar dados em massa para a conta do Azure Cosmos DB para NoSQL usando o SDK do .NET

APLICA-SE A: NoSQL

Este tutorial mostra como criar um aplicativo de console .NET que otimiza a taxa de transferência provisionada (RU/s) necessária para importar dados para o Azure Cosmos DB.

Neste artigo, você lerá dados de uma fonte de dados de exemplo e os importará para um contêiner do Azure Cosmos DB. Este tutorial usa a Versão 3.0+ do Azure Cosmos DB .NET SDK, que pode ser direcionado para .NET Framework ou .NET Core.

Este tutorial aborda:

  • Criando uma conta do Azure Cosmos DB
  • Configurando seu projeto
  • Conectando-se a uma conta do Azure Cosmos DB com suporte em massa habilitado
  • Executar uma importação de dados por meio de operações de criação simultâneas

Pré-requisitos

Antes de seguir as instruções neste artigo, certifique-se de que tem os seguintes recursos:

  • Uma conta ativa do Azure. Se não tiver uma subscrição do Azure, crie uma conta gratuita antes de começar.

    Você pode experimentar o Azure Cosmos DB gratuitamente, sem uma assinatura do Azure e sem necessidade de compromisso. Como alternativa, você pode criar uma conta de camada gratuita do Azure Cosmos DB, com os primeiros 1000 RU/s e 25 GB de armazenamento gratuitamente. Você também pode usar o emulador do Azure Cosmos DB com um URI de https://localhost:8081. Para obter a chave a ser usada com o emulador, consulte Autenticando solicitações.

  • NET Core 3 SDK. Você pode verificar qual versão está disponível em seu ambiente executando dotnet --version.

Passo 1: criar uma conta do Azure Cosmos DB

Crie uma conta do Azure Cosmos DB para NoSQL no portal do Azure ou você pode criar a conta usando o Emulador do Azure Cosmos DB.

Etapa 2: Configurar seu projeto .NET

Abra o prompt de comando do Windows ou uma janela do Terminal no computador local. Você executará todos os comandos nas próximas seções do prompt de comando ou terminal. Execute o seguinte comando dotnet new para criar um novo aplicativo com o nome bulk-import-demo.

dotnet new console -n bulk-import-demo

Altere seu diretório para a pasta do aplicativo recém-criada. Você pode criar o aplicativo com:

cd bulk-import-demo
dotnet build

A saída esperada da compilação deve ser algo como isto:

Restore completed in 100.37 ms for C:\Users\user1\Downloads\CosmosDB_Samples\bulk-import-demo\bulk-import-demo.csproj.
  bulk -> C:\Users\user1\Downloads\CosmosDB_Samples\bulk-import-demo \bin\Debug\netcoreapp2.2\bulk-import-demo.dll

Build succeeded.
    0 Warning(s)
    0 Error(s)

Time Elapsed 00:00:34.17

Etapa 3: Adicionar o pacote do Azure Cosmos DB

Enquanto ainda estiver no diretório do aplicativo, instale a biblioteca de cliente do Azure Cosmos DB para .NET Core usando o comando dotnet add package.

dotnet add package Microsoft.Azure.Cosmos

Etapa 4: Obter suas credenciais de conta do Azure Cosmos DB

O aplicativo de exemplo precisa se autenticar em sua conta do Azure Cosmos DB. Para autenticar, você deve passar as credenciais da conta do Azure Cosmos DB para o aplicativo. Obtenha suas credenciais de conta do Azure Cosmos DB seguindo estas etapas:

  1. Inicie sessão no portal do Azure.
  2. Navegue até sua conta do Azure Cosmos DB.
  3. Abra o painel Chaves e copie o URI e a CHAVE PRIMÁRIA da sua conta.

Se você estiver usando o Emulador do Azure Cosmos DB, obtenha as credenciais do emulador neste artigo.

Etapa 5: Inicializar o objeto CosmosClient com suporte à execução em massa

Abra o arquivo gerado Program.cs em um editor de código. Você criará uma nova instância do CosmosClient com a execução em massa habilitada e a usará para executar operações no Azure Cosmos DB.

Vamos começar substituindo o método padrão Main e definindo as variáveis globais. Essas variáveis globais incluirão as chaves de ponto de extremidade e autorização, o nome do banco de dados, o contêiner que você criará e o número de itens que você inserirá em massa. Certifique-se de substituir os valores de endpointURL e chave de autorização de acordo com seu ambiente.

using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Text.Json;
using System.Threading.Tasks;
using Microsoft.Azure.Cosmos;

public class Program
{
     private const string EndpointUrl = "https://<your-account>.documents.azure.com:443/";
     private const string AuthorizationKey = "<your-account-key>";
     private const string DatabaseName = "bulk-tutorial";
     private const string ContainerName = "items";
     private const int AmountToInsert = 300000;

     static async Task Main(string[] args)
     {

     }
}

Dentro do Main método, adicione o seguinte código para inicializar o objeto CosmosClient:

CosmosClient cosmosClient = new CosmosClient(EndpointUrl, AuthorizationKey, new CosmosClientOptions() { AllowBulkExecution = true });

Nota

Uma vez que a execução em massa é especificada no CosmosClientOptions, eles são efetivamente imutáveis durante o tempo de vida do CosmosClient. A alteração dos valores não terá efeito.

Depois que a execução em massa é habilitada, o CosmosClient agrupa internamente operações simultâneas em chamadas de serviço únicas. Dessa forma, ele otimiza a utilização da taxa de transferência distribuindo chamadas de serviço entre partições e, finalmente, atribuindo resultados individuais aos chamadores originais.

Você pode então criar um recipiente para armazenar todos os nossos itens. Defina /pk como a chave de partição, 50000 RU/s como taxa de transferência provisionada e uma política de indexação personalizada que excluirá todos os campos para otimizar a taxa de transferência de gravação. Adicione o seguinte código após a instrução de inicialização CosmosClient:

Database database = await cosmosClient.CreateDatabaseIfNotExistsAsync(Program.DatabaseName);

await database.DefineContainer(Program.ContainerName, "/pk")
        .WithIndexingPolicy()
            .WithIndexingMode(IndexingMode.Consistent)
            .WithIncludedPaths()
                .Attach()
            .WithExcludedPaths()
                .Path("/*")
                .Attach()
        .Attach()
    .CreateAsync(50000);

Etapa 6: preencher uma lista de tarefas simultâneas

Para aproveitar o suporte à execução em massa, crie uma lista de tarefas assíncronas com base na fonte de dados e nas operações que você deseja executar e use Task.WhenAll para executá-las simultaneamente. Vamos começar usando dados "falsos" para gerar uma lista de itens do nosso modelo de dados. Em um aplicativo do mundo real, os itens viriam da fonte de dados desejada.

Primeiro, adicione o pacote Bogus à solução usando o comando dotnet add package.

dotnet add package Bogus

Defina a definição dos itens que você deseja salvar. Você precisa definir a Item classe dentro do Program.cs arquivo:

public class Item
{
    public string id {get;set;}
    public string pk {get;set;}

    public string username{get;set;}
}

Em seguida, crie uma função auxiliar dentro da Program classe. Esta função auxiliar obterá o número de itens que você definiu para inserir e gera dados aleatórios:

private static IReadOnlyCollection<Item> GetItemsToInsert()
{
    return new Bogus.Faker<Item>()
    .StrictMode(true)
    //Generate item
    .RuleFor(o => o.id, f => Guid.NewGuid().ToString()) //id
    .RuleFor(o => o.username, f => f.Internet.UserName())
    .RuleFor(o => o.pk, (f, o) => o.id) //partitionkey
    .Generate(AmountToInsert);
}

Use a função auxiliar para inicializar uma lista de documentos com os quais trabalhar:

IReadOnlyCollection<Item> itemsToInsert = Program.GetItemsToInsert();

Em seguida, use a lista de documentos para criar tarefas simultâneas e preencha a lista de tarefas para inserir os itens no contêiner. Para executar essa operação, adicione o seguinte código à Program classe:

Container container = database.GetContainer(ContainerName);
List<Task> tasks = new List<Task>(AmountToInsert);
foreach (Item item in itemsToInsert)
{
    tasks.Add(container.CreateItemAsync(item, new PartitionKey(item.pk))
        .ContinueWith(itemResponse =>
        {
            if (!itemResponse.IsCompletedSuccessfully)
            {
                AggregateException innerExceptions = itemResponse.Exception.Flatten();
                if (innerExceptions.InnerExceptions.FirstOrDefault(innerEx => innerEx is CosmosException) is CosmosException cosmosException)
                {
                    Console.WriteLine($"Received {cosmosException.StatusCode} ({cosmosException.Message}).");
                }
                else
                {
                    Console.WriteLine($"Exception {innerExceptions.InnerExceptions.FirstOrDefault()}.");
                }
            }
        }));
}

// Wait until all are done
await Task.WhenAll(tasks);

Todas essas operações pontuais simultâneas serão executadas juntas (ou seja, em massa), conforme descrito na seção de introdução.

Etapa 7: Executar o exemplo

Para executar o exemplo, você pode fazê-lo simplesmente pelo dotnet comando:

dotnet run

Obtenha a amostra completa

Se não tiver tempo de completar os passos deste tutorial, ou apenas pretender transferir os exemplos de código, pode obtê-los a partir do GitHub.

Depois de clonar o projeto, certifique-se de atualizar as credenciais desejadas dentro Program.cs.

O exemplo pode ser executado alterando para o diretório do repositório e usando dotnet:

cd cosmos-dotnet-bulk-import-throughput-optimizer
dotnet run

Próximos passos

Neste tutorial, você executou as seguintes etapas:

  • Criando uma conta do Azure Cosmos DB
  • Configurando seu projeto
  • Conectando-se a uma conta do Azure Cosmos DB com suporte em massa habilitado
  • Executar uma importação de dados por meio de operações de criação simultâneas

Agora você pode prosseguir para o próximo tutorial:

Tentando fazer o planejamento de capacidade para uma migração para o Azure Cosmos DB? Você pode usar informações sobre seu cluster de banco de dados existente para planejamento de capacidade.