Как добавить новый сертификат для прослушивателя шлюза приложений Azure с помощью Python

все.

Я новичок в Интернете и Azure. У меня вопрос о добавлении сертификата в прослушиватель шлюза приложений Azure с Python. Я подробно описываю свою проблему следующим образом.

1. Фон

Я использую среду Azure:

Resource group name: My_ResourceGroup
Subscription ID: sub_id
Tenant ID: tenant_id
Client: my_client
Service principal password: sp_password

2. Верхний домен и субдомен

В группе ресурсов My_ResourceGroup есть два поставщика Azure DNS с зонами contoso.com и chen.contoso.com соответственно. contoso.com - это верхний домен, а chen.contoso.com - поддомен.

Для chen.contoso.com я создал запись A с именем www и IP 10.10.10.10 (обратите внимание, что этот IP используется только для тестирования). Я также создал сертификат (файл cert.pfx) для этого домена, чтобы использовать HTTPS.

3. Установите cert.pfx сертификат на прослушиватель

У меня есть готовый шлюз приложений Azure contoso-appgw в группе ресурсов My_ResourceGroup. В этом шлюзе есть прослушиватель contoso-appgw-hl, и в этом прослушивателе был сертификат cert0.pfx.

Я хочу добавить (или установить) cert.pfx сертификат в прослушиватель contoso-appgw-hl с помощью Azure Python SDK. После этой операции в прослушивателе contoso-appgw-hl: cert0.pfx (старый) должно быть два сертификата. и cert.pfx (новый).

4. Мой код и ссылки

Мой код Python выглядит следующим образом:

from azure.common.credentials import ServicePrincipalCredentials
from azure.mgmt.resource import ResourceManagementClient
from azure.mgmt.network import NetworkManagementClient

# Replace this with your subscription id
subscription_id = 'sub_id'

# Tenant ID for your Azure subscription
TENANT_ID = 'tenant_id'

# Your service principal App ID
CLIENT = 'client'

# Your service principal password
KEY = 'sp_password'

credentials = ServicePrincipalCredentials(
        client_id = CLIENT,
        secret = KEY,
        tenant = TENANT_ID
    )

network_client = NetworkManagementClient(credentials, subscription_id)

network_client.application_gateways.create_or_update(
    'My_ResourceGroup',
    'contoso-appgw',
    {
        'location': 'East US 2',
        'http_listeners': [
            {
                'name': 'contoso-appgw-hl',
                'protocol': 'Https',

                'ssl_certificate': {
                    'data': 'cert.pfx',
                    'name': 'chenkui',
                    'password': '123abc'
                }
            }
        ]
    }
)

Я написал свой код на основе следующих ресурсов:

  1. Пример кода: приложение Azure для управления образцом кода
  2. Документ Azure: определение функции create_or_update

Обратите внимание, что cert.pfx в моем коде является сертификатом формата Base-64, потому что на основе документа требуется сертификат формата Base-64.

5. Сообщение об ошибке

Приведенный выше код не работает. Сообщение об ошибке, показанное в Azure Portal --> contoso-appgw --> Activity log приведенного выше кода:

Operation name:
    Create or Update Application Gateway

Error code:
    InvalidRequestFormat

Message:
    Cannot parse the request.

Даже если я использую портал Azure (т.е. вместо кода Python используйте портал с графическим интерфейсом пользователя в браузере), добавить сертификат также не удается. Сообщение об ошибке, показанное в Azure Portal --> contoso-appgw --> Activity log:

Operation name:
    Create or Update Application Gateway

Error code: 
    ApplicationGatewaySslCertificateDataMustBeSpecified

Message:
    Data must be specified for Certificate /subscriptions/c72b5b1b-771e-4b65-ba34-a7db981c9dcf/resourceGroups/My_ResourceGroup/providers/Microsoft.Network/applicationGateways/contoso-appgw/sslCertificates/chenkui.

6. Мой вопрос

Мои вопросы даются следующим образом:

  1. Что означают эти сообщения об ошибках?
  2. Почему приводятся эти ошибки?
  3. В чем проблема моего кода и как ее решить?

Большое спасибо!


person zchenkui    schedule 08.09.2019    source источник
comment
Не могли бы вы сказать мне, нужно ли вам просто добавить сертификат SSL или вам нужно изменить протокол с http на https?   -  person Jim Xu    schedule 09.09.2019
comment
@JimXu Спасибо за ответ. Я хочу сделать и то, и другое. Добавьте этот сертификат SSL в прослушиватель и измените протокол с http на https.   -  person zchenkui    schedule 09.09.2019
comment
Вы ссылались на docs.microsoft.com/en-us/python/api/azure-mgmt-network/? Согласно документу, вам необходимо предоставить идентификатор ресурса SSL-сертификата.   -  person Jim Xu    schedule 09.09.2019
comment
Следуете ли вы за процессом загрузки сертификата: слушатель - выберите сертификат (создайте новый) - загрузите сертификат - выберите файл pfx, имя сертификата и пароль? Вы используете v1 sku app gw?   -  person Nancy Xiong    schedule 10.09.2019
comment
Для меня я получаю аналогичную ошибку с gw v2, когда я загружаю тот же сертификат PFX, что и существующий, путем создания нового сертификата при выборе сертификата.   -  person Nancy Xiong    schedule 10.09.2019
comment
@zchenkui У вас есть обновления?   -  person Jim Xu    schedule 12.09.2019
comment
@JimXu @NancyXiong Прошу прощения за поздний ответ. Я нашел решение. Проблема здесь в том, что функция create_or_update используется неправильно. При обновлении существующего ресурса мы должны сначала get это сделать. Я дам решение следующим образом.   -  person zchenkui    schedule 13.09.2019


Ответы (2)


Если вы хотите скрыть прослушиватель с http на https, вы можете использовать следующий сценарий PowerShell:

$appgw= Get-AzApplicationGateway -Name "AppGWname" -ResourceGroupName "RG Name"

#$listener= Get-AzApplicationGatewayHttpListener -Name listener1 -ApplicationGateway $appgw

$FEC= Get-AzApplicationGatewayFrontendIPConfig -Name "FrontendIP" -ApplicationGateway $appgw


Add-AzApplicationGatewayFrontendPort -ApplicationGateway $appgw -Name "Name of the Port" -Port 443 

$port = Get-AzApplicationGatewayFrontendPort -ApplicationGateway $appgw -Name "Name of Port"

$passwd = ConvertTo-SecureString  "Passoword" -AsPlainText -Force 


Add-AzApplicationGatewaySSLCertificate -Name "Name of the cert" -CertificateFile "Full path of the cert with.pfx" -Password $passwd -ApplicationGateway $appgw

$cert =Get-AzApplicationGatewaySSLCertificate -Name "Name of cert" -ApplicationGateway $appgw

Set-AzApplicationGatewayHttpListener -ApplicationGateway $appgw -Name "Name of the listener" -FrontendIPConfiguration $FEC -FrontendPort $port -Protocol Https -SslCertificate $cert

Set-AzApplicationGateway -ApplicationGateway $appgw
person Jim Xu    schedule 13.09.2019
comment
Спасибо за ваш ответ. Я нашел решение Python по этой теме. Пожалуйста, проверьте следующий ответ. Большое спасибо! - person zchenkui; 13.09.2019
comment
Ok. Спасибо, что поделились. - person Jim Xu; 13.09.2019

Я нашел способ обновить существующий шлюз приложений. При использовании функции create_or_update для обновления существующего ресурса Azure сначала необходимо get. В противном случае create_or_update создаст новый ресурс вместо обновления существующего.

Следующая ссылка является хорошим примером. Он создает и обновляет виртуальную машину Azure. Создание виртуальных машин Windows и управление ими в Azure с помощью Python

Поскольку для создания ресурсов в Azure и управления ими используется единый метод, мы можем применить идею, приведенную в приведенной выше ссылке, для управления шлюзом приложений. Код выглядит следующим образом.

import base64

from azure.common.credentials import ServicePrincipalCredentials
from azure.mgmt.resource import ResourceManagementClient
from azure.mgmt.network import NetworkManagementClient
from azure.mgmt.network.v2019_06_01.models import ApplicationGateway, ApplicationGatewaySslCertificate


def test_appgw():
    # create credentials
    credentials = ServicePrincipalCredentials(
            client_id = CLIENT,
            secret = KEY,
            tenant = TENANT_ID
        )

    # create network client
    network_client = NetworkManagementClient(credentials, subscription_id)

    # get an existing application gateway
    app_gw = network_client.application_gateways.get(RESOURCE_GROUP_NAME, APPLICATION_GATEWAY_NAME)

    # read the pfx certificate and convert it to base-64 string
    with open('certificate.pfx', 'rb') as binary_cert:
        base64_cert = base64.b64encode(binary_cert.read())
        cert_data = base64_cert.decode('utf-8')

    # create an SSL certificate
    ssl_cert = ApplicationGatewaySslCertificate(
        name=ANY_NAME_IS_OK,
        data=cert_data,
        password=THE_PASSWARD_USED_TO_CREATE_CERTIFICATE
    )

    # app_gw.ssl_certificates is a Python list, so we append the new certificate in it
    app_gw.ssl_certificates.append(ssl_cert)

    # update the application gateway
    network_client.application_gateways.create_or_update(
        RESOURCE_GROUP_NAME,
        APPLICATION_GATEWAY_NAME,
        app_gw
    )

if __name__ == "__main__":
    test_appgw()

Примечание:

  1. Использование функции get для получения существующего шлюза приложений;
  2. Первый параметр name класса ApplicationGatewaySslCertificate - это строка. Вы можете использовать любое имя, какое захотите;
  3. Второй параметр data - это строка. Это НЕ имя сертификата, а строка содержимого сертификата pfx в формате Base-64;
  4. Третий параметр password - это строка. Это должен быть пароль, с помощью которого вы создаете свой pfx сертификат.

Надеюсь, это поможет вам.

person zchenkui    schedule 13.09.2019
comment
@JimXu Я разместил здесь свое решение. Пожалуйста, проверь это. Большое спасибо! - person zchenkui; 13.09.2019