Автоматизация смены секретов для ресурсов с одним набором учетных данных для аутентификации

Лучшим способом проверки подлинности в службах Azure является использование управляемого удостоверения, но иногда его использование невозможно. В этих случаях используют ключи доступа или секреты. Время от времени необходимо сменять эти ключи доступа или секреты.

В этом учебнике описано, как автоматизировать периодическую смену секретов для баз данных и служб, которые используют один набор учетных данных для аутентификации. В частности, в этом учебнике выполняется смена паролей SQL Server, хранящихся в Azure Key Vault. Для ротации используется функция, запускаемая уведомлением Сетки событий Azure:

Схема решения ротации

  1. За 30 дней до истечения срока действия секрета Key Vault публикует в Сетке событий событие "Срок действия скоро истекает".
  2. Сетка событий проверяет подписки на события и с помощью HTTP-запроса методом POST вызывает конечную точку приложения-функции, подписанную на это событие.
  3. Приложение-функция получает сведения о секрете, генерирует случайный пароль и создает другую версию секрета с новым паролем в хранилище ключей.
  4. Приложение-функция обновляет SQL Server, указав новый пароль.

Примечание

Между шагами 3 и 4 может быть задержка. В течение этого времени секрет в Key Vault не сможет пройти проверку подлинности на SQL Server. В случае сбоя на любом из шагов Сетка событий повторит попытку в течение двух часов.

Предварительные требования

Если у вас нет Key Vault и SQL Server, можно использовать эту ссылку для развертывания:

Изображение с кнопкой

  1. Для параметра Группа ресурсов выберите Создать. Укажите имя группы. В нашем примере используется имя akvrotation.
  2. В разделе Sql Администратор Имя входа введите имя входа администратора SQL.
  3. Выберите Review + create (Просмотреть и создать).
  4. Нажмите кнопку Создать

Создание группы ресурсов

Теперь у вас есть Key Vault и экземпляр SQL Server. Вы можете проверить эту установку в Azure CLI, выполнив следующую команду:

az resource list -o table -g akvrotation

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

Name                     ResourceGroup         Location    Type                               Status
-----------------------  --------------------  ----------  ---------------------------------  --------
akvrotation-kv           akvrotation      eastus      Microsoft.KeyVault/vaults
akvrotation-sql          akvrotation      eastus      Microsoft.Sql/servers
akvrotation-sql/master   akvrotation      eastus      Microsoft.Sql/servers/databases
akvrotation-sql2         akvrotation      eastus      Microsoft.Sql/servers
akvrotation-sql2/master  akvrotation      eastus      Microsoft.Sql/servers/databases

Создание и развертывание функции смены паролей SQL Server

Важно!

Для этого шаблона требуется, чтобы хранилище ключей, SQL Server и функция Azure были в одной группе ресурсов.

Затем создайте приложение-функцию с управляемым системой удостоверением в дополнение к другим необходимым компонентам и разверните функции смены паролей SQL Server.

Для приложения-функции требуются следующие компоненты:

  • План службы приложений Azure.
  • Приложение-функция с функциями смены паролей SQL с триггером событий и триггером HTTP
  • Учетная запись хранения, которая нужна для управления триггерами приложения-функции.
  • Политика доступа для получения доступа к секретам в Key Vault с помощью удостоверения приложения-функции.
  • Подписка на события Сетки событий для события SecretNearExpiry
  1. Щелкните ссылку для развертывания шаблона в Azure:

    Изображение с кнопкой

  2. В списке Группа ресурсов выберите avkrotation.

  3. В поле Имя SQL Server введите имя SQL Server с паролем для смены.

  4. В поле Имя хранилища ключей введите имя хранилища ключей

  5. В поле Имя приложения-функции введите имя приложения-функции

  6. В поле Имя секрета введите имя секрета, где будет храниться пароль

  7. В поле URL-адрес репозитория введите расположение кода для функции на сайте GitHub (https://github.com/Azure-Samples/KeyVault-Rotation-SQLPassword-Csharp.git)

  8. Выберите Review + create (Просмотреть и создать).

  9. Нажмите кнопку создания.

Выбор параметра Review+create (Просмотр и создание)

Выполнив описанные выше действия, вы создадите учетную запись хранения, ферму серверов и приложение-функцию. Вы можете проверить эту установку в Azure CLI, выполнив следующую команду:

az resource list -o table -g akvrotation

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

Name                     ResourceGroup         Location    Type                               Status
-----------------------  --------------------  ----------  ---------------------------------  --------
akvrotation-kv           akvrotation       eastus      Microsoft.KeyVault/vaults
akvrotation-sql          akvrotation       eastus      Microsoft.Sql/servers
akvrotation-sql/master   akvrotation       eastus      Microsoft.Sql/servers/databases
cfogyydrufs5wazfunctions akvrotation       eastus      Microsoft.Storage/storageAccounts
akvrotation-fnapp        akvrotation       eastus      Microsoft.Web/serverFarms
akvrotation-fnapp        akvrotation       eastus      Microsoft.Web/sites
akvrotation-fnapp        akvrotation       eastus      Microsoft.insights/components

Дополнительные сведения о создании приложения-функции и использовании управляемого удостоверения для доступа к Key Vault см. в статьях Создание приложения-функции на портале Azure, Использование управляемых удостоверений в Службе приложений и Функциях Azure и Назначение политики доступа к Key Vault с помощью портала Azure.

Функция ротации

Развернутая на предыдущем шаге функция использует событие, чтобы активировать ротацию секрета путем обновления Key Vault и базы данных SQL.

Событие, вызывающее функцию

Приведенная ниже функция считывает данные события и выполняет логику ротации.

public static class SimpleRotationEventHandler
{
   [FunctionName("AKVSQLRotation")]
   public static void Run([EventGridTrigger]EventGridEvent eventGridEvent, ILogger log)
   {
      log.LogInformation("C# Event trigger function processed a request.");
      var secretName = eventGridEvent.Subject;
      var secretVersion = Regex.Match(eventGridEvent.Data.ToString(), "Version\":\"([a-z0-9]*)").Groups[1].ToString();
      var keyVaultName = Regex.Match(eventGridEvent.Topic, ".vaults.(.*)").Groups[1].ToString();
      log.LogInformation($"Key Vault Name: {keyVaultName}");
      log.LogInformation($"Secret Name: {secretName}");
      log.LogInformation($"Secret Version: {secretVersion}");

      SecretRotator.RotateSecret(log, secretName, keyVaultName);
   }
}

Логика ротации секретов

Этот метод ротации считывает сведения о базе данных из секрета, создает другую версию секрета и обновляет базу данных, указав новый секрет.

    public class SecretRotator
    {
		private const string CredentialIdTag = "CredentialId";
		private const string ProviderAddressTag = "ProviderAddress";
		private const string ValidityPeriodDaysTag = "ValidityPeriodDays";

		public static void RotateSecret(ILogger log, string secretName, string keyVaultName)
        {
            //Retrieve Current Secret
            var kvUri = "https://" + keyVaultName + ".vault.azure.net";
            var client = new SecretClient(new Uri(kvUri), new DefaultAzureCredential());
            KeyVaultSecret secret = client.GetSecret(secretName);
            log.LogInformation("Secret Info Retrieved");

            //Retrieve Secret Info
            var credentialId = secret.Properties.Tags.ContainsKey(CredentialIdTag) ? secret.Properties.Tags[CredentialIdTag] : "";
            var providerAddress = secret.Properties.Tags.ContainsKey(ProviderAddressTag) ? secret.Properties.Tags[ProviderAddressTag] : "";
            var validityPeriodDays = secret.Properties.Tags.ContainsKey(ValidityPeriodDaysTag) ? secret.Properties.Tags[ValidityPeriodDaysTag] : "";
            log.LogInformation($"Provider Address: {providerAddress}");
            log.LogInformation($"Credential Id: {credentialId}");

            //Check Service Provider connection
            CheckServiceConnection(secret);
            log.LogInformation("Service  Connection Validated");
            
            //Create new password
            var randomPassword = CreateRandomPassword();
            log.LogInformation("New Password Generated");

            //Add secret version with new password to Key Vault
            CreateNewSecretVersion(client, secret, randomPassword);
            log.LogInformation("New Secret Version Generated");

            //Update Service Provider with new password
            UpdateServicePassword(secret, randomPassword);
            log.LogInformation("Password Changed");
            log.LogInformation($"Secret Rotated Successfully");
        }
}

Полный пример кода можно найти на сайте GitHub.

Добавление секрета в хранилище ключей

Настройте политику доступа, предоставив пользователям разрешение на управление секретами.

az keyvault set-policy --upn <email-address-of-user> --name akvrotation-kv --secret-permissions set delete get list

Создайте секрет с тегами, содержащими идентификатор ресурса SQL Server, имя пользователя SQL Server и срок действия секрета в днях. Укажите имя секрета, начальный пароль из базы данных SQL (в нашем примере — Simple123) и дату окончания срока действия, которая назначена на завтра.

$tomorrowDate = (get-date).AddDays(+1).ToString("yyy-MM-ddThh:mm:ssZ")
az keyvault secret set --name sqlPassword --vault-name akvrotation-kv --value "Simple123" --tags "CredentialId=sqlAdmin" "ProviderAddress=<sql-database-resource-id>" "ValidityPeriodDays=90" --expires $tomorrowDate

При создании секрета с коротким сроком действия через 15 минут публикуется событие SecretNearExpiry, которое вызывает функцию для смены секрета.

Тестирование и проверка

Чтобы убедиться в ротации секрета, перейдите в раздел Key Vault>Секреты:

Снимок экрана: доступ к секретам Key Vault>.

Откройте секрет sqlPassword и просмотрите исходную и измененную версию.

Переход к секретам

Создание веб-приложения

Чтобы проверить учетные данные SQL, создайте веб-приложение. Это веб-приложение получит секрет из Key Vault, извлечет из секрета сведения о базе данных и учетные данные SQL, а также выполнит проверку подключения к SQL.

Для веб-приложения требуются следующие компоненты:

  • веб-приложение с управляемым системой удостоверением;
  • политика доступа для получения доступа к секретам в хранилище ключей с использованием управляемого удостоверения веб-приложения.
  1. Щелкните ссылку для развертывания шаблона в Azure:

    Изображение с кнопкой

  2. Выберите группу ресурсов akvrotation.

  3. В поле Имя SQL Server введите имя SQL Server с паролем для смены.

  4. В поле Имя хранилища ключей введите имя хранилища ключей

  5. В поле Имя секрета введите имя секрета, где хранится пароль

  6. В поле URL-адрес репозитория введите расположение кода для веб-приложения на сайте GitHub (https://github.com/Azure-Samples/KeyVault-Rotation-SQLPassword-Csharp-WebApp.git)

  7. Выберите Review + create (Просмотреть и создать).

  8. Нажмите кнопку создания.

Открытие веб-приложения

Выберите URL-адрес развернутого приложения.

'https://akvrotation-app.azurewebsites.net/'

Когда приложение откроется в браузере, вы увидите созданное секретное значение и подключенную базу данных со значением true.

Дополнительные сведения