Samouczek: tworzenie aplikacji konsolowej platformy .NET za pomocą usługi Azure Cosmos DB for NoSQL
DOTYCZY: NoSQL
Zestaw Azure SDK dla platformy .NET umożliwia dodawanie danych do interfejsu API dla kontenera NoSQL asynchronicznie lub wsadu transakcyjnego. W tym samouczku przedstawiono proces tworzenia nowej aplikacji konsolowej .NET, która dodaje wiele elementów do kontenera.
Z tego samouczka dowiesz się, jak wykonywać następujące czynności:
- Tworzenie bazy danych przy użyciu interfejsu API dla noSQL
- Tworzenie aplikacji konsolowej platformy .NET i dodawanie zestawu Azure SDK dla platformy .NET
- Dodawanie poszczególnych elementów do interfejsu API dla kontenera NoSQL
- Wydajne pobieranie elementów z interfejsu API dla kontenera NoSQL
- Tworzenie transakcji ze zmianami wsadowymi dla kontenera api for NoSQL
Wymagania wstępne
- Istniejące konto usługi Azure Cosmos DB for NoSQL.
- Jeśli masz istniejącą subskrypcję platformy Azure, utwórz nowe konto.
- Brak subskrypcji platformy Azure? Możesz wypróbować usługę Azure Cosmos DB bezpłatnie bez konieczności korzystania z karty kredytowej.
- Visual Studio Code
- .NET 8 lub nowszy
- Doświadczenie w pisaniu aplikacji w języku C#.
Tworzenie interfejsu API dla zasobów NoSQL
Najpierw utwórz pustą bazę danych w istniejącym interfejsie API dla konta NoSQL. Kontener można utworzyć przy użyciu zestawu Azure SDK dla platformy .NET później.
Przejdź do istniejącego konta interfejsu API dla noSQL w witrynie Azure Portal.
W menu zasobów wybierz pozycję Klucze.
Na stronie Klucze sprawdź i zarejestruj wartość pól Identyfikator URI i KLUCZ PODSTAWOWY. Te wartości są używane w całym samouczku.
W menu zasobów wybierz pozycję Eksplorator danych.
Na stronie Eksplorator danych wybierz opcję Nowa baza danych na pasku poleceń.
W oknie dialogowym Nowa baza danych utwórz nowy kontener z następującymi ustawieniami:
Wartość Identyfikator bazy danych cosmicworks
Typ przepływności bazy danych Ręczne Ilość przepływności bazy danych 400
Wybierz przycisk OK , aby utworzyć bazę danych.
Tworzenie aplikacji konsolowej platformy .NET
Teraz utworzysz nową aplikację konsolową platformy .NET i zaimportujesz zestaw Azure SDK dla platformy .NET przy użyciu Microsoft.Azure.Cosmos
biblioteki z narzędzia NuGet.
Otwórz terminal w pustym katalogu.
Tworzenie nowej aplikacji konsolowej przy użyciu wbudowanego
console
szablonudotnet new console --langVersion preview
Dodaj wersję
Microsoft.Azure.Cosmos
3.31.1-preview pakietu z pakietu NuGet.dotnet add package Microsoft.Azure.Cosmos --version 3.31.1-preview
Ponadto dodaj wersję
System.CommandLine
wstępną pakietu z pakietu NuGet.dotnet add package System.CommandLine --prerelease
Ponadto dodaj
Humanizer
pakiet z narzędzia NuGet.dotnet add package Humanizer
Skompiluj projekt aplikacji konsolowej.
dotnet build
Otwórz program Visual Studio Code przy użyciu bieżącego folderu projektu jako obszaru roboczego.
Napiwek
Możesz uruchomić polecenie
code .
w terminalu, aby otworzyć program Visual Studio Code i automatycznie otworzyć katalog roboczy jako bieżący obszar roboczy.Przejdź do pliku Program.cs i otwórz go. Usuń cały istniejący kod w pliku.
Dodaj ten kod do pliku, aby użyć biblioteki System.CommandLine , aby przeanalizować wiersz polecenia dla dwóch ciągów przekazywanych za pośrednictwem
--first
opcji i--last
.using System.CommandLine; var command = new RootCommand(); var nameOption = new Option<string>("--name") { IsRequired = true }; var emailOption = new Option<string>("--email"); var stateOption = new Option<string>("--state") { IsRequired = true }; var countryOption = new Option<string>("--country") { IsRequired = true }; command.AddOption(nameOption); command.AddOption(emailOption); command.AddOption(stateOption); command.AddOption(countryOption); command.SetHandler( handle: CosmosHandler.ManageCustomerAsync, nameOption, emailOption, stateOption, countryOption ); await command.InvokeAsync(args);
Uwaga
W tym samouczku nie jest to całkowicie ważne, aby zrozumieć, jak działa analizator wiersza polecenia. Analizator ma cztery opcje, które można określić, gdy aplikacja jest uruchomiona. Trzy z tych opcji są wymagane, ponieważ będą używane do konstruowania pól identyfikatora i klucza partycji.
W tym momencie projekt nie zostanie skompilowane, ponieważ nie zdefiniowano jeszcze metody statycznej
CosmosHandler.ManageCustomerAsync
.Zapisz plik Program.cs.
Dodawanie elementów do kontenera przy użyciu zestawu SDK
Następnie należy użyć poszczególnych operacji, aby dodać elementy do kontenera interfejsu API dla noSQL. W tej sekcji zdefiniujesz metodę CosmosHandler.ManageCustomerAsync
.
Utwórz nowy plik CosmosHandler.cs .
W pliku CosmosHandler.cs dodaj nową dyrektywę using dla
Humanizer
przestrzeni nazw iMicrosoft.Azure.Cosmos
.using Humanizer; using Microsoft.Azure.Cosmos;
Utwórz nową klasę statyczną o nazwie
CosmosHandler
.public static class CosmosHandler { }
Aby sprawdzić, czy ta aplikacja działa, utwórz krótką implementację metody statycznej
ManageCustomerAsync
, aby wydrukować dane wejściowe wiersza polecenia.public static async Task ManageCustomerAsync(string name, string email, string state, string country) { await Console.Out.WriteLineAsync($"Hello {name} of {state}, {country}!"); }
Zapisz plik CosmosHandler.cs.
Ponownie w terminalu uruchom aplikację.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Dane wyjściowe polecenia powinny być zabawnym powitaniem.
Hello Mica Pereira of Washington, United States!
Wróć do pliku CosmosHandler.cs .
W statycznej klasie CosmosHandler dodaj nowy
private static readonly
element członkowski typuCosmosClient
o nazwie_client
.private static readonly CosmosClient _client;
Utwórz nowy konstruktor statyczny dla
CosmosHandler
klasy .static CosmosHandler() { }
W konstruktorze utwórz nowe wystąpienie
CosmosClient
klasy przekazującej dwa parametry ciągu przy użyciu wartości URI i PRIMARY KEY , które zostały wcześniej zarejestrowane w laboratorium. Zapisz to nowe wystąpienie w elemencie_client
członkowskim.static CosmosHandler() { _client = new CosmosClient( accountEndpoint: "<uri>", authKeyOrResourceToken: "<primary-key>" ); }
Z powrotem w statycznej klasie CosmosHandler utwórz nową metodę asynchroniczną o nazwie
GetContainerAsync
, która zwracaContainer
wartość .private static async Task<Container> GetContainerAsync() { }
Aby wykonać następne kroki, dodaj ten kod w metodzie
GetContainerAsync
.cosmicworks
Pobierz bazę danych i zapisz ją w zmiennej o nazwiedatabase
.Database database = _client.GetDatabase("cosmicworks");
Utwórz nowy rodzaj
List<>
string
wartości na liście hierarchicznych ścieżek klucza partycji i zapisz je w zmiennej o nazwiekeyPaths
.List<string> keyPaths = new() { "/address/country", "/address/state" };
Utwórz nową
ContainerProperties
zmienną o nazwie kontenera (customers
) i liście ścieżek klucza partycji.ContainerProperties properties = new( id: "customers", partitionKeyPaths: keyPaths );
CreateContainerIfNotExistsAsync
Użyj metody , aby podać właściwości kontenera i pobrać kontener. Ta metoda będzie asynchronicznie utworzyć kontener, jeśli jeszcze nie istnieje w bazie danych. Zwróć wynik jako dane wyjścioweGetContainerAsync
metody .return await database.CreateContainerIfNotExistsAsync( containerProperties: properties );
Usuń cały kod w metodzie
ManageCustomerAsync
.Aby wykonać następne kroki, dodaj ten kod w metodzie
ManageCustomerAsync
.Asynchronicznie wywołaj metodę
GetContainerAsync
i zapisz wynik w zmiennej o nazwiecontainer
.Container container = await GetContainerAsync();
Utwórz nową zmienną o nazwie
id
, która używaKebaberize
metody z Humanizer do przekształcenia parametruname
metody.string id = name.Kebaberize();
Uwaga
Metoda
Kebaberize
zastąpi wszystkie spacje łącznikami i zweryfuje tekst do małych liter.Utwórz nowy anonimowy element wpisany przy użyciu
name
parametrów ,state
i metody icountry
zmiennejid
. Zapisz element jako zmienną o nazwiecustomer
.var customer = new { id = id, name = name, address = new { state = state, country = country } };
Użyj metody asynchronicznej
CreateItemAsync
kontenera, aby utworzyć nowy element w kontenerze i przypisać metadane odpowiedzi HTTP do zmiennej o nazwieresponse
.var response = await container.CreateItemAsync(customer);
Zapisz wartości właściwości i
RequestCharge
zmiennejresponse
StatusCode
w konsoli programu . Zapisz również wartość zmiennejid
.Console.WriteLine($"[{response.StatusCode}]\t{id}\t{response.RequestCharge} RUs");
Zapisz plik CosmosHandler.cs.
Wróć do terminalu, ponownie uruchom aplikację.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Dane wyjściowe polecenia powinny zawierać stan i żądanie opłaty za operację.
[Created] mica-pereira 7.05 RUs
Uwaga
Opłata za żądanie może się różnić.
Uruchom aplikację jeszcze raz.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Tym razem program powinien ulec awarii. Jeśli przewiniesz komunikat o błędzie, zobaczysz, że wystąpiła awaria z powodu konfliktu w unikatowym identyfikatorze elementów.
Unhandled exception: Microsoft.Azure.Cosmos.CosmosException : Response status code does not indicate success: Conflict (409);Reason: ( Errors : [ "Resource with specified id or name already exists." ] );
Pobieranie elementu przy użyciu zestawu SDK
Po utworzeniu pierwszego elementu w kontenerze możesz użyć tego samego zestawu SDK do pobrania elementu. W tym miejscu wykonasz zapytanie i wskażesz element, aby porównać różnicę użycia jednostek żądań (RU).
Wróć do lub otwórz plik CosmosHandler.cs .
Usuń wszystkie wiersze kodu z metody z
ManageCustomerAsync
wyjątkiem dwóch pierwszych wierszy.public static async Task ManageCustomerAsync(string name, string email, string state, string country) { Container container = await GetContainerAsync(); string id = name.Kebaberize(); }
Aby wykonać następne kroki, dodaj ten kod w metodzie
ManageCustomerAsync
.Użyj metody asynchronicznej
CreateItemAsync
kontenera, aby utworzyć nowy element w kontenerze i przypisać metadane odpowiedzi HTTP do zmiennej o nazwieresponse
.var response = await container.CreateItemAsync(customer);
Utwórz nowy ciąg o nazwie
sql
z zapytaniem SQL, aby pobrać elementy, w których filtr (@id
) jest zgodny.string sql = @" SELECT * FROM customers c WHERE c.id = @id ";
Utwórz nową
QueryDefinition
zmienną o nazwiequery
przekazującąsql
ciąg jako jedyny parametr zapytania. Ponadto użyj metody płynuWithParameter
, aby zastosować wartość zmiennejid
do parametru@id
.var query = new QueryDefinition( query: sql ) .WithParameter("@id", id);
GetItemQueryIterator<>
Użyj metody ogólnej i zmiennejquery
, aby utworzyć iterator, który pobiera dane z usługi Azure Cosmos DB. Zapisz iterator w zmiennej o nazwiefeed
. Zawijaj to całe wyrażenie w instrukcji using, aby później usunąć iterator.using var feed = container.GetItemQueryIterator<dynamic>( queryDefinition: query );
Asynchronicznie wywołaj metodę
ReadNextAsync
zmiennejfeed
i zapisz wynik w zmiennej o nazwieresponse
.var response = await feed.ReadNextAsync();
Zapisz wartości właściwości i
RequestCharge
zmiennejresponse
StatusCode
w konsoli programu . Zapisz również wartość zmiennejid
.Console.WriteLine($"[{response.StatusCode}]\t{id}\t{response.RequestCharge} RUs");
Zapisz plik CosmosHandler.cs.
Po powrocie do terminalu uruchom aplikację, aby odczytać pojedynczy element przy użyciu zapytania SQL.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Dane wyjściowe polecenia powinny wskazywać, że zapytanie wymaga wielu jednostek żądania (RU).
[OK] mica-pereira 2.82 RUs
Ponownie w pliku CosmosHandler.cs usuń wszystkie wiersze kodu z
ManageCustomerAsync
metody z wyjątkiem dwóch pierwszych wierszy.public static async Task ManageCustomerAsync(string name, string email, string state, string country) { Container container = await GetContainerAsync(); string id = name.Kebaberize(); }
Aby wykonać następne kroki, dodaj ten kod w metodzie
ManageCustomerAsync
.Utwórz nowe wystąpienie klasy
PartitionKeyBuilder
, dodającstate
parametry icountry
jako wartość klucza partycji wieloczęściowej.var partitionKey = new PartitionKeyBuilder() .Add(country) .Add(state) .Build();
Użyj metody kontenera
ReadItemAsync<>
, aby wskazać odczyt elementu z kontenera przy użyciuid
zmiennych ipartitionKey
. Zapisz wynik w zmiennej o nazwieresponse
.var response = await container.ReadItemAsync<dynamic>( id: id, partitionKey: partitionKey );
Zapisz wartości właściwości i
RequestCharge
zmiennejresponse
StatusCode
w konsoli programu . Zapisz również wartość zmiennejid
.Console.WriteLine($"[{response.StatusCode}]\t{id}\t{response.RequestCharge} RU");
Zapisz ponownie plik CosmosHandler.cs.
Po powrocie do terminalu uruchom aplikację jeszcze raz, aby wskazać odczyt pojedynczego elementu.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Dane wyjściowe polecenia powinny wskazywać, że zapytanie wymaga pojedynczej jednostki RU.
[OK] mica-pereira 1 RUs
Tworzenie transakcji przy użyciu zestawu SDK
Na koniec przejmiesz utworzony element, odczytujesz ten element i utworzysz inny powiązany element w ramach jednej transakcji przy użyciu zestawu Azure SDK dla platformy .NET.
Wróć do lub otwórz plik CosmosHandler.cs .
Usuń te wiersze kodu z
ManageCustomerAsync
metody .var response = await container.ReadItemAsync<dynamic>( id: id, partitionKey: partitionKey ); Console.WriteLine($"[{response.StatusCode}]\t{id}\t{response.RequestCharge} RUs");
Aby wykonać następne kroki, dodaj ten nowy kod w metodzie
ManageCustomerAsync
.Utwórz nowy anonimowy element wpisany przy użyciu
name
parametrów ,state
i metody icountry
zmiennejid
. Zapisz element jako zmienną o nazwiecustomerCart
. Ten element reprezentuje koszyk w czasie rzeczywistym dla klienta, który jest obecnie pusty.var customerCart = new { id = $"{Guid.NewGuid()}", customerId = id, items = new string[] {}, address = new { state = state, country = country } };
Utwórz kolejny nowy element typu anonimowego
name
przy użyciu parametrów metody ,state
icountry
zmiennejid
. Zapisz element jako zmienną o nazwiecustomerCart
. Ten element reprezentuje informacje wysyłkowe i kontaktowe klienta.var customerContactInfo = new { id = $"{id}-contact", customerId = id, email = email, location = $"{state}, {country}", address = new { state = state, country = country } };
Utwórz nową partię przy użyciu metody kontenera
CreateTransactionalBatch
przekazującej zmiennąpartitionKey
. Zapisz partię w zmiennej o nazwiebatch
. Użyj płynnych metod, aby wykonać następujące akcje:Method Parametr ReadItem
id
zmienna ciąguCreateItem
customerCart
zmienna typu anonimowegoCreateItem
customerContactInfo
zmienna typu anonimowegovar batch = container.CreateTransactionalBatch(partitionKey) .ReadItem(id) .CreateItem(customerCart) .CreateItem(customerContactInfo);
Użyj metody wsadowej
ExecuteAsync
, aby rozpocząć transakcję. Zapisz wynik w zmiennej o nazwieresponse
.using var response = await batch.ExecuteAsync();
Zapisz wartości właściwości i
RequestCharge
zmiennejresponse
StatusCode
w konsoli programu . Zapisz również wartość zmiennejid
.Console.WriteLine($"[{response.StatusCode}]\t{response.RequestCharge} RUs");
Zapisz ponownie plik CosmosHandler.cs.
Po powrocie do terminalu uruchom aplikację jeszcze raz, aby wskazać odczyt pojedynczego elementu.
dotnet run -- --name 'Mica Pereira' --state 'Washington' --country 'United States'
Dane wyjściowe polecenia powinny zawierać jednostki żądania używane dla całej transakcji.
[OK] 16.05 RUs
Uwaga
Opłata za żądanie może się różnić.
Weryfikowanie końcowych danych w Eksploratorze danych
Aby podsumować kwestie, użyj eksploratora danych w witrynie Azure Portal, aby wyświetlić dane i kontener utworzony w tym samouczku.
Przejdź do istniejącego konta interfejsu API dla noSQL w witrynie Azure Portal.
W menu zasobów wybierz pozycję Eksplorator danych.
Na stronie Eksplorator danych rozwiń
cosmicworks
bazę danych, a następnie wybierzcustomers
kontener.Na pasku poleceń wybierz pozycję Nowe zapytanie SQL.
W edytorze zapytań obserwuj ten ciąg zapytania SQL.
SELECT * FROM c
Wybierz pozycję Wykonaj zapytanie , aby uruchomić zapytanie i obserwować wyniki.
Wyniki powinny zawierać tablicę JSON z trzema elementami utworzonymi w tym samouczku. Zwróć uwagę, że wszystkie elementy mają tę samą hierarchiczną wartość klucza partycji, ale unikatowe pola identyfikatora. Przykładowe dane wyjściowe są obcięte w celu zwięzłości.
[ { "id": "mica-pereira", "name": "Mica Pereira", "address": { "state": "Washington", "country": "United States" }, ... }, { "id": "33d03318-6302-4559-b5c0-f3cc643b2f38", "customerId": "mica-pereira", "items": [], "address": { "state": "Washington", "country": "United States" }, ... }, { "id": "mica-pereira-contact", "customerId": "mica-pereira", "email": null, "location": "Washington, United States", "address": { "state": "Washington", "country": "United States" }, ... } ]
Czyszczenie zasobów
Gdy baza danych używana w tym samouczku nie będzie już potrzebna, usuń bazę danych. W tym celu przejdź do strony konta, wybierz pozycję Eksplorator danych, wybierz cosmicworks
bazę danych, a następnie wybierz pozycję Usuń.