Share via


Schnellstart: Erfüllen der Voraussetzungen für die Bereitstellung einer Containernetzwerkfunktion in Azure Operator Service Manager

In diesem Schnellstart erledigen Sie die Aufgaben, die zur Vorbereitung der Verwendung von Azure Operator Service Manager (AOSM) erforderlich sind.

Voraussetzungen

Wenden Sie sich an Ihr Microsoft-Kundenteam, um Ihr Azure-Abonnement für den Zugriff auf Azure Operator Service Manager (AOSM) zu registrieren, oder bekunden Sie Ihr Interesse über das Partnerregistrierungsformular.

Herunterladen und Installieren der Azure CLI

Verwenden Sie die Bash-Umgebung in Azure Cloud Shell. Weitere Informationen zur Verwendung der Bash-Umgebung in Azure Cloud Shell finden Sie unter Starten der Cloud Shell.

Benutzer*innen, die CLI-Verweisbefehle lieber lokal ausführen möchten, finden weitere Informationen unter Installieren der Azure CLI.

Wenn Sie unter Windows oder macOS arbeiten, sollten Sie die Azure CLI in einem Docker-Container ausführen. Weitere Informationen finden Sie unter Ausführen der Azure CLI in einem Docker-Container.

Wenn Sie eine lokale Installation verwenden, melden Sie sich mit dem Befehl az login bei der Azure CLI an, und befolgen Sie die in Ihrem Terminal angezeigten Eingabeaufforderungen, um die Authentifizierung abzuschließen. Weitere Anmeldeoptionen finden Sie unter Anmelden mit der Azure CLI.

Installieren der CLI-Erweiterung für Azure Operator Service Manager (AOSM)

Installieren Sie die CLI-Erweiterung für Azure Operator Service Manager (AOSM) mit diesem Befehl:

az extension add --name aosm
  1. Führen Sie az version aus, um die installierte Version und die abhängigen Bibliotheken anzuzeigen.
  2. Führen Sie az upgrade aus, um ein Upgrade auf die aktuelle Version der Azure CLI durchzuführen.

Registrieren und Überprüfen der erforderlichen Ressourcenanbieter

Bevor Sie mit der Verwendung von Azure Operator Service Manager beginnen, führen Sie die folgenden Befehle aus, um den erforderlichen Ressourcenanbieter zu registrieren. Dieser Registrierungsprozess kann bis zu 5 Minuten dauern.

# Register Resource Provider
az provider register --namespace Microsoft.HybridNetwork
az provider register --namespace Microsoft.ContainerRegistry

Überprüfen Sie den Registrierungsstatus der Ressourcenanbieter. Führen Sie die folgenden Befehle aus.

# Query the Resource Provider
az provider show -n Microsoft.HybridNetwork --query "{RegistrationState: registrationState, ProviderName: namespace}"
az provider show -n Microsoft.ContainerRegistry --query "{RegistrationState: registrationState, ProviderName: namespace}"

Hinweis

Es kann einige Minuten dauern, bis die Registrierung der Ressourcenanbieter abgeschlossen ist. Sobald die Registrierung erfolgreich ist, können Sie mit der Verwendung von Azure Operator Service Manager (AOSM) beginnen.

Anforderungen für containerisierte Netzwerkfunktionen (Containerized Network Function, CNF)

Für diejenigen, die containerisierte Netzwerkfunktionen verwenden, müssen Sie sicherstellen, dass die folgenden Pakete auf dem Computer installiert sind, auf dem Sie die CLI ausführen:

Konfigurieren der Bereitstellung von containerisierten Netzwerkfunktionen

Für Bereitstellungen von CNFs ist es wichtig, dass Folgendes auf dem Computer gespeichert ist, auf dem Sie die CLI ausführen:

  • Helm-Pakete mit Schema: Diese Pakete sollten in Ihrem lokalen Speicher vorhanden sein, und in der Konfigurationsdatei input.json muss auf diese verwiesen werden. Wenn Sie diesen Schnellstart befolgen, laden Sie das erforderliche Helm-Paket herunter.

  • Erstellen einer Beispielkonfigurationsdatei: Generieren Sie eine Beispielkonfigurationsdatei zum Definieren einer CNF-Bereitstellung. Führen Sie diesen Befehl aus, um eine input.json-Datei zu generieren, die Sie mit Ihrer spezifischen Konfiguration auffüllen müssen.

    az aosm nfd generate-config --definition-type cnf
    
  • Image für Ihre CNF: Es gibt diese Optionen:

    • Ein Verweis auf eine vorhandene Azure Container Registry-Instanz, die die Images für Ihre CNF enthält. Derzeit werden nur eine ACR-Instanz und ein Namespace pro CNF unterstützt. Die Images, die aus dieser ACR-Instanz kopiert werden sollen, werden automatisch basierend auf dem Helm-Paketschema aufgefüllt. Sie müssen über Lese- oder AcrPull-Berechtigungen für diese ACR-Instanz verfügen. Um diese Option zu verwenden, geben Sie source_registry und optional source_registry_namespace in der Datei „input.json“ an.
    • Der Imagename des Docker-Quellimages vom lokalen Computer. Dieser Imagename ist für einen eingeschränkten Anwendungsfall vorgesehen, in dem die CNF nur ein einzelnes Docker-Image erfordert, das im lokalen Docker-Repository vorhanden ist. Um diese Option zu verwenden, geben Sie source_local_docker_image in der Datei „input.json“ an. Docker muss installiert sein. Dieser Schnellstart führt Sie durch das Herunterladen eines NGINX-Docker-Images, das für diese Option verwendet werden soll.
  • Optional: Zuordnungsdatei (path_to_mappings): Optional können Sie eine Datei (auf dem Datenträger) mit dem Namen „path_to_mappings“ bereitstellen. Diese Datei sollte values.yaml spiegeln, wobei die ausgewählten Werte durch Bereitstellungsparameter ersetzt werden. Dadurch werden sie als Parameter für die CNF verfügbar gemacht. Sie können dies auch in input.json leer lassen. Dann generiert die CLI die Datei. In diesem Fall wird standardmäßig jeder Wert in values.yaml als Bereitstellungsparameter verfügbar gemacht. Alternativ können Sie das CLI-Argument --interactive verwenden, um interaktiv Entscheidungen zu treffen. Dieser Schnellstart führt Sie durch die Erstellung dieser Datei.

Stellen Sie beim Konfigurieren der Datei input.json sicher, dass Sie die Helm-Pakete in der Reihenfolge auflisten, in der sie bereitgestellt werden sollen. Wenn beispielsweise das Paket „A“ vor dem Paket „B“ bereitgestellt werden muss, sollte input.json die folgende Struktur aufweisen:

"helm_packages": [
    {
        "name": "A",
        "path_to_chart": "Path to package A",
        "path_to_mappings": "Path to package A mappings",
        "depends_on": [
            "Names of the Helm packages this package depends on"
        ]
    },
    {
        "name": "B",
        "path_to_chart": "Path to package B",
        "path_to_mappings": "Path to package B mappings",
        "depends_on": [
            "Names of the Helm packages this package depends on"
        ]
    }
]

Die Befolgung dieser Richtlinien führt zu einem gut organisierten und strukturierten Ansatz für die Bereitstellung von CNFs mit Helm-Paketen und den zugehörigen Konfigurationen.

Herunterladen des NGINX-Images in ein lokales Docker-Repository

Für diesen Schnellstart laden Sie das NGINX-Docker-Image in Ihr lokales Repository herunter. Die Azure CLI-Erweiterung für Azure Operator Service Manager (AOSM) verschiebt das Image von dort in den ACR-Artefaktspeicher für Azure Operator Service Manager (AOSM). Die CLI-Erweiterung unterstützt auch das Kopieren des Images aus einer vorhandenen ACR-Instanz. Das Kopieren des Images ist der erwartete Standardanwendungsfall, aber es dauert länger, eine ACR-Instanz für diesen Zweck zu erstellen. Deshalb wird diese Methode in diesem Schnellstart nicht verwendet.

Führen Sie den folgenden Befehl aus: docker pull nginx:stable.

Herunterladen des Helm-Beispieldiagramms

Laden Sie das Helm-Beispieldiagramm für diesen Schnellstart herunter.

Einführung in Helm-Diagramme

In diesem Abschnitt wird ein einfaches Helm-Diagramm vorgestellt, das NGINX einrichtet und konfiguriert, um einem bestimmten Port zu lauschen. Das in diesem Abschnitt eingerichtete Helm-Diagramm enthält bereits eine values.schema.json-Datei.

Beispieldatei „values.schema.json“

{
    "$schema": "http://json-schema.org/draft-07/schema",
    "additionalProperties": true,
    "properties": {
        "affinity": {
            "additionalProperties": false,
            "properties": {},
            "type": "object"
        },
        "fullnameOverride": {
            "type": "string"
        },
        "image": {
            "additionalProperties": false,
            "properties": {
                "pullPolicy": {
                    "type": "string"
                },
                "repository": {
                    "type": "string"
                },
                "tag": {
                    "type": "string"
                }
            },
            "type": "object"
        },
        "imagePullSecrets": {
            "items": {
                "anyOf": []
            },
            "type": "array"
        },
        "ingress": {
            "additionalProperties": false,
            "properties": {
                "annotations": {
                    "additionalProperties": false,
                    "properties": {},
                    "type": "object"
                },
                "enabled": {
                    "type": "boolean"
                },
                "hosts": {
                    "items": {
                        "anyOf": [
                            {
                                "additionalProperties": false,
                                "properties": {
                                    "host": {
                                        "type": "string"
                                    },
                                    "paths": {
                                        "items": {
                                            "anyOf": []
                                        },
                                        "type": "array"
                                    }
                                },
                                "type": "object"
                            }
                        ]
                    },
                    "type": "array"
                },
                "tls": {
                    "items": {
                        "anyOf": []
                    },
                    "type": "array"
                }
            },
            "type": "object"
        },
        "nameOverride": {
            "type": "string"
        },
        "nodeSelector": {
            "additionalProperties": false,
            "properties": {},
            "type": "object"
        },
        "podSecurityContext": {
            "additionalProperties": false,
            "properties": {},
            "type": "object"
        },
        "replicaCount": {
            "type": "integer"
        },
        "resources": {
            "additionalProperties": false,
            "properties": {},
            "type": "object"
        },
        "securityContext": {
            "additionalProperties": false,
            "properties": {},
            "type": "object"
        },
        "service": {
            "additionalProperties": false,
            "properties": {
                "port": {
                    "type": "integer"
                },
                "type": {
                    "type": "string"
                }
            },
            "type": "object"
        },
        "serviceAccount": {
            "additionalProperties": false,
            "properties": {
                "create": {
                    "type": "boolean"
                },
                "name": {
                    "type": "null"
                }
            },
            "type": "object"
        },
        "tolerations": {
            "items": {
                "anyOf": []
            },
            "type": "array"
        }
    },
    "type": "object"
}

Obwohl dieser Artikel nicht im Detail auf Helm eingeht, werden einige wichtige Punkte behandelt:

  • Dienstportkonfiguration: Für values.yaml ist standardmäßig der Dienstport 80 festgelegt.

Beispieldatei „values.yaml“

# Default values for nginxdemo. 
# This is a YAML-formatted file. 
# Declare variables to be passed into your templates. 

 
replicaCount: 1 
 

image: 

  # Repository gets overwritten by AOSM to the Artifact Store ACR, however we've hard-coded the image name and tag in deployment.yaml 

  repository: overwriteme 
  tag: stable 
  pullPolicy: IfNotPresent 


imagePullSecrets: [] 
nameOverride: "" 
fullnameOverride: "" 

 
serviceAccount: 

  # Specifies whether a service account should be created 

  create: false 

  # The name of the service account to use. 
  # If not set and create is true, a name is generated using the fullname template 

  name: 
 

podSecurityContext: 

  {} 

  # fsGroup: 2000 

 
securityContext: 

  {} 
  # capabilities: 
  #   drop: 
  #   - ALL 
  # readOnlyRootFilesystem: true 
  # runAsNonRoot: true 
  # runAsUser: 1000 

 
service: 

  type: ClusterIP 
  port: 80 

  
ingress: 

  enabled: false 
  annotations: 

    {} 

    # kubernetes.io/ingress.class: nginx 
    # kubernetes.io/tls-acme: "true" 

  hosts: 

    - host: chart-example.local 
      paths: [] 

  
  tls: [] 

  #  - secretName: chart-example-tls 
  #    hosts: 
  #      - chart-example.local 

 
resources: 

  {} 

  # We usually recommend not to specify default resources and to leave this as a conscious 
  # choice for the user. This also increases chances charts run on environments with little 
  # resources, such as Minikube. If you do want to specify resources, uncomment the following 
  # lines, adjust them as necessary, and remove the curly braces after 'resources:'. 
  # limits: 
  #   cpu: 100m 
  #   memory: 128Mi 
  # requests: 
  #   cpu: 100m 
  #   memory: 128Mi 
 

nodeSelector: {} 

 
tolerations: [] 

 
affinity: {}
  • Portverweise: Dieser Port wird an mehreren Stellen verwendet:

    • In service.yaml als {{ Values.service.port }}

Beispieldatei „service.yaml“

apiVersion: v1 
kind: Service 

metadata: 
  name: {{ include "nginxdemo.fullname" . }} 
  labels: 

{{ include "nginxdemo.labels" . | indent 4 }} 

spec: 
  type: {{ .Values.service.type }} 
  ports: 
    - port: {{ .Values.service.port }} 
      targetPort: http 
      protocol: TCP 
      name: http 

  selector: 
    app.kubernetes.io/name: {{ include "nginxdemo.name" . }} 
    app.kubernetes.io/instance: {{ .Release.Name }}
  • In nginx_config_map.yaml als {{ Values.service.port }}. Diese Datei entspricht /etc/nginx/conf.d/default.conf, mit einer Zuordnung, die mithilfe einer Konfigurationszuordnung in deployment.yamleingerichtet wurde.

Beispieldatei „nginx_config_map.yaml“

apiVersion: v1 
kind: ConfigMap 
metadata: 
  name: nginx-config 
# This writes the nginx config file to the ConfigMap and deployment.yaml mounts it as a volume  
# to the right place. 

data: 
  default.conf: | 
    log_format client '$remote_addr - $remote_user $request_time $upstream_response_time ' 
                    '[$time_local] "$request" $status $body_bytes_sent $request_body "$http_referer" ' 
                    '"$http_user_agent" "$http_x_forwarded_for"'; 

    server { 
        listen       80; 
        listen       {{ .Values.service.port }}; 
        listen  [::]:80; 
        server_name  localhost; 

        access_log  /var/log/nginx/host.access.log  client; 

        location / { 
            root   /usr/share/nginx/html; 
            index  index.html index.htm; 
            error_page 405 =200 $uri; 
        } 


        #error_page  404              /404.html; 
        # redirect server error pages to the static page /50x.html 
        # 
        error_page   500 502 503 504  /50x.html; 
        location = /50x.html { 
            root   /usr/share/nginx/html; 
        } 


        location = /cnf/test {   
            error_page 405 =200 $uri; 
        } 
   

        location = /post_thing { 
            # turn off logging here to avoid double logging 
            access_log off; 
            error_page 405 =200 $uri; 
        } 
    }

Bereitstellungskonfiguration: Die Datei deployment.yaml hebt bestimmte Zeilen hervor, die für imagePullSecrets und image relevant sind. Achten Sie auf das strukturierte Format, da Azure Operator Service Manager (AOSM) die erforderlichen Werte für diese Felder während der Bereitstellung ausfüllt. Weitere Informationen finden Sie unter Anforderungen für Helm-Pakete.

Beispieldatei „deployment.yaml“

apiVersion: apps/v1 
kind: Deployment 
metadata: 
  name: {{ include "nginxdemo.fullname" . }} 
  labels: 
{{ include "nginxdemo.labels" . | indent 4 }} 

spec: 
  replicas: {{ .Values.replicaCount }} 
  selector: 
    matchLabels: 
      app.kubernetes.io/name: {{ include "nginxdemo.name" . }} 
      app.kubernetes.io/instance: {{ .Release.Name }} 

  template: 
    metadata: 
      labels: 
        app.kubernetes.io/name: {{ include "nginxdemo.name" . }} 
        app.kubernetes.io/instance: {{ .Release.Name }} 

    spec: 
      # Copied from sas 
      imagePullSecrets: {{ mustToPrettyJson (ternary (list ) .Values.imagePullSecrets (kindIs "invalid" .Values.imagePullSecrets)) }} 
      serviceAccountName: {{ template "nginxdemo.serviceAccountName" . }} 
      securityContext: 
        {{- toYaml .Values.podSecurityContext | nindent 8 }} 
      containers: 
        - name: {{ .Chart.Name }} 
          securityContext: 
            {{- toYaml .Values.securityContext | nindent 12 }} 
          # Want this to evaluate to acr-name.azurecr.io/nginx:stable (or specific version) 
          # docker tag nginx:stable acr-name.azurecr.io/nginx:stable 
          # docker push acr-name.azurecr.io/nginx:stable 
          # Image hard coded to that put in the Artifact Store ACR for this CNF POC 
          image: "{{ .Values.image.repository }}/nginx:stable" 
          imagePullPolicy: {{ .Values.image.pullPolicy }} 
          ports: 
            - name: http 
              containerPort: 80 
              protocol: TCP 
          livenessProbe: 
            httpGet: 
              path: / 
              port: http 
          readinessProbe: 
            httpGet: 
              path: / 
              port: http 
          resources: 
            {{- toYaml .Values.resources | nindent 12 }} 
          # Gets the nginx config from the configMap - see nginx_config_map.yaml 
          volumeMounts: 
            - name: nginx-config-volume 
              mountPath: /etc/nginx/conf.d/default.conf 
              subPath: default.conf 
      volumes: 
        - name: nginx-config-volume 
          configMap: 
            name: nginx-config 
      {{- with .Values.nodeSelector }} 
      nodeSelector: 
        {{- toYaml . | nindent 8 }} 
      {{- end }} 
    {{- with .Values.affinity }} 
      affinity: 
        {{- toYaml . | nindent 8 }} 
    {{- end }} 
    {{- with .Values.tolerations }} 
      tolerations: 
        {{- toYaml . | nindent 8 }} 
    {{- end }}

Nächste Schritte