Przewodnik dotyczący uruchamiania usługi Azure Functions w języku C# w modelu izolowanego procesu roboczego

Ten artykuł stanowi wprowadzenie do pracy z usługą Azure Functions na platformie .NET przy użyciu izolowanego modelu procesu roboczego. Ten model umożliwia projektowi określanie wersji docelowych platformy .NET niezależnie od innych składników środowiska uruchomieniowego. Aby uzyskać informacje o obsługiwanych wersjach platformy .NET, zobacz obsługiwaną wersję.

Skorzystaj z poniższych linków, aby od razu rozpocząć tworzenie izolowanych funkcji modelu procesu roboczego platformy .NET.

Wprowadzenie Pojęcia Przykłady

Aby dowiedzieć się więcej o wdrażaniu izolowanego projektu modelu roboczego na platformie Azure, zobacz Wdrażanie w usłudze Azure Functions.

Korzyści wynikające z modelu izolowanego procesu roboczego

Istnieją dwa tryby, w których można uruchamiać funkcje biblioteki klas platformy .NET: w tym samym procesie co środowisko uruchomieniowe hosta usługi Functions (w procesie) lub w izolowanym procesie roboczym. Gdy funkcje platformy .NET działają w izolowanym procesie roboczym, możesz skorzystać z następujących korzyści:

  • Mniejsza liczba konfliktów: ponieważ funkcje działają w osobnym procesie, zestawy używane w aplikacji nie powodują konfliktu z różnymi wersjami tych samych zestawów używanych przez proces hosta.
  • Pełna kontrola procesu: kontrolujesz uruchamianie aplikacji, co oznacza, że możesz zarządzać używanymi konfiguracjami i uruchomionym oprogramowaniem pośredniczącym.
  • Standardowe wstrzykiwanie zależności: ponieważ masz pełną kontrolę nad procesem, możesz użyć bieżących zachowań platformy .NET do wstrzykiwania zależności i dołączania oprogramowania pośredniczącego do aplikacji funkcji.
  • Elastyczność wersji platformy .NET: Uruchamianie poza procesem hosta oznacza, że funkcje mogą być uruchamiane w wersjach platformy .NET, które nie są natywnie obsługiwane przez środowisko uruchomieniowe usługi Functions, w tym program .NET Framework.

Jeśli masz istniejącą aplikację funkcji języka C#, która działa w trakcie procesu, musisz zmigrować aplikację, aby skorzystać z tych korzyści. Aby uzyskać więcej informacji, zobacz Migrowanie aplikacji .NET z modelu procesu do izolowanego modelu roboczego.

Aby uzyskać kompleksowe porównanie dwóch trybów, zobacz Różnice między procesem w procesie i izolowanym procesem roboczym .NET Azure Functions.

Obsługiwane wersje

Wersje środowiska uruchomieniowego usługi Functions obsługują określone wersje platformy .NET. Aby dowiedzieć się więcej na temat wersji usługi Functions, zobacz Omówienie wersji środowiska uruchomieniowego usługi Azure Functions. Obsługa wersji zależy również od tego, czy funkcje działają w procesie przetwarzania, czy izolowanego procesu roboczego.

Uwaga

Aby dowiedzieć się, jak zmienić wersję środowiska uruchomieniowego usługi Functions używaną przez aplikację funkcji, zobacz wyświetlanie i aktualizowanie bieżącej wersji środowiska uruchomieniowego.

W poniższej tabeli przedstawiono najwyższy poziom platformy .NET lub .NET Framework, który może być używany z określoną wersją usługi Functions.

Wersja środowiska uruchomieniowego usługi Functions Model izolowanego procesu roboczego Modelw procesie 5
Functions 4.x .NET 8.0
.NET 7.01
.NET 6.02
.NET Framework 4.83
.NET 6.02
Funkcje 1.x4 nie dotyczy .NET Framework 4.8

1 .NET 7 kończy oficjalne wsparcie 14 maja 2024 r.
2 .NET 6 kończy oficjalne wsparcie 12 listopada 2024 r.
3 Proces kompilacji wymaga również zestawu .NET SDK. 4 Zakończenie wsparcia dla wersji 1.x środowiska uruchomieniowego usługi Azure Functions 14 września 2026 r. Aby uzyskać więcej informacji, zobacz to ogłoszenie pomocy technicznej. Aby zapewnić ciągłą pełną obsługę, należy przeprowadzić migrację aplikacji do wersji 4.x.
5 Wsparcie kończy się dla modelu procesu 10 listopada 2026 r. Aby uzyskać więcej informacji, zobacz to ogłoszenie pomocy technicznej. Aby zapewnić ciągłą pełną obsługę, należy przeprowadzić migrację aplikacji do izolowanego modelu procesu roboczego.

Aby uzyskać najnowsze informacje o wersjach usługi Azure Functions, w tym o usunięciu określonych starszych wersji pomocniczych, monitoruj ogłoszenia usługi aplikacja systemu Azure.

Struktura projektu

Projekt platformy .NET dla usługi Azure Functions korzystający z izolowanego modelu roboczego jest w zasadzie projektem aplikacji konsolowej platformy .NET przeznaczonym dla obsługiwanego środowiska uruchomieniowego platformy .NET. Poniżej przedstawiono podstawowe pliki wymagane w dowolnym izolowanym projekcie platformy .NET:

  • Plik projektu języka C# (csproj), który definiuje projekt i zależności.
  • Program.cs pliku, który jest punktem wejścia aplikacji.
  • Wszystkie pliki kodu definiujące funkcje.
  • host.json plik definiujący konfigurację współużytkowany przez funkcje w projekcie.
  • local.settings.json plik, który definiuje zmienne środowiskowe używane przez projekt podczas uruchamiania lokalnego na maszynie.

Kompletne przykłady można znaleźć w przykładowym projekcie platformy .NET 8 i przykładowym projekcie programu .NET Framework 4.8.

Odwołania do pakietu

Projekt platformy .NET dla usługi Azure Functions korzystający z izolowanego modelu roboczego używa unikatowego zestawu pakietów zarówno dla podstawowych funkcji, jak i rozszerzeń powiązań.

Pakiety podstawowe

Do uruchamiania funkcji platformy .NET w izolowanym procesie roboczym wymagane są następujące pakiety:

Pakiety rozszerzeń

Ponieważ funkcje procesu roboczego izolowanego platformy .NET używają różnych typów powiązań, wymagają unikatowego zestawu pakietów rozszerzeń powiązań.

Te pakiety rozszerzeń można znaleźć w obszarze Microsoft.Azure.Functions.Worker.Extensions.

Uruchamianie i konfiguracja

W przypadku korzystania z funkcji izolowanych platformy .NET masz dostęp do uruchamiania aplikacji funkcji, która zwykle znajduje się w elemecie Program.cs. Odpowiadasz za tworzenie i uruchamianie własnego wystąpienia hosta. W związku z tym masz również bezpośredni dostęp do potoku konfiguracji aplikacji. Dzięki procesowi izolowanego procesu roboczego usługi .NET Functions można znacznie łatwiej dodawać konfiguracje, wprowadzać zależności i uruchamiać własne oprogramowanie pośredniczące.

Poniższy kod przedstawia przykład potoku HostBuilder :

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices(s =>
    {
        s.AddApplicationInsightsTelemetryWorkerService();
        s.ConfigureFunctionsApplicationInsights();
        s.AddSingleton<IHttpResponderService, DefaultHttpResponderService>();
        s.Configure<LoggerFilterOptions>(options =>
        {
            // The Application Insights SDK adds a default logging filter that instructs ILogger to capture only Warning and more severe logs. Application Insights requires an explicit override.
            // Log levels can also be configured using appsettings.json. For more information, see https://learn.microsoft.com/en-us/azure/azure-monitor/app/worker-service#ilogger-logs
            LoggerFilterRule toRemove = options.Rules.FirstOrDefault(rule => rule.ProviderName
                == "Microsoft.Extensions.Logging.ApplicationInsights.ApplicationInsightsLoggerProvider");

            if (toRemove is not null)
            {
                options.Rules.Remove(toRemove);
            }
        });
    })
    .Build();

Ten kod wymaga .using Microsoft.Extensions.DependencyInjection;

Przed wywołaniem metody HostBuildernależy wykonać następujące elementyBuild():

  • Wywołaj metodę ConfigureFunctionsWebApplication() , jeśli używasz integracji ASP.NET Core lub ConfigureFunctionsWorkerDefaults() w inny sposób. Aby uzyskać szczegółowe informacje na temat tych opcji, zobacz Wyzwalacz HTTP.
    Jeśli piszesz aplikację przy użyciu języka F#, niektóre rozszerzenia wyzwalacza i powiązań wymagają dodatkowej konfiguracji. Zapoznaj się z dokumentacją konfiguracji rozszerzenia obiektów blob, rozszerzenia Tabele i rozszerzenia usługi Cosmos DB, gdy planujesz używać tych rozszerzeń w aplikacji języka F#.
  • Skonfiguruj dowolną usługę lub konfigurację aplikacji wymaganą przez projekt. Aby uzyskać szczegółowe informacje, zobacz Konfiguracja .
    Jeśli planujesz używać Szczegółowe informacje aplikacji, musisz wywołać polecenie AddApplicationInsightsTelemetryWorkerService() i ConfigureFunctionsApplicationInsights() w delegatuConfigureServices(). Aby uzyskać szczegółowe informacje, zobacz Szczegółowe informacje aplikacji.

Jeśli projekt jest przeznaczony dla programu .NET Framework 4.8, należy również dodać FunctionsDebugger.Enable(); go przed utworzeniem programu HostBuilder. Powinien to być pierwszy wiersz Main() metody. Aby uzyskać więcej informacji, zobacz Debugowanie podczas określania wartości docelowej programu .NET Framework.

Program HostBuilder służy do kompilowania i zwracania w pełni zainicjowanego IHost wystąpienia, które jest uruchamiane asynchronicznie w celu uruchomienia aplikacji funkcji.

await host.RunAsync();

Konfigurowanie

Metoda ConfigureFunctionsWorkerDefaults służy do dodawania ustawień wymaganych przez aplikację funkcji do uruchomienia w izolowanym procesie roboczym, który obejmuje następujące funkcje:

  • Domyślny zestaw konwerterów.
  • Ustaw domyślną wartość JsonSerializerOptions , aby ignorować wielkość liter nazw właściwości.
  • Integracja z rejestrowaniem usługi Azure Functions.
  • Oprogramowanie pośredniczące powiązania danych wyjściowych i funkcje.
  • Oprogramowanie pośredniczące wykonywania funkcji.
  • Domyślna obsługa gRPC.
.ConfigureFunctionsWorkerDefaults()

Posiadanie dostępu do potoku konstruktora hostów oznacza, że podczas inicjowania można również ustawić dowolne konfiguracje specyficzne dla aplikacji. Możesz wywołać metodę ConfigureAppConfiguration w programie HostBuilder co najmniej raz, aby dodać konfiguracje wymagane przez aplikację funkcji. Aby dowiedzieć się więcej na temat konfiguracji aplikacji, zobacz Konfiguracja w programie ASP.NET Core.

Te konfiguracje mają zastosowanie do aplikacji funkcji działającej w osobnym procesie. Aby wprowadzić zmiany w konfiguracji hosta lub wyzwalacza i powiązania funkcji, nadal musisz użyć pliku host.json.

Uwaga

Niestandardowe źródła konfiguracji nie mogą być używane do konfigurowania wyzwalaczy i powiązań. Konfiguracja wyzwalacza i powiązania musi być dostępna dla platformy Functions, a nie tylko dla kodu aplikacji. Tę konfigurację można podać za pomocą ustawień aplikacji, odwołań do usługi Key Vault lub funkcji odwołań do usługi App Configuration.

Wstrzykiwanie zależności

Wstrzykiwanie zależności jest uproszczone w porównaniu z funkcjami przetwarzania platformy .NET, co wymaga utworzenia klasy startowej w celu zarejestrowania usług.

W przypadku aplikacji procesów izolowanych platformy .NET należy użyć standardowego sposobu wywoływania usług ConfigureServices w konstruktorze hosta i używać metod rozszerzeń w IServiceCollection do wstrzykiwania określonych usług.

Poniższy przykład wprowadza zależność pojedynczej usługi:

.ConfigureServices(services =>
{
    services.AddSingleton<IHttpResponderService, DefaultHttpResponderService>();
})

Ten kod wymaga .using Microsoft.Extensions.DependencyInjection; Aby dowiedzieć się więcej, zobacz Wstrzykiwanie zależności w programie ASP.NET Core.

Rejestrowanie klientów platformy Azure

Wstrzykiwanie zależności może służyć do interakcji z innymi usługami platformy Azure. Klientów z zestawu Azure SDK dla platformy .NET można wstrzyknąć przy użyciu pakietu Microsoft.Extensions.Azure . Po zainstalowaniu pakietu zarejestruj klientów, wywołując AddAzureClients() kolekcję usług w programie Program.cs. W poniższym przykładzie skonfigurowano nazwanego klienta dla obiektów blob platformy Azure:

using Microsoft.Extensions.Azure;
using Microsoft.Extensions.Hosting;

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices((hostContext, services) =>
    {
        services.AddAzureClients(clientBuilder =>
        {
            clientBuilder.AddBlobServiceClient(hostContext.Configuration.GetSection("MyStorageConnection"))
                .WithName("copierOutputBlob");
        });
    })
    .Build();

host.Run();

W poniższym przykładzie pokazano, jak można użyć tego typu rejestracji i zestawu SDK, aby skopiować zawartość obiektu blob jako strumień z jednego kontenera do innego przy użyciu wprowadzonego klienta:

using Microsoft.Extensions.Azure;
using Microsoft.Extensions.Logging;

namespace MyFunctionApp
{
    public class BlobCopier
    {
        private readonly ILogger<BlobCopier> _logger;
        private readonly BlobContainerClient _copyContainerClient;

        public BlobCopier(ILogger<BlobCopier> logger, IAzureClientFactory<BlobServiceClient> blobClientFactory)
        {
            _logger = logger;
            _copyContainerClient = blobClientFactory.CreateClient("copierOutputBlob").GetBlobContainerClient("samples-workitems-copy");
            _copyContainerClient.CreateIfNotExists();
        }

        [Function("BlobCopier")]
        public async Task Run([BlobTrigger("samples-workitems/{name}", Connection = "MyStorageConnection")] Stream myBlob, string name)
        {
            await _copyContainerClient.UploadBlobAsync(name, myBlob);
            _logger.LogInformation($"Blob {name} copied!");
        }

    }
}

Element ILogger<T> w tym przykładzie został również uzyskany przez wstrzyknięcie zależności, więc jest on rejestrowany automatycznie. Aby dowiedzieć się więcej na temat opcji konfiguracji rejestrowania, zobacz Rejestrowanie.

Napiwek

W przykładzie użyto ciągu literału dla nazwy klienta zarówno w funkcji, Program.cs jak i funkcji. Rozważ zamiast tego użycie współużytkowanego ciągu stałego zdefiniowanego w klasie funkcji. Można na przykład dodać public const string CopyStorageClientName = nameof(_copyContainerClient); , a następnie odwołać się BlobCopier.CopyStorageClientName do obu lokalizacji. Podobnie można zdefiniować nazwę sekcji konfiguracji za pomocą funkcji, a nie w pliku Program.cs.

Oprogramowanie pośredniczące

Izolowana platforma .NET obsługuje również rejestrację oprogramowania pośredniczącego, ponownie używając modelu podobnego do tego, co istnieje w ASP.NET. Ten model umożliwia wstrzykiwanie logiki do potoku wywołania oraz przed i po wykonaniu funkcji.

Metoda rozszerzenia ConfigureFunctionsWorkerDefaults ma przeciążenie, które umożliwia zarejestrowanie własnego oprogramowania pośredniczącego, jak pokazano w poniższym przykładzie.

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults(workerApplication =>
    {
        // Register our custom middlewares with the worker

        workerApplication.UseMiddleware<ExceptionHandlingMiddleware>();

        workerApplication.UseMiddleware<MyCustomMiddleware>();

        workerApplication.UseWhen<StampHttpHeaderMiddleware>((context) =>
        {
            // We want to use this middleware only for http trigger invocations.
            return context.FunctionDefinition.InputBindings.Values
                          .First(a => a.Type.EndsWith("Trigger")).Type == "httpTrigger";
        });
    })
    .Build();

Metoda UseWhen rozszerzenia może służyć do rejestrowania oprogramowania pośredniczącego, które jest wykonywane warunkowo. Należy przekazać do tej metody predykat, który zwraca wartość logiczną, a oprogramowanie pośredniczące uczestniczy w potoku przetwarzania wywołań, gdy zwracana wartość predykatu to true.

Następujące metody rozszerzenia w funkcjiContext ułatwiają pracę z oprogramowaniem pośredniczącym w izolowanym modelu.

Metoda opis
GetHttpRequestDataAsync HttpRequestData Pobiera wystąpienie po wywołaniu przez wyzwalacz HTTP. Ta metoda zwraca wystąpienie klasy , co jest przydatne, gdy chcesz odczytać dane komunikatów ValueTask<HttpRequestData?>, takie jak nagłówki żądań i pliki cookie.
GetHttpResponseData HttpResponseData Pobiera wystąpienie po wywołaniu przez wyzwalacz HTTP.
GetInvocationResult Pobiera wystąpienie InvocationResultklasy , które reprezentuje wynik bieżącego wykonywania funkcji. Value Użyj właściwości , aby pobrać lub ustawić wartość zgodnie z potrzebami.
GetOutputBindings Pobiera wpisy powiązania wyjściowego dla bieżącego wykonywania funkcji. Każdy wpis w wyniku tej metody jest typu OutputBindingData. Możesz użyć Value właściwości , aby pobrać lub ustawić wartość zgodnie z potrzebami.
BindInputAsync Wiąże element powiązania wejściowego dla żądanego BindingMetadata wystąpienia. Można na przykład użyć tej metody, gdy masz funkcję z powiązaniem wejściowym BlobInput , które musi być używane przez oprogramowanie pośredniczące.

Jest to przykład implementacji oprogramowania pośredniczącego, która odczytuje HttpRequestData wystąpienie i aktualizuje HttpResponseData wystąpienie podczas wykonywania funkcji:

internal sealed class StampHttpHeaderMiddleware : IFunctionsWorkerMiddleware
{
    public async Task Invoke(FunctionContext context, FunctionExecutionDelegate next)
    {
        var requestData = await context.GetHttpRequestDataAsync();

        string correlationId;
        if (requestData!.Headers.TryGetValues("x-correlationId", out var values))
        {
            correlationId = values.First();
        }
        else
        {
            correlationId = Guid.NewGuid().ToString();
        }

        await next(context);

        context.GetHttpResponseData()?.Headers.Add("x-correlationId", correlationId);
    }
}

To oprogramowanie pośredniczące sprawdza obecność określonego nagłówka żądania (x-correlationId), a gdy obecnie używa wartości nagłówka do oznaczania nagłówka odpowiedzi. W przeciwnym razie generuje nową wartość identyfikatora GUID i używa jej do oznaczania nagłówka odpowiedzi. Aby uzyskać bardziej kompletny przykład używania niestandardowego oprogramowania pośredniczącego w aplikacji funkcji, zobacz przykładowy niestandardowy kod referencyjny oprogramowania pośredniczącego.

Dostosowywanie serializacji JSON

Model izolowanego procesu roboczego używa System.Text.Json domyślnie. Zachowanie serializatora można dostosować, konfigurując usługi w ramach Program.cs pliku. W poniższym przykładzie pokazano to przy użyciu elementu ConfigureFunctionsWebApplication, ale będzie ono również działać dla elementu ConfigureFunctionsWorkerDefaults:

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication((IFunctionsWorkerApplicationBuilder builder) =>
    {
        builder.Services.Configure<JsonSerializerOptions>(jsonSerializerOptions =>
        {
            jsonSerializerOptions.PropertyNamingPolicy = JsonNamingPolicy.CamelCase;
            jsonSerializerOptions.DefaultIgnoreCondition = JsonIgnoreCondition.WhenWritingNull;
            jsonSerializerOptions.ReferenceHandler = ReferenceHandler.Preserve;

            // override the default value
            jsonSerializerOptions.PropertyNameCaseInsensitive = false;
        });
    })
    .Build();

Możesz zamiast tego użyć JSON.NET (Newtonsoft.Json) do serializacji. W tym celu należy zainstalować Microsoft.Azure.Core.NewtonsoftJson pakiet. Następnie w rejestracji usługi należy ponownie przypisać Serializer właściwość w WorkerOptions konfiguracji. W poniższym przykładzie pokazano to przy użyciu elementu ConfigureFunctionsWebApplication, ale będzie ono również działać dla elementu ConfigureFunctionsWorkerDefaults:

var host = new HostBuilder()
    .ConfigureFunctionsWebApplication((IFunctionsWorkerApplicationBuilder builder) =>
    {
        builder.Services.Configure<WorkerOptions>(workerOptions =>
        {
            var settings = NewtonsoftJsonObjectSerializer.CreateJsonSerializerSettings();
            settings.ContractResolver = new CamelCasePropertyNamesContractResolver();
            settings.NullValueHandling = NullValueHandling.Ignore;

            workerOptions.Serializer = new NewtonsoftJsonObjectSerializer(settings);
        });
    })
    .Build();

Metody rozpoznawane jako funkcje

Metoda funkcji jest publiczną metodą klasy publicznej z atrybutem Function zastosowanym do metody i atrybutem wyzwalacza zastosowanym do parametru wejściowego, jak pokazano w poniższym przykładzie:

[Function(nameof(QueueFunction))]
[QueueOutput("output-queue")]
public string[] Run([QueueTrigger("input-queue")] Album myQueueItem, FunctionContext context)

Atrybut wyzwalacza określa typ wyzwalacza i wiąże dane wejściowe z parametrem metody. Poprzednia przykładowa funkcja jest wyzwalana przez komunikat kolejki, a komunikat kolejki jest przekazywany do metody w parametrze myQueueItem .

Atrybut Function oznacza metodę jako punkt wejścia funkcji. Nazwa musi być unikatowa w projekcie, zaczynać się literą i zawierać tylko litery, cyfry, _i -, do 127 znaków. Szablony projektów często tworzą metodę o nazwie Run, ale nazwa metody może być dowolną prawidłową nazwą metody języka C#. Metoda musi być publicznym elementem członkowskim klasy publicznej. Zazwyczaj powinna to być metoda wystąpienia, aby usługi mogły być przekazywane za pośrednictwem wstrzykiwania zależności.

Parametry funkcji

Poniżej przedstawiono niektóre parametry, które można uwzględnić jako część podpisu metody funkcji:

  • Powiązania, które są oznaczone jako takie, dekorując parametry jako atrybuty. Funkcja musi zawierać dokładnie jeden parametr wyzwalacza.
  • Obiekt kontekstu wykonywania, który zawiera informacje na temat bieżącego wywołania.
  • Token anulowania używany do bezpiecznego zamykania.

Kontekst wykonywania

Izolowana platforma .NET przekazuje obiekt FunctionContext do metod funkcji. Ten obiekt umożliwia uzyskanie ILogger wystąpienia do zapisu w dziennikach przez wywołanie categoryName metody GetLogger i podanie ciągu. Można użyć tego kontekstu, aby uzyskać ILogger bez konieczności używania wstrzykiwania zależności. Aby dowiedzieć się więcej, zobacz Rejestrowanie.

Tokeny anulowania

Funkcja może akceptować parametr CancellationToken , który umożliwia systemowi operacyjnemu powiadamianie o kodzie po zakończeniu działania funkcji. Możesz użyć tego powiadomienia, aby upewnić się, że funkcja nie zostanie nieoczekiwanie zakończona w sposób, który pozostawia dane w stanie niespójnym.

Tokeny anulowania są obsługiwane w funkcjach platformy .NET podczas uruchamiania w izolowanym procesie roboczym. Poniższy przykład zgłasza wyjątek po odebraniu żądania anulowania:

[Function(nameof(ThrowOnCancellation))]
public async Task ThrowOnCancellation(
    [EventHubTrigger("sample-workitem-1", Connection = "EventHubConnection")] string[] messages,
    FunctionContext context,
    CancellationToken cancellationToken)
{
    _logger.LogInformation("C# EventHub {functionName} trigger function processing a request.", nameof(ThrowOnCancellation));

    foreach (var message in messages)
    {
        cancellationToken.ThrowIfCancellationRequested();
        await Task.Delay(6000); // task delay to simulate message processing
        _logger.LogInformation("Message '{msg}' was processed.", message);
    }
}

Poniższy przykład wykonuje akcje czyszczenia po odebraniu żądania anulowania:

[Function(nameof(HandleCancellationCleanup))]
public async Task HandleCancellationCleanup(
    [EventHubTrigger("sample-workitem-2", Connection = "EventHubConnection")] string[] messages,
    FunctionContext context,
    CancellationToken cancellationToken)
{
    _logger.LogInformation("C# EventHub {functionName} trigger function processing a request.", nameof(HandleCancellationCleanup));

    foreach (var message in messages)
    {
        if (cancellationToken.IsCancellationRequested)
        {
            _logger.LogInformation("A cancellation token was received, taking precautionary actions.");
            // Take precautions like noting how far along you are with processing the batch
            _logger.LogInformation("Precautionary activities complete.");
            break;
        }

        await Task.Delay(6000); // task delay to simulate message processing
        _logger.LogInformation("Message '{msg}' was processed.", message);
    }
}

Powiązania

Powiązania są definiowane przy użyciu atrybutów metod, parametrów i typów zwracanych. Powiązania mogą dostarczać dane jako ciągi, tablice i typy serializacji, takie jak zwykłe stare obiekty klas (POCO). W przypadku niektórych rozszerzeń powiązań można również powiązać z typami specyficznymi dla usługi zdefiniowanymi w zestawach SDK usługi.

W przypadku wyzwalaczy HTTP zobacz sekcję Wyzwalacz HTTP.

Pełny zestaw przykładów referencyjnych korzystających z wyzwalaczy i powiązań z izolowanymi funkcjami procesu roboczego można znaleźć w przykładzie referencyjnym rozszerzeń powiązań.

Powiązania wejściowe

Funkcja może mieć zero lub więcej powiązań wejściowych, które mogą przekazywać dane do funkcji. Podobnie jak wyzwalacze, powiązania wejściowe są definiowane przez zastosowanie atrybutu powiązania do parametru wejściowego. Po wykonaniu funkcji środowisko uruchomieniowe próbuje pobrać dane określone w powiązaniu. Żądane dane są często zależne od informacji dostarczonych przez wyzwalacz przy użyciu parametrów powiązania.

Powiązania wyjściowe

Aby zapisać w powiązaniu wyjściowym, należy zastosować atrybut powiązania wyjściowego do metody funkcji, która definiuje sposób zapisywania w powiązanej usłudze. Wartość zwracana przez metodę jest zapisywana w powiązaniu wyjściowym. Na przykład w poniższym przykładzie wartość ciągu jest zapisywana w kolejce komunikatów o nazwie output-queue przy użyciu powiązania wyjściowego:

[Function(nameof(QueueFunction))]
[QueueOutput("output-queue")]
public string[] Run([QueueTrigger("input-queue")] Album myQueueItem, FunctionContext context)
{
    // Use a string array to return more than one message.
    string[] messages = {
        $"Album name = {myQueueItem.Name}",
        $"Album songs = {myQueueItem.Songs.ToString()}"};

    _logger.LogInformation("{msg1},{msg2}", messages[0], messages[1]);

    // Queue Output messages
    return messages;
}

Wiele powiązań wyjściowych

Dane zapisywane w powiązaniu wyjściowym są zawsze zwracaną wartością funkcji. Jeśli musisz zapisać więcej niż jedno powiązanie wyjściowe, musisz utworzyć niestandardowy typ zwracany. Ten zwracany typ musi mieć atrybut powiązania wyjściowego zastosowany do co najmniej jednej właściwości klasy. Poniższy przykład z wyzwalacza HTTP zapisuje zarówno odpowiedź HTTP, jak i powiązanie wyjściowe kolejki:

public static class MultiOutput
{
    [Function(nameof(MultiOutput))]
    public static MyOutputType Run([HttpTrigger(AuthorizationLevel.Anonymous, "get")] HttpRequestData req,
        FunctionContext context)
    {
        var response = req.CreateResponse(HttpStatusCode.OK);
        response.WriteString("Success!");

        string myQueueOutput = "some output";

        return new MyOutputType()
        {
            Name = myQueueOutput,
            HttpResponse = response
        };
    }
}

public class MyOutputType
{
    [QueueOutput("myQueue")]
    public string Name { get; set; }

    public HttpResponseData HttpResponse { get; set; }
}

Odpowiedź z wyzwalacza HTTP jest zawsze traktowana jako dane wyjściowe, więc atrybut wartości zwracanej nie jest wymagany.

Typy zestawów SDK

W przypadku niektórych typów powiązań specyficznych dla usługi dane powiązania mogą być udostępniane przy użyciu typów z zestawów SDK i struktur usług. Zapewniają one więcej możliwości poza tym, co może oferować serializowany ciąg lub zwykły obiekt CLR (POCO). Aby korzystać z nowszych typów, projekt musi zostać zaktualizowany w celu używania nowszych wersji zależności podstawowych.

Dependency Wymaganie dotyczące wersji
Microsoft.Azure.Functions.Worker 1.18.0 lub nowszy
Microsoft.Azure.Functions.Worker.Sdk 1.13.0 lub nowszy

Podczas testowania typów zestawu SDK lokalnie na maszynie należy również używać narzędzi Azure Functions Core Tools w wersji 4.0.5000 lub nowszej. Bieżącą wersję można sprawdzić przy użyciu func version polecenia .

Każde rozszerzenie wyzwalacza i powiązania ma również własne minimalne wymaganie dotyczące wersji, które opisano w artykułach referencyjnych dotyczących rozszerzeń. Następujące powiązania specyficzne dla usługi udostępniają typy zestawów SDK:

Usługa Wyzwalacz Powiązanie wejściowe Powiązanie wyjściowe
Obiekty blob platformy Azure Ogólnie dostępne Ogólnie dostępne Typy zestawów SDK nie są zalecane.1
Kolejki platformy Azure Ogólnie dostępne Powiązanie wejściowe nie istnieje Typy zestawów SDK nie są zalecane.1
Azure Service Bus Ogólnie dostępne Powiązanie wejściowe nie istnieje Typy zestawów SDK nie są zalecane.1
Azure Event Hubs Ogólnie dostępne Powiązanie wejściowe nie istnieje Typy zestawów SDK nie są zalecane.1
Azure Cosmos DB Typy zestawów SDK nie są używane2 Ogólnie dostępne Typy zestawów SDK nie są zalecane.1
Tabele platformy Azure Wyzwalacz nie istnieje Ogólnie dostępne Typy zestawów SDK nie są zalecane.1
Azure Event Grid Ogólnie dostępne Powiązanie wejściowe nie istnieje Typy zestawów SDK nie są zalecane.1

1 W przypadku scenariuszy wyjściowych, w których należy użyć typu zestawu SDK, należy utworzyć klientów zestawu SDK i pracować z nimi bezpośrednio zamiast używać powiązania wyjściowego. Zobacz Rejestrowanie klientów platformy Azure, aby uzyskać przykład iniekcji zależności.

2 Wyzwalacz usługi Cosmos DB używa zestawienia zmian usługi Azure Cosmos DB i uwidacznia elementy zestawienia zmian jako typy serializowalne w formacie JSON. Brak typów zestawów SDK jest by-design dla tego scenariusza.

Uwaga

W przypadku używania wyrażeń powiązań, które opierają się na danych wyzwalacza, nie można używać typów zestawu SDK dla samego wyzwalacza.

Wyzwalacz HTTP

Wyzwalacze HTTP umożliwiają wywoływanie funkcji przez żądanie HTTP. Istnieją dwa różne podejścia, których można użyć:

  • Model integracji ASP.NET Core korzystający z pojęć znanych deweloperom ASP.NET Core
  • Wbudowany model, który nie wymaga dodatkowych zależności i używa typów niestandardowych dla żądań i odpowiedzi HTTP. Takie podejście jest utrzymywane w celu zapewnienia zgodności z poprzednimi wersjami dla aplikacji roboczych izolowanych platformy .NET.

integracja ASP.NET Core

W tej sekcji pokazano, jak pracować z bazowymi obiektami żądania HTTP i odpowiedzi przy użyciu typów z ASP.NET Core, w tym HttpRequest, HttpResponse i IActionResult. Ten model nie jest dostępny dla aplikacji przeznaczonych dla platformy .NET Framework, które zamiast tego powinny używać wbudowanego modelu.

Uwaga

Nie wszystkie funkcje ASP.NET Core są uwidocznione przez ten model. W szczególności potok oprogramowania pośredniczącego ASP.NET Core i możliwości routingu nie są dostępne. integracja ASP.NET Core wymaga używania zaktualizowanych pakietów.

Aby włączyć integrację ASP.NET Core dla protokołu HTTP:

  1. Dodaj odwołanie w projekcie do pakietu Microsoft.Azure.Functions.Worker.Extensions.Http.AspNetCore w wersji 1.0.0 lub nowszej.

  2. Zaktualizuj projekt, aby używał tych określonych wersji pakietów:

  3. Program.cs W pliku zaktualizuj konfigurację konstruktora hostów, aby zamiast ConfigureFunctionsWebApplication()ConfigureFunctionsWorkerDefaults(). W poniższym przykładzie przedstawiono minimalną konfigurację bez innych dostosowań:

    using Microsoft.Extensions.Hosting;
    using Microsoft.Azure.Functions.Worker;
    
    var host = new HostBuilder()
        .ConfigureFunctionsWebApplication()
        .Build();
    
    host.Run();
    
  4. Zaktualizuj wszystkie istniejące funkcje wyzwalane przez protokół HTTP, aby używać typów ASP.NET Core. W tym przykładzie przedstawiono standard HttpRequest i używaną IActionResult dla prostej funkcji "hello, world":

    [Function("HttpFunction")]
    public IActionResult Run(
        [HttpTrigger(AuthorizationLevel.Anonymous, "get")] HttpRequest req)
    {
        return new OkObjectResult($"Welcome to Azure Functions, {req.Query["name"]}!");
    }
    

Wbudowany model HTTP

W modelu wbudowanym system tłumaczy przychodzący komunikat żądania HTTP na obiekt HttpRequestData przekazywany do funkcji. Ten obiekt udostępnia dane z żądania, w tym Headers, Cookies, Identities, i URLopcjonalnie komunikat Body. Ten obiekt jest reprezentacją żądania HTTP, ale nie jest bezpośrednio połączony z bazowym odbiornikiem HTTP lub odebranym komunikatem.

Podobnie funkcja zwraca obiekt HttpResponseData , który dostarcza dane używane do tworzenia odpowiedzi HTTP, w tym komunikatu StatusCode, Headersi opcjonalnie komunikatu Body.

W poniższym przykładzie pokazano użycie elementów HttpRequestData i HttpResponseData:

[Function(nameof(HttpFunction))]
public static HttpResponseData Run([HttpTrigger(AuthorizationLevel.Anonymous, "get", "post", Route = null)] HttpRequestData req,
    FunctionContext executionContext)
{
    var logger = executionContext.GetLogger(nameof(HttpFunction));
    logger.LogInformation("message logged");

    var response = req.CreateResponse(HttpStatusCode.OK);
    response.Headers.Add("Content-Type", "text/plain; charset=utf-8");
    response.WriteString("Welcome to .NET isolated worker !!");

    return response;
}

Rejestrowanie

W izolowanym środowisku .NET można zapisywać w dziennikach przy użyciu ILogger<T> wystąpienia lub ILogger . Rejestrator można uzyskać za pomocą wstrzykiwania zależności elementu ILogger<T> lub elementu ILoggerFactory:

public class MyFunction {
    
    private readonly ILogger<MyFunction> _logger;
    
    public MyFunction(ILogger<MyFunction> logger) {
        _logger = logger;
    }
    
    [Function(nameof(MyFunction))]
    public void Run([BlobTrigger("samples-workitems/{name}", Connection = "")] string myBlob, string name)
    {
        _logger.LogInformation($"C# Blob trigger function Processed blob\n Name: {name} \n Data: {myBlob}");
    }

}

Rejestrator można również uzyskać z obiektu FunctionContext przekazanego do funkcji. Wywołaj metodę GetLogger<T> lub GetLogger , przekazując wartość ciągu, która jest nazwą kategorii, w której są zapisywane dzienniki. Kategoria jest zwykle nazwą konkretnej funkcji, z której są zapisywane dzienniki. Aby dowiedzieć się więcej o kategoriach, zobacz artykuł dotyczący monitorowania.

Użyj metod ILogger<T> i ILogger , aby zapisać różne poziomy dziennika, takie jak LogWarning lub LogError. Aby dowiedzieć się więcej na temat poziomów dzienników, zobacz artykuł dotyczący monitorowania. Poziomy dziennika składników dodanych do kodu można dostosować, rejestrując filtry w ramach HostBuilder konfiguracji:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices(services =>
    {
        // Registers IHttpClientFactory.
        // By default this sends a lot of Information-level logs.
        services.AddHttpClient();
    })
    .ConfigureLogging(logging =>
    {
        // Disable IHttpClientFactory Informational logs.
        // Note -- you can also remove the handler that does the logging: https://github.com/aspnet/HttpClientFactory/issues/196#issuecomment-432755765 
        logging.AddFilter("System.Net.Http.HttpClient", LogLevel.Warning);
    })
    .Build();

W ramach konfigurowania aplikacji w Program.csprogramie można również zdefiniować zachowanie dotyczące sposobu, w jaki błędy są wyświetlane w dziennikach. Domyślnie wyjątki zgłaszane przez kod mogą być opakowane w element RpcException. Aby usunąć tę dodatkową warstwę, ustaw EnableUserCodeException właściwość na wartość "true" w ramach konfigurowania konstruktora:

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults(builder => {}, options =>
    {
        options.EnableUserCodeException = true;
    })
    .Build();

Szczegółowe dane dotyczące aplikacji

Aplikację procesu izolowanego można skonfigurować tak, aby emitować dzienniki bezpośrednio do aplikacji Szczegółowe informacje. To zachowanie zastępuje domyślne zachowanie przekazywania dzienników za pośrednictwem hosta i jest zalecane, ponieważ zapewnia kontrolę nad tym, jak te dzienniki są emitowane.

Instalowanie pakietów

Aby zapisać dzienniki bezpośrednio w aplikacji Szczegółowe informacje z kodu, dodaj odwołania do tych pakietów w projekcie:

Aby dodać te odwołania do projektu, możesz uruchomić następujące polecenia:

dotnet add package Microsoft.ApplicationInsights.WorkerService
dotnet add package Microsoft.Azure.Functions.Worker.ApplicationInsights

Konfigurowanie uruchamiania

Po zainstalowaniu pakietów należy wywołać AddApplicationInsightsTelemetryWorkerService() polecenie i ConfigureFunctionsApplicationInsights() podczas konfiguracji usługi w Program.cs pliku, tak jak w tym przykładzie:

using Microsoft.Azure.Functions.Worker;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
    
var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices(services => {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
    })
    .Build();

host.Run();

Wywołanie w celu ConfigureFunctionsApplicationInsights() dodawania elementu ITelemetryModule, który nasłuchuje zdefiniowanej przez ActivitySourcefunkcję . Spowoduje to utworzenie telemetrii zależności wymaganej do obsługi śledzenia rozproszonego. Aby dowiedzieć się więcej o AddApplicationInsightsTelemetryWorkerService() tym, jak go używać, zobacz Application Szczegółowe informacje for Worker Service applications (Aplikacja Szczegółowe informacje dla aplikacji usługi procesu roboczego).

Zarządzanie poziomami dzienników

Ważne

Host usługi Functions i izolowany proces roboczy procesu mają oddzielną konfigurację dla poziomów dziennika itp. Każda konfiguracja aplikacji Szczegółowe informacje w host.json nie wpłynie na rejestrowanie z procesu roboczego, a podobnie konfiguracja wykonana w kodzie procesu roboczego nie będzie mieć wpływu na rejestrowanie z hosta. Należy zastosować zmiany w obu miejscach, jeśli scenariusz wymaga dostosowania w obu warstwach.

Pozostała część aplikacji nadal współpracuje z elementami ILogger i ILogger<T>. Jednak domyślnie zestaw SDK usługi Application Insights dodaje filtr rejestrowania, który nakazuje rejestratorowi przechwytywanie tylko ostrzeżeń i poważniejszych dzienników. Jeśli chcesz wyłączyć to zachowanie, usuń regułę filtru w ramach konfiguracji usługi:

var host = new HostBuilder()
    .ConfigureFunctionsWorkerDefaults()
    .ConfigureServices(services => {
        services.AddApplicationInsightsTelemetryWorkerService();
        services.ConfigureFunctionsApplicationInsights();
    })
    .ConfigureLogging(logging =>
    {
        logging.Services.Configure<LoggerFilterOptions>(options =>
        {
            LoggerFilterRule defaultRule = options.Rules.FirstOrDefault(rule => rule.ProviderName
                == "Microsoft.Extensions.Logging.ApplicationInsights.ApplicationInsightsLoggerProvider");
            if (defaultRule is not null)
            {
                options.Rules.Remove(defaultRule);
            }
        });
    })
    .Build();

host.Run();

Optymalizacje wydajności

W tej sekcji opisano opcje, które można włączyć, aby zwiększyć wydajność wokół zimnego startu.

Ogólnie rzecz biorąc, aplikacja powinna używać najnowszych wersji jej podstawowych zależności. Co najmniej należy zaktualizować projekt w następujący sposób:

  1. Uaktualnij program Microsoft.Azure.Functions.Worker do wersji 1.19.0 lub nowszej.
  2. Uaktualnij zestaw Microsoft.Azure.Functions.Worker.Sdk do wersji 1.16.4 lub nowszej.
  3. Dodaj odwołanie do platformy do Microsoft.AspNetCore.Appprogramu , chyba że aplikacja jest przeznaczona dla platformy .NET Framework.

Poniższy fragment kodu przedstawia tę konfigurację w kontekście pliku projektu:

  <ItemGroup>
    <FrameworkReference Include="Microsoft.AspNetCore.App" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker" Version="1.21.0" />
    <PackageReference Include="Microsoft.Azure.Functions.Worker.Sdk" Version="1.16.4" />
  </ItemGroup>

Symbole zastępcze

Symbole zastępcze to funkcja platformy, która poprawia zimny start dla aplikacji przeznaczonych dla platformy .NET 6 lub nowszej. Aby użyć tej optymalizacji, należy jawnie włączyć symbole zastępcze, wykonując następujące kroki:

  1. Zaktualizuj konfigurację projektu, aby używać najnowszych wersji zależności, zgodnie z opisem w poprzedniej sekcji.

  2. WEBSITE_USE_PLACEHOLDER_DOTNETISOLATED Ustaw ustawienie aplikacji na 1, co można zrobić za pomocą tego polecenia az functionapp config appsettings set:

    az functionapp config appsettings set -g <groupName> -n <appName> --settings 'WEBSITE_USE_PLACEHOLDER_DOTNETISOLATED=1'
    

    W tym przykładzie zastąp <groupName> ciąg nazwą grupy zasobów i zastąp <appName> ciąg nazwą aplikacji funkcji.

  3. Upewnij się, że netFrameworkVersion właściwość aplikacji funkcji jest zgodna z platformą docelową projektu, która musi być platformą .NET 6 lub nowszą. Możesz to zrobić za pomocą tego polecenia az functionapp config set :

    az functionapp config set -g <groupName> -n <appName> --net-framework-version <framework>
    

    W tym przykładzie zastąp <framework> również ciągiem odpowiedniej wersji, takim jak v8.0, v7.0lub v6.0, zgodnie z docelową wersją platformy .NET.

  4. Upewnij się, że aplikacja funkcji jest skonfigurowana do korzystania z procesu 64-bitowego, który można wykonać za pomocą tego polecenia az functionapp config set :

    az functionapp config set -g <groupName> -n <appName> --use-32bit-worker-process false
    

Ważne

Podczas ustawiania wartości na WEBSITE_USE_PLACEHOLDER_DOTNETISOLATED1wartość wszystkie inne konfiguracje aplikacji funkcji muszą być ustawione poprawnie. W przeciwnym razie uruchomienie aplikacji funkcji może zakończyć się niepowodzeniem.

Zoptymalizowana funkcja wykonawcza

Funkcja wykonawcza jest składnikiem platformy, która powoduje uruchomienie wywołań. Zoptymalizowana wersja tego składnika jest domyślnie włączona, począwszy od wersji 1.16.2 zestawu SDK. Nie jest wymagana żadna inna konfiguracja.

ReadyToRun

Aplikację funkcji można skompilować jako pliki binarne ReadyToRun. ReadyToRun to forma kompilacji przed czasem, która może poprawić wydajność uruchamiania, aby zmniejszyć efekt zimnych startów podczas uruchamiania w planie Zużycie. Funkcja ReadyToRun jest dostępna na platformie .NET 6 i nowszych wersjach i wymaga wersji 4.0 lub nowszej środowiska uruchomieniowego usługi Azure Functions.

Funkcja ReadyToRun wymaga skompilowania projektu pod kątem architektury środowiska uruchomieniowego aplikacji hostingowej. Jeśli te ustawienia nie są wyrównane, aplikacja napotka błąd podczas uruchamiania. Wybierz identyfikator środowiska uruchomieniowego z tej tabeli:

System operacyjny Aplikacja jest 32-bitowa1 Identyfikator środowiska uruchomieniowego
Windows Prawda win-x86
Windows Fałsz win-x64
Linux Prawda Nie dotyczy (nieobsługiwane)
Linux Fałsz linux-x64

1 Tylko aplikacje 64-bitowe kwalifikują się do innych optymalizacji wydajności.

Aby sprawdzić, czy aplikacja systemu Windows jest 32-bitowa lub 64-bitowa, możesz uruchomić następujące polecenie interfejsu wiersza polecenia, zastępując <group_name> nazwę grupy zasobów i <app_name> nazwą aplikacji. Dane wyjściowe "true" wskazują, że aplikacja jest 32-bitowa, a wartość "false" wskazuje 64-bitową wartość.

 az functionapp config show -g <group_name> -n <app_name> --query "use32BitWorkerProcess"

Możesz zmienić aplikację na 64-bitową przy użyciu następującego polecenia, używając tych samych podstawień:

az functionapp config set -g <group_name> -n <app_name> --use-32bit-worker-process false`

Aby skompilować projekt jako ReadyToRun, zaktualizuj plik projektu, dodając <PublishReadyToRun> elementy i <RuntimeIdentifier> . W poniższym przykładzie przedstawiono konfigurację publikowania w aplikacji funkcji systemu Windows 64-bitowej.

<PropertyGroup>
  <TargetFramework>net8.0</TargetFramework>
  <AzureFunctionsVersion>v4</AzureFunctionsVersion>
  <RuntimeIdentifier>win-x64</RuntimeIdentifier>
  <PublishReadyToRun>true</PublishReadyToRun>
</PropertyGroup>

Jeśli nie chcesz ustawiać <RuntimeIdentifier> elementu jako część pliku projektu, możesz również skonfigurować go jako część samego gestu publikowania. Na przykład w przypadku aplikacji funkcji systemu Windows 64-bitowej polecenie interfejsu wiersza polecenia platformy .NET będzie następujące:

dotnet publish --runtime win-x64

W programie Visual Studio opcja Target Runtime (Docelowe środowisko uruchomieniowe ) w profilu publikowania powinna być ustawiona na prawidłowy identyfikator środowiska uruchomieniowego. Po ustawieniu wartości domyślnej elementu Portable nie jest używana funkcja ReadyToRun.

Wdrażanie w usłudze Azure Functions

Podczas wdrażania projektu kodu funkcji na platformie Azure musi on działać w aplikacji funkcji lub w kontenerze systemu Linux. Aplikacja funkcji i inne wymagane zasoby platformy Azure muszą istnieć przed wdrożeniem kodu.

Aplikację funkcji można również wdrożyć w kontenerze systemu Linux. Aby uzyskać więcej informacji, zobacz Praca z kontenerami i usługą Azure Functions.

Tworzenie zasobów platformy Azure

Aplikację funkcji i inne wymagane zasoby na platformie Azure można utworzyć przy użyciu jednej z następujących metod:

Publikowanie projektu kodu

Po utworzeniu aplikacji funkcji i innych wymaganych zasobów na platformie Azure można wdrożyć projekt kodu na platformie Azure przy użyciu jednej z następujących metod:

Aby uzyskać więcej informacji, zobacz Technologie wdrażania w usłudze Azure Functions.

Wymagania dotyczące wdrażania

Istnieje kilka wymagań dotyczących uruchamiania funkcji platformy .NET w modelu izolowanego procesu roboczego na platformie Azure, w zależności od systemu operacyjnego:

  • FUNCTIONS_WORKER_RUNTIME musi być ustawiona na wartość dotnet-isolated.
  • parametr netFrameworkVersion musi być ustawiony na żądaną wersję.

Podczas tworzenia aplikacji funkcji na platformie Azure przy użyciu metod w poprzedniej sekcji te wymagane ustawienia są dodawane. Podczas tworzenia tych zasobów przy użyciu szablonów usługi ARM lub plików Bicep na potrzeby automatyzacji należy upewnić się, że zostały one ustawione w szablonie.

Debugowanie

W przypadku uruchamiania lokalnego przy użyciu programu Visual Studio lub Visual Studio Code możesz debugować izolowany projekt roboczy platformy .NET w zwykły sposób. Istnieją jednak dwa scenariusze debugowania, które nie działają zgodnie z oczekiwaniami.

Debugowanie zdalne przy użyciu programu Visual Studio

Ponieważ aplikacja izolowanego procesu roboczego działa poza środowiskiem uruchomieniowym usługi Functions, musisz dołączyć zdalny debuger do oddzielnego procesu. Aby dowiedzieć się więcej na temat debugowania przy użyciu programu Visual Studio, zobacz Debugowanie zdalne.

Debugowanie podczas określania wartości docelowej programu .NET Framework

Jeśli izolowany projekt jest przeznaczony dla programu .NET Framework 4.8, bieżący zakres wersji zapoznawczej wymaga ręcznego wykonania kroków w celu włączenia debugowania. Te kroki nie są wymagane w przypadku korzystania z innej platformy docelowej.

Aplikacja powinna zaczynać się od wywołania metody jako FunctionsDebugger.Enable(); pierwszej operacji. Dzieje się tak w metodzie Main() przed zainicjowaniem programu HostBuilder. Plik Program.cs powinien wyglądać podobnie do następującego:

using System;
using System.Diagnostics;
using Microsoft.Extensions.Hosting;
using Microsoft.Azure.Functions.Worker;
using NetFxWorker;

namespace MyDotnetFrameworkProject
{
    internal class Program
    {
        static void Main(string[] args)
        {
            FunctionsDebugger.Enable();

            var host = new HostBuilder()
                .ConfigureFunctionsWorkerDefaults()
                .Build();

            host.Run();
        }
    }
}

Następnie należy ręcznie dołączyć do procesu przy użyciu debugera programu .NET Framework. Program Visual Studio nie wykonuje tego automatycznie w przypadku aplikacji programu .NET Framework procesu roboczego izolowanego, a należy unikać operacji "Rozpocznij debugowanie".

W katalogu projektu (lub w katalogu wyjściowym kompilacji) uruchom polecenie:

func host start --dotnet-isolated-debug

Spowoduje to uruchomienie procesu roboczego, a proces zostanie zatrzymany z następującym komunikatem:

Azure Functions .NET Worker (PID: <process id>) initialized in debug mode. Waiting for debugger to attach...

Gdzie <process id> jest identyfikatorem procesu roboczego. Teraz możesz użyć programu Visual Studio do ręcznego dołączenia do procesu. Aby uzyskać instrukcje dotyczące tej operacji, zobacz Jak dołączyć do uruchomionego procesu.

Po dołączeniu debugera wykonywanie procesu zostanie wznowione i będzie można debugować.

Wersje platformy .NET w wersji zapoznawczej

Przed ogólnie dostępnym wydaniem wersja platformy .NET może zostać wydana w wersji zapoznawczej lub w stanie Go-live . Aby uzyskać szczegółowe informacje na temat tych stanów, zobacz oficjalne zasady pomocy technicznej platformy .NET.

Chociaż możliwe może być skierowanie danej wersji z lokalnego projektu usługi Functions, aplikacje funkcji hostowane na platformie Azure mogą nie mieć dostępnej wersji. Usługi Azure Functions można używać tylko z wersjami w wersji zapoznawczej lub wydaniami na żywo zanotowaną w tej sekcji.

Usługa Azure Functions nie działa obecnie z żadnymi wydaniami platformy .NET "Wersja zapoznawcza" ani "Go-live". Zobacz Obsługiwane wersje , aby uzyskać listę ogólnie dostępnych wersji, których można użyć.

Korzystanie z zestawu SDK platformy .NET w wersji zapoznawczej

Aby używać usługi Azure Functions z wersją zapoznawcza platformy .NET, należy zaktualizować projekt, wykonując następujące czynności:

  1. Instalowanie odpowiedniej wersji zestawu .NET SDK w programowania
  2. TargetFramework Zmiana ustawienia w .csproj pliku

Podczas wdrażania w aplikacji funkcji na platformie Azure należy również upewnić się, że platforma została udostępniona aplikacji. Aby to zrobić w systemie Windows, możesz użyć następującego polecenia interfejsu wiersza polecenia. Zastąp <groupName> ciąg nazwą grupy zasobów i zastąp <appName> ciąg nazwą aplikacji funkcji. Zastąp <framework> ciąg odpowiednią wersją, taką jak v8.0.

az functionapp config set -g <groupName> -n <appName> --net-framework-version <framework>

Zagadnienia dotyczące korzystania z wersji zapoznawczych platformy .NET

Podczas korzystania z usługi Functions z wersjami zapoznawcza platformy .NET należy wziąć pod uwagę następujące zagadnienia:

  • Podczas tworzenia funkcji w programie Visual Studio należy użyć programu Visual Studio w wersji zapoznawczej, która obsługuje kompilowanie projektów usługi Azure Functions przy użyciu zestawów SDK platformy .NET w wersji zapoznawczej.

  • Upewnij się, że masz najnowsze narzędzia i szablony usługi Functions. Aby zaktualizować narzędzia:

    1. Przejdź do pozycji Opcje narzędzi>, wybierz pozycję Azure Functions w obszarze Projekty i rozwiązania.
    2. Wybierz pozycję Sprawdź dostępność aktualizacji i zainstaluj aktualizacje zgodnie z monitem.
  • W okresie obowiązywania wersji zapoznawczej środowisko deweloperskie może mieć najnowszą wersję zapoznawcza platformy .NET niż hostowana usługa. Może to spowodować niepowodzenie aplikacji funkcji podczas wdrażania. Aby rozwiązać ten problem, możesz określić wersję zestawu SDK do użycia w programie global.json.

    1. Uruchom polecenie i zanotuj dotnet --list-sdks wersję zapoznawcza używaną obecnie podczas programowania lokalnego.
    2. dotnet new globaljson --sdk-version <SDK_VERSION> --force Uruchom polecenie , gdzie <SDK_VERSION> jest wersją używaną lokalnie. Na przykład powoduje, dotnet new globaljson --sdk-version dotnet-sdk-8.0.100-preview.7.23376.3 --force że system używa zestawu .NET 8 Preview 7 SDK podczas kompilowania projektu.

Uwaga

Ze względu na ładowanie just in time struktur w wersji zapoznawczej aplikacje funkcji działające w systemie Windows mogą mieć zwiększone czasy zimnego uruchamiania w porównaniu z wcześniejszymi wersjami ogólnie dostępnymi.

Następne kroki