Det går inte att hämta avbildningar från Azure Container Registry till Azure Kubernetes Service kluster

Obs!

Var den här artikeln användbar? Dina indata är viktiga för oss. Använd knappen Feedback på den här sidan för att berätta hur bra den här artikeln fungerade för dig eller hur vi kan förbättra den.

När du använder Microsoft Azure Container Registry tillsammans med Azure Kubernetes Service (AKS) måste en autentiseringsmekanism upprättas. Du kan konfigurera AKS till Container Registry-integrering med hjälp av några enkla Azure CLI- eller Azure PowerShell-kommandon. Den här integreringen tilldelar AcrPull-rollen för kubelet-identiteten som är associerad med AKS-klustret för att hämta avbildningar från ett containerregister.

I vissa fall misslyckas försök att hämta avbildningar från ett containerregister till ett AKS-kluster. Den här artikeln innehåller vägledning för felsökning av de vanligaste felen som uppstår när du hämtar avbildningar från ett containerregister till ett AKS-kluster.

Innan du börjar

Den här artikeln förutsätter att du har ett befintligt AKS-kluster och ett befintligt containerregister. Se följande snabbstarter:

Du behöver också att Azure CLI version 2.0.59 eller en senare version installeras och konfigureras. Kör az version för att fastställa versionen. Om du måste installera eller uppgradera kan du läsa Installera Azure CLI.

Symptom och inledande felsökning

Kubernetes-poddens STATUS är ImagePullBackOff eller ErrImagePull. Om du vill få detaljerad felinformation kör du följande kommando och kontrollerar Händelser från utdata.

kubectl describe pod <podname> -n <namespace>

Vi rekommenderar att du börjar felsöka genom att kontrollera containerregistrets hälsa och kontrollera om containerregistret är tillgängligt från AKS-klustret.

Kontrollera containerregistrets hälsotillstånd genom att köra följande kommando:

az acr check-health --name <myregistry> --ignore-errors --yes

Om ett problem identifieras innehåller det en felkod och beskrivning. Mer information om fel och möjliga lösningar finns i Referens för hälsokontrollfel.

Obs!

Om du får Helm-relaterade eller notarierelaterade fel betyder det inte att du har ett problem som påverkar Container Registry eller AKS. Det anger bara att Helm eller Notary inte är installerat eller att Azure CLI inte är kompatibelt med den aktuella installerade versionen av Helm eller Notary och så vidare.

Kontrollera om containerregistret är tillgängligt från AKS-klustret genom att köra följande az aks check-acr-kommando :

az aks check-acr --resource-group <MyResourceGroup> --name <MyManagedCluster> --acr <myacr>.azurecr.io

Följande avsnitt hjälper dig att felsöka de vanligaste felen som visas i Händelser i kommandots kubectl describe pod utdata.

Orsak 1: 401 Obehörigt fel

Ett AKS-kluster kräver en identitet. Den här identiteten kan vara antingen en hanterad identitet eller ett huvudnamn för tjänsten. Om AKS-klustret använder en hanterad identitet används kubelet-identiteten för autentisering med ACR. Om AKS-klustret använder som en identitet som huvudnamn för tjänsten används själva tjänstens huvudnamn för autentisering med ACR. Oavsett vad identiteten är krävs rätt auktorisering som används för att hämta en avbildning från ett containerregister. Annars kan du få följande "401 Unauthorized"-fel:

Det gick inte att hämta avbildningen "<acrname.azurecr.io/<> repository:tag>": [rpc error: code = Unknown desc = failed to pull and unpack image "<acrname.azurecr.io/>< repository:tag>": det gick inte att matcha referensen "<acrname.azurecr.io/<> repository:tag>": det gick inte att auktorisera: det gick inte att hämta oauth-token: oväntad status: 401 Obehörig obehörig

Flera lösningar kan hjälpa dig att lösa det här felet, med följande begränsningar:

Lösning 1: Kontrollera att AcrPull-rolltilldelning har skapats för identitet

Integreringen mellan AKS och Container Registry skapar en AcrPull-rolltilldelning på containerregisternivå för AKS-klustrets kubelet-identitet. Kontrollera att rolltilldelningen har skapats.

Om du vill kontrollera om AcrPull-rolltilldelningen har skapats använder du någon av följande metoder:

  • Kör följande kommando:

    az role assignment list --scope /subscriptions/<subscriptionID>/resourceGroups/<resourcegroupname>/providers/Microsoft.ContainerRegistry/registries/<acrname> -o table
    
  • Checka in Azure Portal genom att välja Azure Container Registry>Access-kontroll (IAM)>Rolltilldelningar. Mer information finns i Lista Azure-rolltilldelningar med hjälp av Azure Portal.

Förutom AcrPull-rollen kan vissa inbyggda roller och anpassade roller också innehålla åtgärden "Microsoft.ContainerRegistry/registries/pull/read". Kontrollera dessa roller om du har någon av dem.

Om rolltilldelningen AcrPull inte skapas skapar du den genom att konfigurera Container Registry-integrering för AKS-klustret med följande kommando:

az aks update -n <myAKSCluster> -g <myResourceGroup> --attach-acr <acr-resource-id>

Lösning 2: Kontrollera att tjänstens huvudnamn inte har upphört att gälla

Kontrollera att hemligheten för tjänstens huvudnamn som är associerad med AKS-klustret inte har upphört att gälla. Kontrollera förfallodatumet för tjänstens huvudnamn genom att köra följande kommandon:

SP_ID=$(az aks show --resource-group <myResourceGroup> --name <myAKSCluster> \
    --query servicePrincipalProfile.clientId -o tsv)

az ad sp credential list --id "$SP_ID" --query "[].endDate" -o tsv

Mer information finns i Kontrollera förfallodatumet för tjänstens huvudnamn.

Om hemligheten har upphört att gälla uppdaterar du autentiseringsuppgifterna för AKS-klustret.

Lösning 3: Kontrollera att AcrPull-rollen har tilldelats rätt huvudnamn för tjänsten

I vissa fall refererar rolltilldelningen för containerregistret fortfarande till det gamla tjänstens huvudnamn. Till exempel när tjänstens huvudnamn för AKS-klustret ersätts med ett nytt. Följ dessa steg för att se till att rolltilldelningen för containerregistret refererar till rätt huvudnamn för tjänsten:

  1. Kör följande kommando för att kontrollera tjänstens huvudnamn som används av AKS-klustret:

    az aks show --resource-group <myResourceGroup> \
        --name <myAKSCluster> \
        --query servicePrincipalProfile.clientId \
        --output tsv
    
  2. Kör följande kommando för att kontrollera tjänstens huvudnamn som refereras av rolltilldelningen för containerregistret:

    az role assignment list --scope /subscriptions/<subscriptionID>/resourceGroups/<resourcegroupname>/providers/Microsoft.ContainerRegistry/registries/<acrname> -o table
    
  3. Jämför de två huvudnamnen för tjänsten. Om de inte matchar integrerar du AKS-klustret med containerregistret igen.

Lösning 4: Kontrollera att kubelet-identiteten refereras till i AKS VMSS

När en hanterad identitet används för autentisering med ACR kallas den hanterade identiteten kubelet-identiteten. Som standard tilldelas kubelet-identiteten på AKS VMSS-nivå. Om kubelet-identiteten tas bort från AKS VMSS kan AKS-noderna inte hämta avbildningar från ACR.

Kör följande kommando för att hitta kubelet-identiteten för ditt AKS-kluster:

az aks show --resource-group <MyResourceGroup> --name <MyManagedCluster> --query identityProfile.kubeletidentity

Sedan kan du lista identiteterna för AKS VMSS genom att öppna VMSS från nodresursgruppen och välja Identitetsanvändare>tilldelad i Azure Portal eller genom att köra följande kommando:

az vmss identity show --resource-group <NodeResourceGroup> --name <AksVmssName>

Om kubelet-identiteten för ditt AKS-kluster inte har tilldelats AKS VMSS tilldelar du tillbaka den.

Obs!

Det går inte att ändra AKS VMSS med hjälp av IaaS-API:erna eller från Azure Portal, och ingen AKS-åtgärd kan ta bort kubelet-identiteten från AKS VMSS. Det innebär att något oväntat tog bort det, till exempel en manuell borttagning som utförs av en gruppmedlem. Om du vill förhindra sådan borttagning eller ändring kan du överväga att använda NRGLockdown-funktionen.

Eftersom ändringar av AKS VMSS inte stöds sprids de inte på AKS-nivå. För att tilldela om kubelet-identiteten till AKS VMSS krävs en avstämningsåtgärd. Det gör du genom att köra följande kommando:

az aks update --resource-group <MyResourceGroup> --name <MyManagedCluster>

Lösning 5: Kontrollera att tjänstens huvudnamn är korrekt och att hemligheten är giltig

Om du hämtar en avbildning med hjälp av en avbildningshämtningshemlighet och kubernetes-hemligheten har skapats med hjälp av värdena för ett huvudnamn för tjänsten kontrollerar du att det associerade tjänstens huvudnamn är korrekt och att hemligheten fortfarande är giltig. Gör så här:

  1. Kör följande kubectl get - och base64-kommando för att se värdena för Kubernetes-hemligheten:

    kubectl get secret <secret-name> --output="jsonpath={.data.\.dockerconfigjson}" | base64 --decode
    
  2. Kontrollera förfallodatumet genom att köra följande kommando az ad sp credential list . Användarnamnet är tjänstens huvudnamn.

    az ad sp credential list --id "<username>" --query "[].endDate" --output tsv
    
  3. Om det behövs återställer du hemligheten för tjänstens huvudnamn genom att köra följande az ad sp-återställningskommando för autentiseringsuppgifter :

    az ad sp credential reset --name "$SP_ID" --query password --output tsv
    
  4. Uppdatera eller återskapa Kubernetes-hemligheten i enlighet med detta.

Lösning 6: Kontrollera att Kubernetes-hemligheten har rätt värden för administratörskontot för containerregistret

Om du hämtar en avbildning med hjälp av en avbildningshämtningshemlighet och kubernetes-hemligheten skapades med hjälp av värden för administratörskontot för containerregistret kontrollerar du att värdena i Kubernetes-hemligheten är desamma som värdena för administratörskontot för containerregistret. Gör så här:

  1. Kör följande kubectl get - och base64-kommando för att se värdena för Kubernetes-hemligheten:

    kubectl get secret <secret-name> --output="jsonpath={.data.\.dockerconfigjson}" | base64 --decode
    
  2. I Azure Portal söker du efter och väljer Containerregister.

  3. I listan över containerregister väljer du ditt containerregister.

  4. I navigeringsfönstret för containerregistret väljer du Åtkomstnycklar.

  5. På sidan Åtkomstnycklar för containerregistret jämför du containerregistrets värden med värdena i Kubernetes-hemligheten.

  6. Om värdena inte matchar uppdaterar eller återskapar du Kubernetes-hemligheten i enlighet med detta.

Obs!

Om en åtgärd för att återskapa lösenord har inträffat visas en åtgärd med namnet "Återskapa inloggningsuppgifter för containerregistret" på sidan Aktivitetslogg i containerregistret. Aktivitetsloggen har en kvarhållningsperiod på 90 dagar.

Orsak 2: Det gick inte att hitta avbildningen

Det gick inte att hämta avbildningen "<acrname.azurecr.io/<> repository:tag>": [rpc error: code = NotFound desc = failed to pull and unpack image "<acrname.azurecr.io/>< repository:tag>": det gick inte att matcha referensen "<acrname.azurecr.io/>< repository:tag>": <acrname.azurecr.io/>< repository:tag>: hittades inte

Lösning: Kontrollera att avbildningsnamnet är korrekt

Om du ser det här felet kontrollerar du att avbildningsnamnet är helt korrekt. Du bör kontrollera registernamnet, registerinloggningsservern, lagringsplatsens namn och taggen. Ett vanligt misstag är att inloggningsservern anges som "azureacr.io" i stället för "azurecr.io".

Om avbildningsnamnet inte är helt korrekt kan felet 401 Obehörig också inträffa eftersom AKS alltid försöker hämta anonymt oavsett om containerregistret har aktiverat anonym pull-åtkomst.

Orsak 3: 403 – Förbjudet fel

Det gick inte att hämta avbildningen "<acrname.azurecr.io/>< repository:tag>": rpc-fel: code = Unknown desc = failed to pull and unpack image "<acrname.azurecr.io/>< repository:tag>": det gick inte att matcha referensen "<acrname.azurecr.io/<> repository:tag>": det gick inte att auktorisera: det gick inte att hämta anonym token: oväntad status: 403 Förbjudet

Om nätverksgränssnittet för containerregistrets privata slutpunkt och AKS-klustret finns i olika virtuella nätverk kontrollerar du att den virtuella nätverkslänken för AKS-klustrets virtuella nätverk har angetts i Privat DNS zonen i containerregistret. (Länken heter "privatelink.azurecr.io" som standard.) Om länken för det virtuella nätverket inte finns i Privat DNS-zonen i containerregistret lägger du till den på något av följande sätt:

Lösning 2: Lägg till AKS-Load Balancer offentliga IP-adress till det tillåtna IP-adressintervallet för containerregistret

Om AKS-klustret ansluter offentligt till containerregistret (INTE via en privat länk eller en slutpunkt) och containerregistrets offentliga nätverksåtkomst är begränsad till valda nätverk lägger du till AKS-Load Balancer offentliga IP-adress till containerregistrets tillåtna IP-adressintervall:

  1. Kontrollera att åtkomsten till det offentliga nätverket är begränsad till valda nätverk.

    I Azure Portal navigerar du till containerregistret. Under Inställningar väljer du Nätverk. På fliken Offentlig åtkomst är offentlig nätverksåtkomst inställd på Valda nätverk eller Inaktiverad.

  2. Hämta AKS-Load Balancer offentliga IP-adress genom att använda något av följande sätt:

    • I Azure Portal navigerar du till AKS-klustret. Under Inställningar väljer du Egenskaper, väljer en av vm-skalningsuppsättningarna i infrastrukturresursgruppen och kontrollerar den offentliga IP-adressen för AKS-Load Balancer.

    • Kör följande kommando:

      az network public-ip show --resource-group <infrastructure-resource-group> --name <public-IP-name> --query ipAddress -o tsv
      
  3. Tillåt åtkomst från AKS-Load Balancer offentliga IP-adress genom att använda något av följande sätt:

    • Kör az acr network-rule add kommandot på följande sätt:

      az acr network-rule add --name acrname --ip-address <AKS-load-balancer-public-IP-address>
      

      Mer information finns i Lägga till nätverksregel i registret.

    • I Azure Portal navigerar du till containerregistret. Under Inställningar väljer du Nätverk. På fliken Offentlig åtkomst under Brandvägg lägger du till AKS-Load Balancer offentliga IP-adress i Adressintervall och väljer sedan Spara. Mer information finns i Åtkomst från det valda offentliga nätverket – portalen.

      Obs!

      Om Åtkomst till offentligt nätverk har angetts till Inaktiverad växlar du den först till Valda nätverk .

      Skärmbild om hur du lägger till AKS-Load Balancer offentliga IP-adress i adressintervallet

Orsak 4: 443-timeoutfel

Det gick inte att hämta avbildningen "<acrname.azurecr.io/<> repository:tag>": rpc error: code = Unknown desc = failed to pull and unpack image "<acrname.azurecr.io/<> repository:tag>": det gick inte att matcha referensen "<acrname.azurecr.io/>< repository:tag>": det gick inte att göra en begäran: Head "https://< acrname.azurecr.io/v2/<> repository>/manifests/v1": dial tcp <acrprivateipaddress>:443: i/o timeout

Obs!

Felet "443 timeout" inträffar bara när du ansluter privat till ett containerregister med hjälp av Azure Private Link.

Lösning 1: Kontrollera att peering för virtuella nätverk används

Om nätverksgränssnittet för containerregistrets privata slutpunkt och AKS-klustret finns i olika virtuella nätverk kontrollerar du att peering för virtuella nätverk används för båda de virtuella nätverken. Du kan kontrollera peering för virtuella nätverk genom att köra Azure CLI-kommandot az network vnet peering list --resource-group <MyResourceGroup> --vnet-name <MyVirtualNetwork> --output table eller i Azure Portal genom att välja VNETsPeerings> under panelen Inställningar. Mer information om att lista alla peerings för ett angivet virtuellt nätverk finns i az network vnet peering list.

Om peering för virtuella nätverk används för båda de virtuella nätverken kontrollerar du att statusen är "Ansluten". Om statusen är Frånkopplad tar du bort peer-kopplingen från båda de virtuella nätverken och skapar den sedan igen. Om statusen är "Ansluten" läser du felsökningsguiden: Peeringstatusen är "Ansluten".

För ytterligare felsökning ansluter du till en av AKS-noderna eller poddarna och testar sedan anslutningen till containerregistret på TCP-nivå med hjälp av telnet- eller Netcat-verktyget. Kontrollera IP-adressen med nslookup <acrname>.azurecr.io kommandot och kör telnet <ip-address-of-the-container-registry> 443 sedan kommandot .

Mer information om hur du ansluter till AKS-noder finns i Ansluta med SSH till Azure Kubernetes Service klusternoder (AKS) för underhåll eller felsökning.

Lösning 2: Använd Azure Firewall Service

Om nätverksgränssnittet för containerregistrets privata slutpunkt och AKS-klustret finns i olika virtuella nätverk kan du, förutom peering för virtuella nätverk, använda Azure Firewall Service för att konfigurera en nätverkstopologi av typen Hub-spoke i Azure. När du konfigurerar brandväggsregeln måste du använda nätverksregler för att uttryckligen tillåta den utgående anslutningen till ip-adresserna för containerregistrets privata slutpunkt.

Orsak 5: Ingen matchning för plattformen i manifestet

Värdoperativsystemet (nodoperativsystem) är inte kompatibelt med den avbildning som används för podden eller containern. Om du till exempel schemalägger en podd för att köra en Linux-container på en Windows-nod eller en Windows-container på en Linux-nod uppstår följande fel:

Det gick inte att hämta avbildningen "<acrname.azurecr.io/>< repository:tag>":
[
  rpc-fel:
  code = NotFound
  desc = det gick inte att hämta och packa upp avbildningen "<acrname.azurecr.io/>< repository:tag>": ingen matchning för plattformen i manifestet: hittades inte,
]

Det här felet kan inträffa för en avbildning som hämtas från valfri källa, så länge avbildningen inte är kompatibel med värdoperativsystemet. Felet är inte begränsat till avbildningar som hämtas från containerregistret.

Lösning: Konfigurera fältet nodeSelector korrekt i podden eller distributionen

Ange rätt nodeSelector fält i konfigurationsinställningarna för din podd eller distribution. Rätt värde för det här fältets inställning säkerställer att podden schemaläggs kubernetes.io/os på rätt typ av nod. Följande tabell visar hur du anger kubernetes.io/os inställningen i YAML:

Containertyp YAML-inställning
Linux-container "kubernetes.io/os": linux
Windows-container "kubernetes.io/os": windows

Följande YAML-kod beskriver till exempel en podd som måste schemaläggas på en Linux-nod:

apiVersion: v1
kind: Pod
metadata:
  name: aspnetapp
  labels:
    app: aspnetapp
spec:
  containers:
  - image: "mcr.microsoft.com/dotnet/core/samples:aspnetapp"
    name: aspnetapp-image
    ports:
    - containerPort: 80
      protocol: TCP
  nodeSelector:
    "kubernetes.io/os": linux

Mer information

Om felsökningsguiden i den här artikeln inte hjälper dig att lösa problemet kan du tänka på följande:

  • Kontrollera nätverkssäkerhetsgrupper och routningstabeller som är associerade med undernät, om du har något av dessa objekt.

  • Om en virtuell installation som en brandvägg styr trafiken mellan undernät kontrollerar du åtkomstreglerna för brandväggen och brandväggen.

Ansvarsfriskrivning för information från tredje part

De produkter från andra tillverkare som diskuteras i denna artikel tillverkas oberoende av Microsoft. Produkternas funktion eller tillförlitlighet kan därför inte garanteras.

Kontakta oss för att få hjälp

Om du har frågor eller behöver hjälp skapar du en supportförfrågan eller frågar Azure community support. Du kan också skicka produktfeedback till Azure-feedbackcommunityn.