Share via


Skapa ett REST API för en starthändelse för tokenutfärding i Azure Functions

Den här artikeln beskriver hur du skapar ett REST API med en starthändelse för tokenutfärdning med Hjälp av Azure Functions i Azure-portalen. Du skapar en Azure-funktionsapp och en HTTP-utlösarfunktion som kan returnera extra anspråk för din token.

Förutsättningar

Den här artikeln beskriver hur du skapar ett REST API för en starthändelse för tokenutfärdande med hjälp av NuGet-biblioteket Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents och konfigurerar det för autentisering. Du skapar en HTTP-utlösarfunktion i Visual Studio eller Visual Studio Code, konfigurerar den för autentisering och distribuerar den till Azure-portalen, där den kan nås via Azure Functions.

Förutsättningar

Kommentar

NuGet-biblioteket Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents finns för närvarande i förhandsversion. Steg i den här artikeln kan komma att ändras. För implementering av allmän tillgänglighet för implementering av en starthändelse för tokenutfärdning kan du göra det med hjälp av Azure-portalen.

Skapa Azure-funktionsappen

I Azure-portalen skapar du en Azure-funktionsapp och dess associerade resurs innan du fortsätter att skapa funktionen HTTP-utlösare.

  1. Logga in på Azure-portalen som minst programadministratöroch autentiseringsadministratör.

  2. I menyn i Azure-portalen eller på sidan Start väljer du Skapa en resurs.

  3. Sök efter och välj Funktionsapp och välj Skapa.

  4. På sidan Grundläggande skapar du en funktionsapp med hjälp av inställningarna som anges i följande tabell:

    Inställning Föreslaget värde beskrivning
    Abonnemang Din prenumeration Prenumerationen under vilken den nya funktionsappen ska skapas.
    Resursgrupp myResourceGroup Välj och befintlig resursgrupp eller namn på den nya där du skapar funktionsappen.
    Funktionsappens namn Globalt unikt namn Ett namn som identifierar den nya funktionsappen. Giltiga tecken är a-z (skiftlägesokänsligt), 0-9 och -.
    Distribuera kod eller containeravbildning Kod Alternativ för att publicera kodfiler eller en Docker-container. I den här självstudien väljer du Kod.
    Körningsstack .NET Önskat programmeringsspråk. I den här självstudien väljer du .NET.
    Version: 6 (LTS) i processen Version av .NET-körningen. Processen innebär att du kan skapa och ändra funktioner i portalen, vilket rekommenderas för den här guiden
    Region Önskad region Välj en region som är nära dig eller nära andra tjänster som dina funktioner kan komma åt.
    Operativsystem Windows Operativsystemet är förvalt baserat på valet av körningsstack.
    Plantyp Förbrukning (serverlös) Värdplan som definierar hur resurser allokeras till din funktionsapp.
  5. Välj Granska + skapa för att granska appkonfigurationsvalen och välj sedan Skapa. Distributionen tar några minuter.

  6. När du har distribuerat väljer du Gå till resurs för att visa din nya funktionsapp.

Skapa en HTTP-utlösarfunktion

När Azure-funktionsappen har skapats skapar du en HTTP-utlösarfunktion i appen. Med HTTP-utlösaren kan du anropa en funktion med en HTTP-begäran och refereras av ditt anpassade Microsoft Entra-autentiseringstillägg.

  1. På sidan Översikt i funktionsappen väljer du fönstret Funktioner och väljer Skapa funktion under Skapa i Azure-portalen.
  2. I fönstret Skapa funktion lämnar du egenskapen Utvecklingsmiljö som Utveckla i portalen. Under Mall väljer du HTTP-utlösare.
  3. Under Mallinformation anger du CustomAuthenticationExtensionsAPI för egenskapen Ny funktion .
  4. För auktoriseringsnivån väljer du Funktion.
  5. Välj Skapa. Skärmbild som visar hur du väljer utvecklingsmiljön och mallen.

Redigera funktionen

Koden läser det inkommande JSON-objektet och Microsoft Entra-ID skickar JSON-objektet till ditt API. I det här exemplet läss korrelations-ID-värdet. Sedan returnerar koden en samling anpassade anspråk, inklusive den ursprungliga CorrelationId, ApiVersion azure-funktionens, en DateOfBirth och CustomRoles som returneras till Microsoft Entra-ID.

  1. På menyn under Utvecklare väljer du Kod + Test.

  2. Ersätt hela koden med följande kodfragment och välj sedan Spara.

    #r "Newtonsoft.Json"
    using System.Net;
    using Microsoft.AspNetCore.Mvc;
    using Microsoft.Extensions.Primitives;
    using Newtonsoft.Json;
    public static async Task<IActionResult> Run(HttpRequest req, ILogger log)
    {
        log.LogInformation("C# HTTP trigger function processed a request.");
        string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
        dynamic data = JsonConvert.DeserializeObject(requestBody);
    
        // Read the correlation ID from the Microsoft Entra request    
        string correlationId = data?.data.authenticationContext.correlationId;
    
        // Claims to return to Microsoft Entra
        ResponseContent r = new ResponseContent();
        r.data.actions[0].claims.CorrelationId = correlationId;
        r.data.actions[0].claims.ApiVersion = "1.0.0";
        r.data.actions[0].claims.DateOfBirth = "01/01/2000";
        r.data.actions[0].claims.CustomRoles.Add("Writer");
        r.data.actions[0].claims.CustomRoles.Add("Editor");
        return new OkObjectResult(r);
    }
    public class ResponseContent{
        [JsonProperty("data")]
        public Data data { get; set; }
        public ResponseContent()
        {
            data = new Data();
        }
    }
    public class Data{
        [JsonProperty("@odata.type")]
        public string odatatype { get; set; }
        public List<Action> actions { get; set; }
        public Data()
        {
            odatatype = "microsoft.graph.onTokenIssuanceStartResponseData";
            actions = new List<Action>();
            actions.Add(new Action());
        }
    }
    public class Action{
        [JsonProperty("@odata.type")]
        public string odatatype { get; set; }
        public Claims claims { get; set; }
        public Action()
        {
            odatatype = "microsoft.graph.tokenIssuanceStart.provideClaimsForToken";
            claims = new Claims();
        }
    }
    public class Claims{
        [JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
        public string CorrelationId { get; set; }
        [JsonProperty(NullValueHandling = NullValueHandling.Ignore)]
        public string DateOfBirth { get; set; }
        public string ApiVersion { get; set; }
        public List<string> CustomRoles { get; set; }
        public Claims()
        {
            CustomRoles = new List<string>();
        }
    }
    
  3. På den översta menyn väljer du Hämta funktions-URL och kopierar URL-värdet . Den här funktions-URL:en kan användas när du konfigurerar ett anpassat autentiseringstillägg.

Skapa och skapa Azure-funktionsappen

I det här steget skapar du ett HTTP-utlösarfunktions-API med din IDE, installerar nödvändiga NuGet-paket och kopierar i exempelkoden. Du skapar projektet och kör funktionen för att extrahera den lokala funktions-URL:en.

Skapa programmet

Följ dessa steg för att skapa en Azure-funktionsapp:

  1. Öppna Visual Studio och välj Skapa ett nytt projekt.
  2. Sök efter och välj Azure Functions och välj sedan Nästa.
  3. Ge projektet ett namn, till exempel AuthEventsTrigger. Det är en bra idé att matcha lösningsnamnet med projektnamnet.
  4. Välj en plats för projektet. Välj Nästa.
  5. Välj .NET 6.0 (långsiktig support) som målramverk.
  6. Välj Http-utlösare som funktionstyp och auktoriseringsnivån är inställd på Funktion. Välj Skapa.
  7. I Solution Explorer byter du namn på filen Function1.cs till AuthEventsTrigger.cs och godkänner ändringsförslaget för byt namn.

Installera NuGet-paket och skapa projektet

När du har skapat projektet måste du installera nödvändiga NuGet-paket och skapa projektet.

  1. På den översta menyn i Visual Studio väljer du Projekt och sedan Hantera NuGet-paket.
  2. Välj fliken Bläddra och sök sedan efter och välj Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents i den högra rutan. Välj Installera.
  3. Använd och acceptera ändringarna i popup-fönster som visas.

Lägga till exempelkoden

Funktions-API:et är källan till extra anspråk för din token. I den här artikeln hårdkodar vi värdena för exempelappen. I produktion kan du hämta information om användaren från ett externt datalager.

I filen AuthEventsTrigger.cs ersätter du hela innehållet i filen med följande kod:

using System;
using Microsoft.Azure.WebJobs;
using Microsoft.Extensions.Logging;
using Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents.TokenIssuanceStart;
using Microsoft.Azure.WebJobs.Extensions.AuthenticationEvents;

namespace AuthEventsTrigger
{
    public static class AuthEventsTrigger
    {
        [FunctionName("onTokenIssuanceStart")]
        public static WebJobsAuthenticationEventResponse Run(
            [WebJobsAuthenticationEventsTrigger] WebJobsTokenIssuanceStartRequest request, ILogger log)
        {
            try
            {
                // Checks if the request is successful and did the token validation pass
                if (request.RequestStatus == WebJobsAuthenticationEventsRequestStatusType.Successful)
                {
                    // Fetches information about the user from external data store
                    // Add new claims to the token's response
                    request.Response.Actions.Add(
                        new WebJobsProvideClaimsForToken(
                            new WebJobsAuthenticationEventsTokenClaim("dateOfBirth", "01/01/2000"),
                            new WebJobsAuthenticationEventsTokenClaim("customRoles", "Writer", "Editor"),
                            new WebJobsAuthenticationEventsTokenClaim("apiVersion", "1.0.0"),
                            new WebJobsAuthenticationEventsTokenClaim(
                                "correlationId", 
                                request.Data.AuthenticationContext.CorrelationId.ToString())));
                }
                else
                {
                    // If the request fails, such as in token validation, output the failed request status, 
                    // such as in token validation or response validation.
                    log.LogInformation(request.StatusMessage);
                }
                return request.Completed();
            }
            catch (Exception ex) 
            { 
                return request.Failed(ex);
            }
        }
    }
}

Skapa och köra projektet lokalt

Projektet har skapats och exempelkoden har lagts till. Med din IDE måste vi skapa och köra projektet lokalt för att extrahera den lokala funktions-URL:en.

  1. Gå till Skapa på den översta menyn och välj Skapa lösning.
  2. Tryck på F5 eller välj AuthEventsTrigger på den översta menyn för att köra funktionen.
  3. Kopiera funktions-URL :en från terminalen som öppnas när funktionen körs. Detta kan användas när du konfigurerar ett anpassat autentiseringstillägg.

Det är en bra idé att testa funktionen lokalt innan du distribuerar den till Azure. Vi kan använda en dummy-JSON-brödtext som imiterar den begäran som Microsoft Entra-ID skickar till ditt REST-API. Använd önskat API-testverktyg för att anropa funktionen direkt.

  1. Öppna local.settings.json i din IDE och ersätt koden med följande JSON. Vi kan ange "AuthenticationEvents__BypassTokenValidation" till true för lokala teständamål.

    {
      "IsEncrypted": false,
      "Values": {
        "AzureWebJobsStorage": "",
        "AzureWebJobsSecretStorageType": "files",
        "FUNCTIONS_WORKER_RUNTIME": "dotnet",
        "AuthenticationEvents__BypassTokenValidation" : true
      }
    }
    
  2. Använd det API-testverktyg du föredrar, skapa en ny HTTP-begäran och ange HTTP-metoden till POST.

  3. Använd följande JSON-brödtext som imiterar den begäran som Microsoft Entra-ID skickar till rest-API:et.

    {
        "type": "microsoft.graph.authenticationEvent.tokenIssuanceStart",
        "source": "/tenants/aaaabbbb-0000-cccc-1111-dddd2222eeee/applications/00001111-aaaa-2222-bbbb-3333cccc4444",
        "data": {
            "@odata.type": "microsoft.graph.onTokenIssuanceStartCalloutData",
            "tenantId": "aaaabbbb-0000-cccc-1111-dddd2222eeee",
            "authenticationEventListenerId": "11112222-bbbb-3333-cccc-4444dddd5555",
            "customAuthenticationExtensionId": "22223333-cccc-4444-dddd-5555eeee6666",
            "authenticationContext": {
                "correlationId": "aaaa0000-bb11-2222-33cc-444444dddddd",
                "client": {
                    "ip": "127.0.0.1",
                    "locale": "en-us",
                    "market": "en-us"
                },
                "protocol": "OAUTH2.0",
                "clientServicePrincipal": {
                    "id": "aaaaaaaa-0000-1111-2222-bbbbbbbbbbbb",
                    "appId": "00001111-aaaa-2222-bbbb-3333cccc4444",
                    "appDisplayName": "My Test application",
                    "displayName": "My Test application"
                },
                "resourceServicePrincipal": {
                    "id": "aaaaaaaa-0000-1111-2222-bbbbbbbbbbbb",
                    "appId": "00001111-aaaa-2222-bbbb-3333cccc4444",
                    "appDisplayName": "My Test application",
                    "displayName": "My Test application"
                },
                "user": {
                    "companyName": "Casey Jensen",
                    "createdDateTime": "2023-08-16T00:00:00Z",
                    "displayName": "Casey Jensen",
                    "givenName": "Casey",
                    "id": "00aa00aa-bb11-cc22-dd33-44ee44ee44ee",
                    "mail": "casey@contoso.com",
                    "onPremisesSamAccountName": "Casey Jensen",
                    "onPremisesSecurityIdentifier": "<Enter Security Identifier>",
                    "onPremisesUserPrincipalName": "Casey Jensen",
                    "preferredLanguage": "en-us",
                    "surname": "Jensen",
                    "userPrincipalName": "casey@contoso.com",
                    "userType": "Member"
                }
            }
        }
    }
    
    
  4. Välj Skicka och du bör få ett JSON-svar som liknar följande:

    {
        "data": {
            "@odata.type": "microsoft.graph.onTokenIssuanceStartResponseData",
            "actions": [
                {
                    "@odata.type": "microsoft.graph.tokenIssuanceStart.provideClaimsForToken",
                    "claims": {
                        "customClaim1": "customClaimValue1",
                        "customClaim2": [
                            "customClaimString1",
                            "customClaimString2" 
                        ]
                    }
                }
    
            ]
        }
    }
    

Distribuera funktionen och publicera till Azure

Funktionen måste distribueras till Azure med vår IDE. Kontrollera att du är korrekt inloggad på ditt Azure-konto så att funktionen kan publiceras.

  1. Högerklicka på projektet i Solution Explorer och välj Publicera.

  2. I Mål väljer du Azure och sedan Nästa.

  3. Välj Azure Function App (Windows) för Det specifika målet, välj Azure Function App (Windows) och välj sedan Nästa.

  4. I funktionsinstansen använder du listrutan Prenumerationsnamn för att välja den prenumeration under vilken den nya funktionsappen ska skapas.

  5. Välj var du vill publicera den nya funktionsappen och välj Skapa ny.

  6. På sidan Funktionsapp (Windows) använder du inställningarna för funktionsappen som anges i följande tabell och väljer sedan Skapa.

    Inställning Föreslaget värde Description
    Namn Globalt unikt namn Ett namn som identifierar den nya funktionsappen. Giltiga tecken är a-z (skiftlägesokänsligt), 0-9 och -.
    Abonnemang Din prenumeration Prenumerationen under vilken den nya funktionsappen skapas.
    Resursgrupp myResourceGroup Välj en befintlig resursgrupp eller ge den nya namnet där du skapar funktionsappen.
    Plantyp Förbrukning (serverlös) Värdplan som definierar hur resurser allokeras till din funktionsapp.
    Plats Önskad region Välj en region som är nära dig eller nära andra tjänster som dina funktioner kan komma åt.
    Azure Storage Ditt lagringskonto Azure Functions-körmiljön kräver ett Azure Storage-konto. Välj Ny för att konfigurera ett allmänt lagringskonto.
    Application Insights Standardvärde En funktion i Azure Monitor. Detta är automatiskt markerat, välj den som du vill använda eller konfigurera en ny.
  7. Vänta en stund tills funktionsappen har distribuerats. När fönstret har stängts väljer du Slutför.

  8. Ett nytt publiceringsfönster öppnas. Längst upp väljer du Publicera. Vänta några minuter tills funktionsappen har distribuerats och visas i Azure-portalen.

Konfigurera autentisering för din Azure-funktion

Det finns tre sätt att konfigurera autentisering för din Azure-funktion:

Som standard har koden konfigurerats för autentisering i Azure-portalen med hjälp av miljövariabler. Använd flikarna nedan för att välja önskad metod för att implementera miljövariabler, eller också kan du läsa den inbyggda Azure App Service-autentiseringen och auktoriseringen. Använd följande värden för att konfigurera miljövariabler:

Name Värde
AuthenticationEvents__AudienceAppId App-ID för anpassat autentiseringstillägg som har konfigurerats i Konfigurera en anpassad anspråksprovider för en tokenutfärdarhändelse
AuthenticationEvents__AuthorityUrl • Personalklientorganisation https://login.microsoftonline.com/<tenantID>
• Extern klientorganisation https://<mydomain>.ciamlogin.com
AuthenticationEvents__AuthorizedPartyAppId 99045fe1-7639-4a75-9d4a-577b6ca3810f eller någon annan behörig part

Konfigurera autentisering i Azure-portalen med hjälp av miljövariabler

  1. Logga in på Azure-portalen som minst programadministratöreller autentiseringsadministratör.
  2. Gå till funktionsappen som du skapade och under Inställningar väljer du Konfiguration.
  3. Under Programinställningar väljer du Ny programinställning och lägger till miljövariablerna från tabellen och deras associerade värden.
  4. Välj Spara för att spara programinställningarna.

Gå vidare