Anropa Azure Function/REST API-kontroller
Med Invoke Azure Function/REST API Checks (Anropa Azure-funktion/REST API-kontroller) kan du skriva kod för att avgöra om en specifik pipelinefas tillåts komma åt en skyddad resurs eller inte. Dessa kontroller kan köras i två lägen:
- Asynkront (rekommenderas): push-läge, där Azure DevOps väntar på azure-funktionen/REST API-implementeringen för att anropa tillbaka till Azure DevOps med ett beslut om fasåtkomst
- Synkront: avsökningsläge, där Azure DevOps regelbundet anropar Azure Function/REST API för att få ett beslut om fasåtkomst
I resten av den här guiden refererar vi till Azure Function/REST API Checks helt enkelt som kontroller.
Det rekommenderade sättet att använda kontroller är i asynkront läge. Det här läget ger dig den högsta nivån av kontroll över kontrolllogik, gör det enkelt att resonera om vilket tillstånd systemet befinner sig i och frikoppla Azure Pipelines från implementeringen av dina kontroller, vilket ger bästa skalbarhet. Alla synkrona kontroller kan implementeras med hjälp av det asynkrona kontrollläget.
Asynkrona kontroller
I asynkront läge gör Azure DevOps ett anrop till azure-funktionen/REST API-kontrollen och väntar på ett återanrop med beslutet om resursåtkomst. Det finns ingen öppen HTTP-anslutning mellan Azure DevOps och din kontrollimplementering under väntetiden.
Resten av det här avsnittet handlar om Azure-funktionskontroller, men om inget annat anges gäller vägledningen även för att anropa REST API-kontroller.
Rekommenderad implementering av asynkrona kontroller
Det rekommenderade asynkrona läget har två kommunikationssteg:
- Leverera checknyttolasten. Azure Pipelines gör ett HTTP-anrop till din Azure-funktion/REST API endast för att leverera checknyttolasten och inte för att ta emot ett beslut på plats. Funktionen bör bara bekräfta mottagandet av informationen och avsluta HTTP-anslutningen med Azure DevOps. Din kontrollimplementering bör bearbeta HTTP-begäran inom 3 sekunder.
- Leverera åtkomstbeslut via ett återanrop. Kontrollen bör köras asynkront, utvärdera det villkor som krävs för att pipelinen ska få åtkomst till den skyddade resursen (eventuellt göra flera utvärderingar vid olika tidpunkter). När den har fattat ett slutgiltigt beslut gör din Azure-funktion ett HTTP REST-anrop till Azure DevOps för att meddela beslutet. När som helst bör det finnas en enda öppen HTTP-anslutning mellan Azure DevOps och din kontrollimplementering. På så sätt sparas resurser både på Azure-funktionssidan och på Azure Pipelines sida.
Om en kontroll godkänns tillåts pipelinen åtkomst till en skyddad resurs och fasdistributionen kan fortsätta. Om en kontroll misslyckas misslyckas fasen. Om det finns flera kontroller i en enda fas måste alla passera innan åtkomst till skyddade resurser tillåts, men ett enda fel räcker för att misslyckas i fasen.
Den rekommenderade implementeringen av asynkront läge för en enskild Azure-funktionskontroll visas i följande diagram.
Stegen i diagrammet är:
- Kontrollera leveransen. Azure Pipelines förbereder distributionen av en pipelinefas och kräver åtkomst till en skyddad resurs. Den anropar motsvarande Azure-funktionskontroll och förväntar sig kvittobekräftelse, genom att anropet slutar med en HTTP 200-statuskod. Fasdistributionen pausas i väntan på ett beslut.
- Kontrollera utvärdering. Det här steget sker i din Azure-funktionsimplementering, som körs på dina egna Azure-resurser och vars kod är helt under din kontroll. Vi rekommenderar att din Azure-funktion följer dessa steg:
- 2.1 Starta en asynkron uppgift och returnera HTTP-statuskod
200
- 2.2 Ange en inre loop där den kan utföra flera villkorsutvärderingar
- 2.3 Utvärdera åtkomstvillkoren
- 2.4 Om det inte kan nå ett slutgiltigt beslut, schemalägg om en omvärdering av villkoren för en senare punkt och gå sedan till steg 2.3
- 2.1 Starta en asynkron uppgift och returnera HTTP-statuskod
- Beslutskommunikation. Azure-funktionen anropar tillbaka till Azure Pipelines med åtkomstbeslutet. Fasdistributionen kan fortsätta
När du använder den rekommenderade implementeringen visar informationssidan för pipelinekörning den senaste kontrollloggen.
Rekommenderad konfiguration för asynkrona kontroller
Kontrollera konfigurationspanelen i Azure Function/REST API:
- Valt återanrop för slutförandehändelsen
- Ange Tid mellan utvärderingar (minuter) till 0
Om du anger tid mellan utvärderingar till ett värde som inte är noll innebär det att kontrollbeslutet (pass/fail) inte är slutgiltigt. Kontrollen omvärderas tills alla andra Godkännanden & checkar når ett slutligt tillstånd.
Skicka information om pipelinekörning till kontroller
När du konfigurerar kontrollen kan du ange den pipelinekörningsinformation som du vill skicka till din kontroll. Du bör minst skicka:
"PlanUrl": "$(system.CollectionUri)"
"ProjectId": "$(system.TeamProjectId)"
"HubName": "$(system.HostType)"
"PlanId": "$(system.PlanId)"
"JobId": "$(system.JobId)"
"TaskInstanceId": "$(system.TaskInstanceId)"
"AuthToken": "$(system.AccessToken)"
Dessa nyckel/värde-par anges som standard i REST-anropet Headers
som görs av Azure Pipelines.
Du bör använda AuthToken
för att göra anrop till Azure DevOps, till exempel när din check anropar tillbaka med ett beslut.
Samtal till Azure DevOps
För att nå ett beslut kan kontrollen behöva information om den aktuella pipelinekörningen som inte kan skickas till kontrollen, så kontrollen måste hämta den. Tänk dig att kontrollen verifierar att en pipelinekörning körde en viss uppgift, till exempel en statisk analysuppgift. Din kontroll måste anropa Azure DevOps och hämta listan över redan utförda uppgifter.
Om du vill anropa Azure DevOps rekommenderar vi att du använder jobbåtkomsttoken som utfärdats för kontrollkörningen i stället för en personlig åtkomsttoken (PAT).. Token har redan angetts för dina kontroller som standard i AuthToken
rubriken.
Jämfört med PAT är jobbåtkomsttoken mindre benägen att begränsas, behöver inte manuell uppdatering och är inte kopplad till ett personligt konto. Token är giltig i 48 timmar.
Med hjälp av jobbåtkomsttoken tar du bort problem med begränsning av REST API för Azure DevOps. När du använder en PAT använder du samma PAT för alla körningar av din pipeline. Om du kör ett stort antal pipelines begränsas PAT. Det här är mindre av ett problem med jobbåtkomsttoken eftersom en ny token genereras för varje kontrollkörning.
Token utfärdas för den byggidentitet som används för att köra en pipeline, till exempel FabrikamFiberChat-byggtjänsten (FabrikamFiber). Med andra ord kan token användas för att komma åt samma lagringsplatser eller pipelinekörningar som värdpipelinen kan. Om du har aktiverat Skydda åtkomst till lagringsplatser i YAML-pipelines begränsas dess omfång ytterligare till endast de lagringsplatser som refereras i pipelinekörningen.
Om kontrollen behöver komma åt icke-Pipelines-relaterade resurser, till exempel Boards user stories, bör du ge sådana behörigheter till pipelines byggidentiteter. Om kontrollen kan utlösas från flera projekt kontrollerar du att alla pipelines i alla projekt har åtkomst till de resurser som krävs.
Skicka tillbaka ett beslut till Azure DevOps
Din kontrollimplementering måste använda REST API-anropet efter händelsen för att meddela ett beslut tillbaka till Azure Pipelines. Kontrollera att du anger följande egenskaper:
Headers
:Basic: {AuthToken}
Body
:
{
"name": "TaskCompleted",
"taskId": "{TaskInstanceId}",
"jobId": "{JobId}",
"result": "succeeded|failed"
}
Skicka statusuppdateringar till Azure DevOps från kontroller
Du kan tillhandahålla statusuppdateringar till Azure Pipelines-användare från dina kontroller med hjälp av REST-API:er för Azure Pipelines. Den här funktionen är till exempel användbar om du vill meddela användarna att kontrollen väntar på en extern åtgärd, till exempel om någon behöver godkänna en ServiceNow-biljett.
Stegen för att skicka statusuppdateringar är:
Alla REST API-anrop måste autentiseras.
Exempel
Grundläggande Azure-funktionskontroll
I det här grundläggande exemplet kontrollerar Azure-funktionen att den anropande pipelinekörningen körde en CmdLine
uppgift innan den beviljades åtkomst till en skyddad resurs.
Azure-funktionen går igenom följande steg:
- Bekräftar mottagandet av checknyttolasten
- Skickar en statusuppdatering till Azure Pipelines som kontrollen startade
- Använder
{AuthToken}
för att göra ett återanrop till Azure Pipelines för att hämta pipelinekörningens tidslinjepost - Kontrollerar om tidslinjen innehåller en uppgift med
"id": "D9BAFED4-0B18-4F58-968D-86655B4D2CE9"
(aktivitetensCmdLine
ID) - Skickar en statusuppdatering med resultatet av sökningen
- Skickar ett kontrollbeslut till Azure Pipelines
Du kan ladda ned det här exemplet från GitHub.
Om du vill använda den här Azure-funktionskontrollen måste du ange följande Headers
när du konfigurerar kontrollen:
{
"Content-Type":"application/json",
"PlanUrl": "$(system.CollectionUri)",
"ProjectId": "$(system.TeamProjectId)",
"HubName": "$(system.HostType)",
"PlanId": "$(system.PlanId)",
"JobId": "$(system.JobId)",
"TimelineId": "$(system.TimelineId)",
"TaskInstanceId": "$(system.TaskInstanceId)",
"AuthToken": "$(system.AccessToken)",
"BuildId": "$(build.BuildId)"
}
Avancerad Azure-funktionskontroll
I det här avancerade exemplet kontrollerar Azure-funktionen att arbetsobjektet i Azure Boards som refereras i incheckningsmeddelandet som utlöste pipelinekörningen är i rätt tillstånd.
Azure-funktionen går igenom följande steg:
- Bekräftar mottagandet av checknyttolasten
- Skickar en statusuppdatering till Azure Pipelines som kontrollen startade
- Använder
{AuthToken}
för att göra ett återanrop till Azure Pipelines för att hämta tillståndet för azure boards-arbetsobjektet som refereras i incheckningsmeddelandet som utlöste pipelinekörningen - Kontrollerar om arbetsobjektet är i
Completed
tillståndet - Skickar en statusuppdatering med resultatet av kontrollen
- Om arbetsobjektet inte är i
Completed
tillståndet schemaläggs en annan utvärdering på 1 minut - När arbetsobjektet är i rätt tillstånd skickar det ett positivt beslut till Azure Pipelines
Du kan ladda ned det här exemplet från GitHub.
Om du vill använda den här Azure-funktionskontrollen måste du ange följande Headers
när du konfigurerar kontrollen:
{
"Content-Type":"application/json",
"PlanUrl": "$(system.CollectionUri)",
"ProjectId": "$(system.TeamProjectId)",
"HubName": "$(system.HostType)",
"PlanId": "$(system.PlanId)",
"JobId": "$(system.JobId)",
"TimelineId": "$(system.TimelineId)",
"TaskInstanceId": "$(system.TaskInstanceId)",
"AuthToken": "$(system.AccessToken)",
"BuildId": "$(build.BuildId)"
}
Felhantering
För närvarande utvärderar Azure Pipelines en enda kontrollinstans högst 2 000 gånger.
Om din check inte anropar tillbaka till Azure Pipelines inom den konfigurerade tidsgränsen hoppas den associerade fasen över. Steg beroende på den hoppas också över.
Synkrona kontroller
I synkront läge gör Azure DevOps ett anrop till Azure Function/REST API-kontrollen för att få ett omedelbart beslut om åtkomst till en skyddad resurs är tillåten eller inte.
Implementeringen av synkroniseringsläget för en enda Azure-funktionskontroll visas i följande diagram.
Stegen är:
- Azure Pipelines förbereder distributionen av en pipelinefas och kräver åtkomst till en skyddad resurs
- Den anger en inre loop där:
- 2.1. Azure Pipelines anropar motsvarande Azure-funktionskontroll och väntar på ett beslut
- 2.2. Din Azure-funktion utvärderar de villkor som krävs för att tillåta åtkomst och returnerar ett beslut
- 2.3. Om Svarstexten för Azure-funktionen inte uppfyller de framgångsvillkor som du definierade och Tiden mellan utvärderingarna inte är noll, schemaläggs en ny kontrollutvärdering i Azure Pipelines efter tid mellan utvärderingarna
Konfigurera synkrona kontroller
Om du vill använda synkront läge för Azure Function/REST-API:et kontrollerar du följande i kontrollkonfigurationspanelen:
- Valt ApiResponse för slutförandehändelsen under Avancerat
- Angav villkoren för lyckad åtgärd som definierar när kontrollen ska godkännas baserat på kontrollens svarstext
- Ange Tid mellan utvärderingar till 0 under Kontrollalternativ
- Ange Timeout till hur länge du vill vänta på att en kontroll ska lyckas. Om det inte finns något positivt beslut och tidsgränsen nås hoppas motsvarande pipelinefas över
Inställningen Tid mellan utvärderingar definierar hur länge kontrollens beslut är giltigt. Värdet 0 innebär att beslutet är slutgiltigt. Ett värde som inte är noll innebär att kontrollen görs igen efter det konfigurerade intervallet, när dess beslut är negativt. När flera Godkännanden och kontroller körs görs kontrollen på nytt oavsett beslut.
Det maximala antalet utvärderingar definieras av förhållandet mellan timeout och tid mellan utvärderingsvärden. Vi rekommenderar att du ser till att det här förhållandet är högst 10.
Skicka information om pipelinekörning till kontroller
När du konfigurerar kontrollen kan du ange den pipelinekörningsinformation som du vill skicka till din Azure-funktion/REST API-kontroll. Som standard lägger Azure Pipeline till följande information i Headers
http-anropet den gör.
"PlanUrl": "$(system.CollectionUri)"
"ProjectId": "$(system.TeamProjectId)"
"HubName": "$(system.HostType)"
"PlanId": "$(system.PlanId)"
"JobId": "$(system.JobId)"
"TaskInstanceId": "$(system.TaskInstanceId)"
"AuthToken": "$(system.AccessToken)"
Vi rekommenderar inte att du gör anrop till Azure DevOps i synkront läge, eftersom det sannolikt kommer att leda till att kontrollen tar mer än 3 sekunder att svara, så kontrollen misslyckas.
Felhantering
För närvarande utvärderar Azure Pipelines en enda kontrollinstans högst 2 000 gånger.
När du ska använda asynkrona eller synkrona kontroller
Nu ska vi titta på några exempel på användningsfall och vilken typ av kontroller som rekommenderas.
Extern information måste vara korrekt
Anta att du har en tjänst Anslut till en produktionsresurs och vill se till att åtkomst till den endast tillåts om informationen i en ServiceNow-biljett är korrekt. I det här fallet skulle flödet vara följande:
- Du lägger till en asynkron Azure-funktionskontroll som verifierar att ServiceNow-biljetten är korrekt
- När en pipeline som vill använda tjänsten Anslut ion körs:
- Azure Pipelines anropar din kontrollfunktion
- Om informationen är felaktig returnerar kontrollen ett negativt beslut. Anta det här resultatet
- Pipelinesteget misslyckas
- Du uppdaterar informationen i ServiceNow-biljetten
- Du startar om den misslyckade fasen
- Kontrollen körs igen och den här gången lyckas den
- Pipelinekörningen fortsätter
Externt godkännande måste beviljas
Anta att du har en tjänst Anslut ion till en produktionsresurs och vill se till att åtkomsten till den endast tillåts efter att en administratör godkänt en ServiceNow-biljett. I det här fallet skulle flödet vara följande:
- Du lägger till en asynkron Azure-funktionskontroll som verifierar att ServiceNow-biljetten har godkänts
- När en pipeline som vill använda tjänsten Anslut ion körs:
- Azure Pipelines anropar din kontrollfunktion.
- Om ServiceNow-biljetten inte godkänns skickar Azure-funktionen en uppdatering till Azure Pipelines och schemaläggs om för att kontrollera tillståndet för biljetten på 15 minuter
- När biljetten har godkänts anropar kontrollen tillbaka till Azure Pipelines med ett positivt beslut
- Pipelinekörningen fortsätter
Utvecklingsprocessen följdes
Anta att du har en tjänst Anslut ion till en produktionsresurs och vill se till att åtkomsten till den endast tillåts om kodtäckningen är över 80 %. I det här fallet skulle flödet vara följande:
- Du skriver din pipeline på ett sådant sätt att fasfel gör att bygget misslyckas
- Du lägger till en asynkron Azure-funktionskontroll som verifierar kodtäckningen för den associerade pipelinekörningen
- När en pipeline som vill använda tjänsten Anslut ion körs:
- Azure Pipelines anropar din kontrollfunktion
- Om kodtäckningsvillkoret inte uppfylls returnerar kontrollen ett negativt beslut. Anta det här resultatet
- Kontrollfelet gör att fasen misslyckas, vilket gör att pipelinekörningen misslyckas
- Teknikteamet lägger till nödvändiga enhetstester för att nå 80 % kodtäckning
- En ny pipelinekörning utlöses och den här gången godkänns kontrollen
- Pipelinekörningen fortsätter
Prestandakriterierna måste uppfyllas
Anta att du distribuerar nya versioner av systemet i flera steg, med början i en kanariedistribution. Du vill se till att prestandan för din kanariedistribution är tillräcklig. I det här fallet skulle flödet vara följande:
- Du lägger till en asynkron Azure-funktionskontroll
- När en pipeline som vill använda tjänsten Anslut ion körs:
- Azure Pipelines anropar din kontrollfunktion
- Kontrollen startar en övervakare av canary-distributionens prestanda
- Kontrollen schemalägger flera kontrollpunkter för utvärdering för att se hur prestandan utvecklades
- När du har fått tillräckligt förtroende för canary-distributionens prestanda anropar Din Azure-funktion tillbaka till Azure Pipelines med ett positivt beslut
- Pipelinekörningen fortsätter
Distributionsorsaken måste vara giltig
Anta att du har en tjänst Anslut ion till en resurs för produktionsmiljön och vill se till att åtkomsten till den endast sker för manuellt köade versioner. I det här fallet skulle flödet vara följande:
- Du lägger till en synkron Azure-funktionskontroll som verifierar att
Build.Reason
för pipelinekörningen ärManual
- Du konfigurerar Azure-funktionskontrollen för att skicka
Build.Reason
in dessHeaders
- Du anger kontrollens Tid mellan utvärderingar till 0, så fel eller pass är slutgiltigt och ingen omvärdering krävs
- När en pipeline som vill använda tjänsten Anslut ion körs:
- Azure Pipelines anropar din kontrollfunktion
- Om orsaken är annan än
Manual
misslyckas kontrollen och pipelinekörningen misslyckas
Kontrollera efterlevnad
Anropa Azure Function- och REST API-kontroller innehåller nu regler som matchar rekommenderad användning. Kontrollerna måste följa dessa regler beroende på läget och antalet återförsök:
Asynkrona kontroller (återanropsläge): Azure Pipelines försöker inte utföra asynkrona kontroller igen. Du bör ange ett resultat asynkront när en utvärdering är slutgiltig. För att asynkrona kontroller ska anses vara kompatibla måste tidsintervallet mellan utvärderingarna vara 0.
Synkrona kontroller (ApiResponse-läge): Det maximala antalet återförsök för kontrollen är 10. Du kan ange på flera olika sätt. Du kan till exempel konfigurera tidsgränsen till 20 och tidsintervallet mellan utvärderingarna till 2. Eller så kan du konfigurera tidsgränsen till 100 och tidsintervallet mellan utvärderingarna till 10. Men om du konfigurerar tidsgränsen till 100 och anger tidsintervallet mellan utvärderingarna till 2, är kontrollen inte kompatibel eftersom du begär 50 återförsök. Förhållandet mellan timeout och tidsintervall mellan utvärderingar bör vara mindre än eller lika med 10.
Flera kontroller
Innan Azure Pipelines distribuerar en fas i en pipelinekörning kan flera kontroller behöva skickas. En skyddad resurs kan ha en eller flera kontroller kopplade till sig. En fas kan använda flera skyddade resurser. Azure Pipelines samlar in alla kontroller som är associerade med varje skyddad resurs som används i en fas och utvärderar dem samtidigt.
En pipelinekörning kan endast distribueras till en fas när alla kontroller skickas samtidigt. Ett enda slutligt negativt beslut gör att pipelinen nekas åtkomst och att fasen misslyckas.
När du använder kontroller på det rekommenderade sättet (asynkront, med slutgiltiga tillstånd) blir deras åtkomstbeslut slutgiltiga och underlättar förståelsen av systemets tillstånd.
Se avsnittet Flera Godkännanden och kontroller för exempel.