Nuta
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zalogować się lub zmienić katalogi.
Dostęp do tej strony wymaga autoryzacji. Możesz spróbować zmienić katalogi.
Usługa Azure Functions wykonuje kod aplikacji przy użyciu procedur obsługi specyficznych dla języka. Te programy obsługi specyficzne dla języka umożliwiają usłudze Functions obsługę większości języków kluczowych domyślnie. Może być jednak konieczne uruchomienie kodu w innym języku lub pakiecie.
Niestandardowe programy obsługi to lekkie serwery internetowe, które odbierają zdarzenia z procesu hostującego Azure Functions. Niestandardowe programy obsługi umożliwiają wdrażanie w usłudze Azure Functions dowolnego projektu kodu obsługującego typy pierwotne HTTP.
Niestandardowe programy obsługi najlepiej sprawdzają się w sytuacjach, w których chcesz:
- Zaimplementuj aplikację funkcji w języku, który nie jest obecnie oferowany natywnie, na przykład Go lub Rust.
- Zaimplementuj aplikację funkcji w środowisku uruchomieniowym, które nie jest obecnie polecane domyślnie, na przykład Deno.
- Wdróż serwer utworzony przy użyciu standardowych zestawów SDK MCP w usłudze Azure Functions.
Za pomocą niestandardowych procedur obsługi można używać wyzwalaczy oraz powiązań wejściowych i wyjściowych za pośrednictwem pakietów rozszerzeń.
Rozpocznij pracę z niestandardowymi procedurami obsługi usługi Azure Functions, korzystając z przewodników Szybki start w języku Go i Rust.
Omówienie
Na poniższym diagramie przedstawiono relację między hostem usługi Functions i serwerem internetowym zaimplementowanym jako procedura obsługi niestandardowej.
- Każde zdarzenie wyzwala żądanie wysyłane do hosta usługi Functions. Zdarzenie to dowolny wyzwalacz, który obsługuje usługa Azure Functions.
- Następnie host usługi Functions wystawia ładunek żądania na serwerze internetowym. Ładunek zawiera dane wyzwalacza i powiązania wejściowego oraz inne metadane dla funkcji.
- Serwer internetowy wykonuje pojedynczą funkcję i zwraca ładunek odpowiedzi do hosta usługi Functions.
- Host usługi Functions przekazuje dane z odpowiedzi na powiązania wyjściowe funkcji do przetwarzania.
Aplikacja usługi Azure Functions zaimplementowana jako niestandardowa procedura obsługi musi skonfigurować pliki host.json, local.settings.json i function.json zgodnie z kilkoma konwencjami.
Wdrażanie własnych serwerów MCP
Niestandardowe programy obsługi umożliwiają również hostowanie serwerów MCP, które są kompilowane przy użyciu oficjalnych zestawów SDK MCP w usłudze Azure Functions. Niestandardowe programy obsługi zapewniają proste i usprawnione środowisko do hostowania serwerów MCP na platformie Azure. Aby uzyskać więcej informacji, zobacz Samodzielnie hostowany zdalny serwer MCP w usłudze Azure Functions.
Uwaga
Możliwość hostowania serwerów MCP usługi Azure Functions tworzonych przy użyciu oficjalnych zestawów SDK MCP jest obecnie dostępna w wersji zapoznawczej.
Struktura aplikacji
Aby zaimplementować niestandardową procedurę obsługi, aplikacja wymaga następujących aspektów:
- Plik host.json w katalogu głównym aplikacji
- Plik local.settings.json w katalogu głównym aplikacji
- Plik function.json dla każdej funkcji (wewnątrz folderu zgodnego z nazwą funkcji)
- Polecenie, skrypt lub plik wykonywalny uruchamiający serwer internetowy
Na poniższym diagramie pokazano, jak te pliki wyglądają w systemie plików dla funkcji o nazwie "MyQueueFunction" i pliku wykonywalnego niestandardowego programu obsługi o nazwie handler.exe.
| /MyQueueFunction
| function.json
|
| host.json
| local.settings.json
| handler.exe
Konfigurowanie
Aplikację można skonfigurować za pomocą plikówhost.json i local.settings.json .
host.json
host.json kieruje hosta usługi Functions, gdzie wysyłać żądania, wskazując serwer internetowy, który może przetwarzać zdarzenia HTTP.
Zdefiniuj niestandardową procedurę obsługi, konfigurując plik host.json ze szczegółowymi informacjami na temat uruchamiania serwera internetowego customHandler za pośrednictwem sekcji .
{
"version": "2.0",
"customHandler": {
"description": {
"defaultExecutablePath": "handler.exe"
}
}
}
Sekcja customHandler wskazuje element docelowy zgodnie z definicją elementu defaultExecutablePath. Obiektem docelowym wykonywania może być polecenie, plik wykonywalny lub plik, w którym zaimplementowano serwer internetowy.
arguments Użyj tablicy, aby przekazać wszystkie argumenty do pliku wykonywalnego. Argumenty obsługują rozszerzanie zmiennych środowiskowych (ustawień aplikacji) przy użyciu %% notacji.
Możesz również zmienić katalog roboczy używany przez plik wykonywalny za pomocą polecenia workingDirectory.
{
"version": "2.0",
"customHandler": {
"description": {
"defaultExecutablePath": "app/handler.exe",
"arguments": [
"--database-connection-string",
"%DATABASE_CONNECTION_STRING%"
],
"workingDirectory": "app"
}
}
}
Obsługa powiązań
Wyzwalacze standardowe wraz z powiązaniami wejściowymi i wyjściowymi są dostępne przez odwoływanie się do pakietów rozszerzeń w pliku host.json .
local.settings.json
local.settings.json definiuje ustawienia aplikacji używane podczas lokalnego uruchamiania aplikacji funkcji. Ponieważ może zawierać wpisy tajne, wyklucz local.settings.json z kontroli źródła. Na platformie Azure zamiast tego użyj ustawień aplikacji.
W przypadku niestandardowych procedur obsługi ustaw wartość FUNCTIONS_WORKER_RUNTIMECustom na w local.settings.json.
{
"IsEncrypted": false,
"Values": {
"FUNCTIONS_WORKER_RUNTIME": "Custom"
}
}
Metadane funkcji
W przypadku korzystania z niestandardowej procedury obsługi zawartość function.json jest taka sama jak podczas definiowania funkcji w dowolnym innym kontekście. Jedynym wymaganiem jest umieszczenie pliku function.json w folderze o nazwie odpowiadającej nazwie funkcji.
Poniższe function.json konfiguruje funkcję, która ma wyzwalacz kolejki i powiązanie wyjściowe kolejki. Ponieważ znajduje się on w folderze o nazwie MyQueueFunction, definiuje funkcję o nazwie MyQueueFunction.
MyQueueFunction/function.json
{
"bindings": [
{
"name": "myQueueItem",
"type": "queueTrigger",
"direction": "in",
"queueName": "messages-incoming",
"connection": "AzureWebJobsStorage"
},
{
"name": "$return",
"type": "queue",
"direction": "out",
"queueName": "messages-outgoing",
"connection": "AzureWebJobsStorage"
}
]
}
Ładunek żądania
Gdy host usługi Functions odbiera komunikat kolejki, wysyła żądanie POST HTTP do niestandardowego programu obsługi z ładunkiem w treści.
Poniższy kod przedstawia przykładowy ładunek żądania. Ładunek zawiera strukturę JSON z dwoma elementami członkowskimi: Data i Metadata.
Element Data członkowski zawiera klucze zgodne z nazwami danych wejściowych i wyzwalaczy zgodnie z definicją w tablicy powiązań w pliku function.json .
Element Metadata członkowski zawiera metadane wygenerowane ze źródła zdarzeń.
{
"Data": {
"myQueueItem": "{ message: \"Message sent\" }"
},
"Metadata": {
"DequeueCount": 1,
"ExpirationTime": "2019-10-16T17:58:31+00:00",
"Id": "800ae4b3-bdd2-4c08-badd-f08e5a34b865",
"InsertionTime": "2019-10-09T17:58:31+00:00",
"NextVisibleTime": "2019-10-09T18:08:32+00:00",
"PopReceipt": "AgAAAAMAAAAAAAAAAgtnj8x+1QE=",
"sys": {
"MethodName": "QueueTrigger",
"UtcNow": "2019-10-09T17:58:32.2205399Z",
"RandGuid": "24ad4c06-24ad-4e5b-8294-3da9714877e9"
}
}
}
Ładunek odpowiedzi
Zgodnie z konwencją odpowiedzi funkcji są formatowane jako pary klucz/wartość. Obsługiwane klucze obejmują:
|
|
Typ danych | Uwagi |
|---|---|---|
Outputs |
obiekt | Przechowuje wartości odpowiedzi zdefiniowane przez tablicę bindings w function.json.Jeśli na przykład funkcja jest skonfigurowana przy użyciu wyjściowego powiązania kolejki o nazwie "myQueueOutput", to Outputs zawiera klucz nazwany myQueueOutput, który niestandardowy program obsługi używa do wysyłanych do kolejki komunikatów. |
Logs |
macierz | Komunikaty wyświetlane w dziennikach wywołania usługi Functions. Podczas uruchamiania na platformie Azure komunikaty są wyświetlane w usłudze Application Insights. |
ReturnValue |
ciąg | Służy do dostarczania odpowiedzi, gdy dane wyjściowe są skonfigurowane tak jak $return w pliku function.json . |
W tej tabeli przedstawiono przykład ładunku odpowiedzi.
{
"Outputs": {
"res": {
"body": "Message enqueued"
},
"myQueueOutput": [
"queue message 1",
"queue message 2"
]
},
"Logs": [
"Log message 1",
"Log message 2"
],
"ReturnValue": "{\"hello\":\"world\"}"
}
Przykłady
Niestandardowe programy obsługi można zaimplementować w dowolnym języku, który obsługuje odbieranie zdarzeń HTTP. W poniższych przykładach pokazano, jak zaimplementować niestandardową procedurę obsługi przy użyciu języka programowania Go.
Funkcja z powiązaniami
W tym przykładzie pokazano funkcję o nazwie order , która akceptuje POST żądanie z ładunkiem reprezentującym zamówienie produktu. Po opublikowaniu zamówienia w funkcji program tworzy komunikat usługi Queue Storage i zwraca odpowiedź HTTP.
Implementacja
W folderze o nazwie order plik function.json konfiguruje funkcję wyzwalaną przez protokół HTTP.
order/function.json
{
"bindings": [
{
"type": "httpTrigger",
"direction": "in",
"name": "req",
"methods": ["post"]
},
{
"type": "http",
"direction": "out",
"name": "res"
},
{
"type": "queue",
"name": "message",
"direction": "out",
"queueName": "orders",
"connection": "AzureWebJobsStorage"
}
]
}
Ta funkcja jest zdefiniowana jako funkcja wyzwalana przez protokół HTTP, która zwraca odpowiedź HTTP i zwraca komunikat usługi Queue Storage.
W katalogu głównym aplikacji plik host.json jest skonfigurowany do uruchamiania pliku wykonywalnego o nazwie handler.exe (handler w systemie Linux lub macOS).
{
"version": "2.0",
"customHandler": {
"description": {
"defaultExecutablePath": "handler.exe"
}
},
"extensionBundle": {
"id": "Microsoft.Azure.Functions.ExtensionBundle",
"version": "[4.*, 5.0.0)"
}
}
Jest to żądanie HTTP wysyłane do środowiska uruchomieniowego usługi Functions.
POST http://127.0.0.1:7071/api/order HTTP/1.1
Content-Type: application/json
{
"id": 1005,
"quantity": 2,
"color": "black"
}
Środowisko uruchomieniowe usługi Functions wysyła następujące żądanie HTTP do niestandardowego programu obsługi:
POST http://127.0.0.1:<FUNCTIONS_CUSTOMHANDLER_PORT>/order HTTP/1.1
Content-Type: application/json
{
"Data": {
"req": {
"Url": "http://localhost:7071/api/order",
"Method": "POST",
"Query": "{}",
"Headers": {
"Content-Type": [
"application/json"
]
},
"Params": {},
"Body": "{\"id\":1005,\"quantity\":2,\"color\":\"black\"}"
}
},
"Metadata": {
}
}
Uwaga
Niektóre części ładunku zostały usunięte w celu zwięzłości.
handler.exe to skompilowany niestandardowy program obsługi języka Go, który uruchamia serwer internetowy i odpowiada na żądania wywołania funkcji z hosta usługi Functions.
package main
import (
"encoding/json"
"fmt"
"log"
"net/http"
"os"
)
type InvokeRequest struct {
Data map[string]json.RawMessage
Metadata map[string]interface{}
}
type InvokeResponse struct {
Outputs map[string]interface{}
Logs []string
ReturnValue interface{}
}
func orderHandler(w http.ResponseWriter, r *http.Request) {
var invokeRequest InvokeRequest
d := json.NewDecoder(r.Body)
d.Decode(&invokeRequest)
var reqData map[string]interface{}
json.Unmarshal(invokeRequest.Data["req"], &reqData)
outputs := make(map[string]interface{})
outputs["message"] = reqData["Body"]
resData := make(map[string]interface{})
resData["body"] = "Order enqueued"
outputs["res"] = resData
invokeResponse := InvokeResponse{outputs, nil, nil}
responseJson, _ := json.Marshal(invokeResponse)
w.Header().Set("Content-Type", "application/json")
w.Write(responseJson)
}
func main() {
customHandlerPort, exists := os.LookupEnv("FUNCTIONS_CUSTOMHANDLER_PORT")
if !exists {
customHandlerPort = "8080"
}
mux := http.NewServeMux()
mux.HandleFunc("/order", orderHandler)
fmt.Println("Go server Listening on: ", customHandlerPort)
log.Fatal(http.ListenAndServe(":"+customHandlerPort, mux))
}
W tym przykładzie niestandardowy program obsługujący uruchamia serwer WWW do obsługi zdarzeń HTTP i nasłuchuje żądań za pośrednictwem FUNCTIONS_CUSTOMHANDLER_PORT.
Mimo że host usługi Functions odbiera oryginalne żądanie HTTP pod adresem /api/order, wywołuje niestandardową procedurę obsługi, używając nazwy funkcji (czyli nazwy jej folderu). W tym przykładzie funkcja jest definiowana w ścieżce ./order Host wysyła niestandardowy program obsługi żądania HTTP w ścieżce /order.
Podczas wysyłania POST żądań do tej funkcji dane wyzwalacza i metadane funkcji są dostępne za pośrednictwem treści żądania HTTP. Dostęp do oryginalnej treści żądania HTTP można uzyskać w ładunku Data.req.Body.
Odpowiedź funkcji jest formatowana w pary klucz/wartość, w których element członkowski przechowuje wartość JSON, w której Outputs klucze są zgodne z danymi wyjściowymi zdefiniowanymi w pliku function.json .
Jest to przykładowy ładunek, który ten program obsługi powraca do hosta usługi Functions.
{
"Outputs": {
"message": "{\"id\":1005,\"quantity\":2,\"color\":\"black\"}",
"res": {
"body": "Order enqueued"
}
},
"Logs": null,
"ReturnValue": null
}
message Ustawiając dane wyjściowe równe danych zamówienia, które pochodzą z żądania, funkcja generuje dane, które nakazują dane do skonfigurowanej kolejki. Host usługi Functions zwraca również odpowiedź HTTP skonfigurowaną w res obiekcie wywołującym.
Funkcja tylko http
W przypadku funkcji wyzwalanych przez protokół HTTP, które nie mają dodatkowych powiązań ani wyjść, zamiast korzystać z niestandardowych ładunków żądania i odpowiedzi, możesz chcieć, aby twój obsługujący pracował bezpośrednio z żądaniem i odpowiedzią HTTP. Można skonfigurować to zachowanie w host.json, używając ustawienia, które obsługuje przesyłanie strumieniowe odpowiedzi.
Ważne
Podstawowym celem funkcji niestandardowych procedur obsługi jest włączenie języków i środowisk uruchomieniowych, które nie mają obecnie najwyższej jakości obsługi w usłudze Azure Functions. Chociaż możesz uruchamiać aplikacje internetowe przy użyciu niestandardowych procedur obsługi, usługa Azure Functions nie jest standardowym zwrotnym serwerem proxy. Niektóre składniki żądania HTTP, takie jak niektóre nagłówki i trasy, mogą być ograniczone. Aplikacja może również doświadczać nadmiernego zimnego startu.
Aby rozwiązać te okoliczności, rozważ uruchomienie aplikacji internetowych w usłudze aplikacja systemu Azure Service.
W poniższym przykładzie pokazano, jak skonfigurować funkcję wyzwalaną przez protokół HTTP bez dodatkowych powiązań ani danych wyjściowych. Scenariusz zaimplementowany w tym przykładzie zawiera funkcję o nazwie hello , która akceptuje GET element lub POST .
Implementacja
W folderze o nazwie hello plik function.json konfiguruje funkcję wyzwalaną przez protokół HTTP.
hello/function.json
{
"bindings": [
{
"type": "httpTrigger",
"authLevel": "anonymous",
"direction": "in",
"name": "req",
"methods": ["get", "post"]
},
{
"type": "http",
"direction": "out",
"name": "res"
}
]
}
Funkcja jest skonfigurowana do akceptowania żądań GET i POST , a wartość wyniku jest dostarczana za pomocą argumentu o nazwie res.
W katalogu głównym aplikacji plik host.json jest skonfigurowany do uruchamiania handler.exe i enableProxyingHttpRequest jest ustawiony na truewartość .
{
"version": "2.0",
"customHandler": {
"description": {
"defaultExecutablePath": "handler.exe"
},
"enableProxyingHttpRequest": true
}
}
Poniżej znajduje się żądanie POST do hosta usługi Functions. Następnie host Functions wysyła żądanie do niestandardowej procedury obsługi.
POST http://127.0.0.1:7071/api/hello HTTP/1.1
Content-Type: application/json
{
"message": "Hello World!"
}
Plik handler.go implementuje serwer internetowy i funkcję HTTP.
package main
import (
"fmt"
"io/ioutil"
"log"
"net/http"
"os"
)
func helloHandler(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Content-Type", "application/json")
if r.Method == "GET" {
w.Write([]byte("hello world"))
} else {
body, _ := ioutil.ReadAll(r.Body)
w.Write(body)
}
}
func main() {
customHandlerPort, exists := os.LookupEnv("FUNCTIONS_CUSTOMHANDLER_PORT")
if !exists {
customHandlerPort = "8080"
}
mux := http.NewServeMux()
mux.HandleFunc("/api/hello", helloHandler)
fmt.Println("Go server Listening on: ", customHandlerPort)
log.Fatal(http.ListenAndServe(":"+customHandlerPort, mux))
}
W tym przykładzie niestandardowy program obsługi tworzy serwer internetowy do obsługi zdarzeń HTTP i nasłuchuje żądań za pośrednictwem komponentu FUNCTIONS_CUSTOMHANDLER_PORT.
GET żądania są obsługiwane przez zwrócenie ciągu, a POST żądania mają dostęp do treści żądania.
Trasa dla funkcji order w tym miejscu jest /api/hellotaka sama jak oryginalne żądanie.
Uwaga
FUNCTIONS_CUSTOMHANDLER_PORT nie jest publicznym portem używanym do wywoływania funkcji. Host usługi Functions używa tego portu do wywoływania niestandardowego modułu obsługi.
Wdrażanie
Można wdrożyć niestandardowy program obsługi we wszystkich opcjach hostingu usługi Azure Functions. Jeśli program obsługi wymaga zależności systemu operacyjnego lub platformy (na przykład środowiska uruchomieniowego języka), może być konieczne użycie niestandardowego kontenera.
Podczas tworzenia aplikacji funkcji na platformie Azure dla niestandardowych procedur obsługi, wybierz .NET Core jako technologię.
Aby wdrożyć niestandardową aplikację obsługi przy użyciu narzędzi Azure Functions Core Tools, uruchom następujące polecenie.
func azure functionapp publish $functionAppName
Uwaga
Upewnij się, że wszystkie pliki wymagane do uruchomienia niestandardowej procedury obsługi znajdują się w folderze i uwzględnione we wdrożeniu. Jeśli niestandardowa procedura obsługi jest binarnym plikiem wykonywalnym lub ma zależności specyficzne dla platformy, upewnij się, że te pliki są zgodne z docelową platformą wdrażania.
Ograniczenia
- Niestandardowy serwer sieci Web programu obsługi musi być uruchomiony w ciągu 60 sekund.
Przykłady
Przykłady implementacji funkcji w różnych językach można znaleźć w repozytorium GitHub z niestandardowymi przykładami obsługi.
Rozwiązywanie problemów i pomoc techniczna
Rejestrowanie śledzenia
Jeśli nie można uruchomić niestandardowego procesu obsługi lub jeśli ma problemy z komunikacją z hostem usługi Functions, zwiększ poziom dziennika aplikacji funkcji, aby wyświetlić Trace więcej komunikatów diagnostycznych z hosta.
Aby zmienić domyślny poziom dziennika aplikacji funkcji, skonfiguruj logLevel ustawienie w logging sekcji host.json.
{
"version": "2.0",
"customHandler": {
"description": {
"defaultExecutablePath": "handler.exe"
}
},
"logging": {
"logLevel": {
"default": "Trace"
}
}
}
Host usługi Functions generuje dodatkowe komunikaty dziennika, w tym informacje związane z niestandardowym procesem obsługi. Użyj dzienników, aby zbadać problemy podczas uruchamiania niestandardowego procesu obsługi lub wywoływania funkcji w niestandardowej procedurze obsługi.
Lokalnie dzienniki są drukowane w konsoli programu .
Na platformie Azure wykonaj zapytanie o ślady usługi Application Insights, aby wyświetlić komunikaty dziennika. Jeśli aplikacja generuje dużą liczbę dzienników, do usługi Application Insights są wysyłane tylko podzbiór komunikatów dziennika. Wyłącz próbkowanie , aby upewnić się, że wszystkie komunikaty są rejestrowane.
Testowanie niestandardowej procedury obsługi w izolacji
Niestandardowe aplikacje obsługi to procesy serwera internetowego, dlatego warto uruchomić je osobno i testować wywoływanie funkcji, wysyłając przykładowe żądania HTTP. W przypadku wysyłania żądań HTTP z ładunkami upewnij się, że wybrano narzędzie, które zapewnia bezpieczeństwo danych. Aby uzyskać więcej informacji, zobacz Narzędzia do testowania HTTP.
Tę strategię można również użyć w potokach ciągłej integracji/ciągłego wdrażania do uruchamiania testów automatycznych w niestandardowej procedurze obsługi.
Środowisko wykonywania
Niestandardowe programy obsługi działają w tym samym środowisku co typowa aplikacja usługi Azure Functions. Przetestuj program obsługi, aby upewnić się, że środowisko zawiera wszystkie zależności, które należy uruchomić. W przypadku aplikacji, które wymagają dodatkowych zależności, może być konieczne ich uruchomienie przy użyciu niestandardowego obrazu kontenera hostowanego w planie Premium usługi Azure Functions.
Uzyskiwanie pomocy technicznej
Jeśli potrzebujesz pomocy w aplikacji funkcji z niestandardowymi procedurami obsługi, możesz przesłać żądanie za pośrednictwem zwykłych kanałów pomocy technicznej. Jednak ze względu na szeroką gamę możliwych języków używanych do tworzenia niestandardowych aplikacji obsługi obsługa nie jest nieograniczona.
Obsługa jest dostępna, jeśli host usługi Functions ma problemy z uruchamianiem lub komunikowaniem się z niestandardowym procesem obsługi. W przypadku problemów specyficznych dla wewnętrznego działania niestandardowego procesu obsługi, takich jak problemy z wybranym językiem lub strukturą, nasz zespół pomocy technicznej nie może udzielić pomocy w tym kontekście.
Następne kroki
Rozpocznij tworzenie aplikacji usługi Azure Functions w języku Go lub Rust, korzystając z niestandardowego przewodnika Szybki start dla procedur obsługi.