Как использовать хранилище ключей Azure для получения строки подключения, а затем установить AzureWebJobsServiceBus для ServiceBusTrigger - PullRequest
0 голосов
/ 29 апреля 2019

Если я установлю строку подключения AzureWebJobsServiceBus в local.settings.json, то ошибки не будет. Однако я хотел бы использовать хранилище ключей Azure, чтобы предотвратить раскрытие строки подключения.

Ниже моя ошибка:

Microsoft.Azure.WebJobs.Host: Ошибка индексации метода «MyAzureFunc.Run». Microsoft.ServiceBus: строка подключения служебной шины не имеет ожидаемого формата. Либо в строке есть неожиданные свойства, либо формат неверный. Пожалуйста, проверьте строку раньше. пытаясь снова.

Вот мой код:

public static class MyAzureFunc
{
    private static readonly SettingsContext _settings;

    static MyAzureFunc()
    {
        _settings = new SettingsContext(new Settings
        {
            BaseUrl = Environment.GetEnvironmentVariable("BaseUrl"),
            ServiceBusConnectionString = Environment.GetEnvironmentVariable("ServiceBus"),
            certThumbprint = Environment.GetEnvironmentVariable("CertThumbprint"),
            keyVaultClientId = Environment.GetEnvironmentVariable("KeyVaultClientId"),
            ServiceBusSecretUrl = Environment.GetEnvironmentVariable("ServiceBusSecretUrl")
        });

        Environment.SetEnvironmentVariable("AzureWebJobsServiceBus", _settings.ServiceBusConnectionString);
    }

    [FunctionName("Func")]
    public static async Task Run([ServiceBusTrigger(ServiceBusContext.MyQueueName)] BrokeredMessage msg, TraceWriter log)
    {
    ......
    }
}

public SettingsContext(Settings settings)
{
    new MapperConfiguration(cfg => cfg.CreateMap<Settings, SettingsContext>()).CreateMapper().Map(settings, this);
    if (!string.IsNullOrEmpty(settings.certThumbprint) && !string.IsNullOrEmpty(settings.keyVaultClientId))
    {
        var cert = Helpers.GetCertificate(settings.certThumbprint);
        var assertionCert = new ClientAssertionCertificate(settings.keyVaultClientId, cert);
        KeyVaultClient = GetKeyVaultClient(assertionCert);

        if (ServiceBusConnectionString == "nil" && !string.IsNullOrEmpty(settings.ServiceBusSecretUrl))
        {
            ServiceBusConnectionString = KeyVaultClient.GetSecretAsync(settings.ServiceBusSecretUrl).Result.Value;
        }
    }
}

private static KeyVaultClient GetKeyVaultClient(ClientAssertionCertificate assertionCert)
{
    return new KeyVaultClient(new KeyVaultClient.AuthenticationCallback(async (string authority, string resource, string scope) =>
    {
        var context = new AuthenticationContext(authority, TokenCache.DefaultShared);
        var result = await context.AcquireTokenAsync(resource, assertionCert);
        return result.AccessToken;
    }));
}

1 Ответ

1 голос
/ 29 апреля 2019

Это на самом деле намного проще, чем то, что вы пытаетесь;) Смотрите здесь .KeyVault изначально интегрирован с функциями / службами Azure для безопасного хранения настроек.

В файле local.settings.json вы используете строку подключения как есть (в виде простого текста).Этот файл никогда не регистрируется.

В Azure у вас есть настройка приложения с тем же именем, но вместо ввода строки подключения в виде простого текста вы добавляете ссылку на настройку KeyVault следующим образом:

@Microsoft.KeyVault(SecretUri=https://myvault.vault.azure.net/secrets/mysecret/ec96f02080254f109c51a1f14cdb1931)

Единственное, что вам нужно сделать, - это включить управляемую идентификацию вашей функции и предоставить разрешения на чтение этой идентификации в KeyVault.

...