Аутентификация и авторизация - важная часть любой системы управления секретами. Таким образом, я бы сказал, что управление идентификацией и доступом является краеугольным камнем всех систем управления секретами. Секреты, которыми буквально должен владеть правильный человек с правильными привилегиями, не могут попасть в чужие руки.

В этом блоге мы интегрируем управление идентификацией и доступом из открытого WSO2 Identity Server в одну из самых популярных систем управления секретами, HashiCorp Vault.

Что такое Vault от HashiCorp?

Представьте, что во время разработки вашего приложения вам необходимо создать соединение с базой данных. Для этого необходимо хранить учетные данные подключения к базе данных и использовать их всякий раз, когда это необходимо. Итак, где мы храним эти учетные данные? Вы можете сохранить их в файле конфигурации, но с высоким риском их потери. Как насчет их шифрования? Тем не менее, вам нужно где-то хранить главный ключ для дешифрования, что опять же создает такую ​​же угрозу безопасности.

Решение - поместить их в хранилище! Приложение выполнит аутентификацию в хранилище и при необходимости получит необходимые учетные данные. Хранилище будет безопасно управлять нашими учетными данными.

Vault от HashiCorp - это такая реализация хранилища. Он может безопасно управлять секретами, такими как пароли, токены, сертификаты, ключи API и любые другие секреты в современных вычислениях.

Аутентификация в Vault от HashiCorp

Как вы, наверное, уже заметили, аутентификация - важная часть хранилища. Хранилище должно гарантировать, что каждый хранимый в нем секрет доступен только ожидаемой аудитории и никому другому.

HashiCorp Vault поддерживает систему аутентификации и авторизации на основе токенов. Авторизация здесь контролирует, что пользователь может и не может делать в Vault. Токену хранилища назначается набор политик, который определяет, что пользователь, имеющий этот токен, может делать в хранилище.

В хранилище HashiCorp аутентификация - это просто процесс, с помощью которого пользователь или машина получает токен хранилища.

HashiCorp Vault поддерживает несколько подключаемых методов аутентификации. Он поддерживает OOTB для многих существующих методов аутентификации, включая GitHub, Azure, AWS и Google Cloud.

Он также поддерживает аутентификацию с помощью JWT. Это то, что мы собираемся использовать в этой статье для аутентификации в хранилище с использованием WSO2 Identity Server.

Аутентификация в Vault с использованием WSO2 Identity Server

Мы будем использовать WSO2 Identity Server в качестве JWT-провайдера для аутентификации в HashiCorp Vault, получая JWT от Identity Server и обменивая его на Vault Token. Посмотрим, как мы можем с этим работать.

В этом руководстве я собираюсь использовать экземпляр WSO2 Identity Server 5.7.

Настроить сервер идентификации WSO2

Используемая нами аутентификация на основе JWT требует, чтобы Vault использовал WSO2 IS в качестве провайдера OpenId Connect. Это позволяет Vault проверять JWT в запросе на вход, получая открытые ключи из WSO2 IS. В дополнение к этому Vault требует, чтобы экземпляр WSO2 IS имел сертификат, подписанный CA, чтобы проверять соединения между ними.

Однако OOTB WSO2 IS упаковывает самоподписанный сертификат SSL в качестве своего общедоступного сертификата. Поэтому нам нужно настроить это с помощью сертификата, подписанного CA. Для этого вы можете использовать это полное руководство. С этого момента я предполагаю, что ваш Identity Server настроен с сертификатом, подписанным CA.

Теперь нам нужно экспортировать публичный сертификат из WSO2 IS в формате PEM. Позже в этом руководстве мы предоставим это Vault. Получив сертификат, храните его где-нибудь, чтобы мы могли использовать его позже.

Теперь следующая часть немного хлопотна из-за известной проблемы с WSO2 Identity Server 5.7. В WSO2 IS 5.7 URL-адрес издателя OIDC не везде согласован. Это означает, что у него нет единой точки для настройки URL-адреса издателя OIDC, используемого в токах JWT, ответе на обнаружение OIDC и т. Д. Это было исправлено, начиная с версии WSO2 IS 5.8. Но на момент написания этого блога версия 5.8 еще не выпущена. Если вам нужна дополнительная информация по этому поводу, обратитесь к этой проблеме на GitHub.

Как это влияет на нас? Хранилищу требуется значение URL-адреса издателя OIDC для получения открытых ключей, и оно проверяет этот URL-адрес эмитента на соответствие утверждению iss в токене JWT из запроса на вход. Теперь из-за упомянутой проблемы настройка URL-адреса издателя OIDC не изменит утверждение iss в токене JWT.

Поэтому мы настроим конечную точку обнаружения OIDC для WSO2 IS в соответствии с утверждением OOTB iss в токенах JWT.

Откройте файл ‹IS_Home› /repository/conf/identity/identity.xml. Найдите конфигурацию ‹OIDCDiscoveryEPUrl›. Измените это значение на следующее.

<OIDCDiscoveryEPUrl>${carbon.protocol}://${carbon.host}:${carbon.management.port}/oauth2/token</OIDCDiscoveryEPUrl>

Мы предоставим этот URL-адрес в качестве источника OIDC для Vault позже. Он добавит /.well-known/openid-configuration к этому издателю и получит документ обнаружения OIDC из WSO2 IS. Но любой HTTP-запрос с URI, содержащим /.well-known, защищен в WSO2 IS, поэтому требует аутентификации. Поэтому нам нужно снять это ограничение, чтобы Vault мог взаимодействовать с WSO2 IS.

Откройте файл ‹IS_Home› /repository/conf/identity/identity.xml. Найдите конфигурацию ‹Resource context =” (. *) /. Well-known (. *) ”Secured =” true ”http-method =” all ”/› в разделе ‹ResourceAccessControl ›. Установите для параметра secure значение false. Теперь это должно выглядеть, как показано ниже.

<Resource context="(.*)/.well-known(.*)" secured="false" http-method="all"/>

Теперь наш экземпляр WSO2 IS готов к взаимодействию с Vault. Прежде чем мы перейдем к WSO2 IS, давайте получим токен JWT ID для аутентификации Vault.

Но прежде чем мы запросим токен JWT ID, нам нужно настроить WSO2 IS для нашего запроса токена ID. Во-первых, давайте создадим поставщика услуг для нашего JWT-запроса.

Перейдите в ‹IS_HOME› / bin и запустите сценарий wso2server.sh, чтобы запустить экземпляр WSO2 IS.

sh wso2server.sh

Перейдите на Домашняя страница ›Идентификация› Поставщики услуг ›Добавить. Введите имя как vault.jwt.provider. Нажмите зарегистрироваться.

Откройте Конфигурация входящей аутентификации ›Конфигурация OAuth / OpenID Connect и нажмите кнопку Настроить.

На форуме «Регистрация нового приложения» установите для URL-адреса обратного вызова желаемое значение. После успешной аутентификации пользователя с помощью WSO2 IS проверяющая сторона (клиент, который сделал запрос аутентификации, обычно наш браузер) будет перенаправлен на URL-адрес обратного вызова с требуемым токеном идентификатора в качестве параметра запроса.

В этом руководстве я собираюсь установить это значение на домашней странице Google. Для этого нет особой причины. Мне просто нужно какое-то перенаправление без орешков, чтобы я мог получить свой ID-токен из параметров запроса в перенаправленном URL-адресе. Вы поймете это лучше, когда мы позже запросим JWT.

Я также установлю Включить ограничение аудитории и добавлю значение https://admin.wso2.com, набрав и нажав кнопку Добавить рядом с ним. Это будет использоваться позже с Vault, чтобы установить ограничение аутентификации на основе аудитории.

Остальное оставьте как есть. Нажмите кнопку Добавить. Вернувшись к поставщику услуг, нажмите кнопку Обновить.

Все в порядке. Затем необходимо запросить токен JWT ID с помощью нашего поставщика услуг vault.jwt.provider. Но если я сделаю это сейчас, для запроса, который я собираюсь выполнить следующим, токен идентификатора ответа не будет содержать дополнительных утверждений пользователя. Это будет плохо на будущее, потому что аутентификация Vault JWT имеет потрясающие возможности для работы с утверждениями пользователей в токене идентификатора.

Поэтому я направлю вас к этому руководству из документации WSO2, чтобы настроить несколько примеров утверждений с нашим поставщиком услуг vault.jwt.provider, создать и настроить пользователя с именем tom, и создайте объект запроса OIDC, чтобы запросить WSO2 IS добавить некоторые дополнительные утверждения в токен идентификатора ответа.

Перед тем, как сделать это, убедитесь, что вы выполнили только шаги со 2 по 5. И воспользуйтесь для них нашим поставщиком услуг vault.jwt.provider. В конце шага 5 вы создадите подписанный объект запроса. Получи это и возвращайся сюда.

Ok. Я предполагаю, что теперь у вас есть подписанный объект запроса, о котором я просил. Используйте указанный ниже URL-адрес в своем браузере, чтобы получить токен JWT ID для созданного вами пользователя tom.

https://<server-host-name>:9443/oauth2/authorize?
        response_type=id_token
        &client_id=<client-id>
        &redirect_uri=https://www.google.com/
        &scope=openid
        &state=af0ifjsldkj
        &nonce=n-0S6_WzA2Mj
        &request=<signed-request-object>

Обязательно заполните каждое из значений заполнителя в приведенном выше запросе.

‹server-host-name›: имя хоста вашего экземпляра WSO2 IS.

‹client-id›: значение ключа клиента OAuth для поставщика услуг vault.jwt.provider.

‹signed-request-object›: Вы уже знаете, что это такое!

Как только вы это сделаете, вы будете перенаправлены на страницу входа в WSO2 IS. Используйте учетные данные для пользователя tom. Если в качестве следующего шага вас попросят предоставить согласие любого пользователя, утвердите его.

После успешной аутентификации вы будете перенаправлены на URL-адрес обратного вызова, настроенный ранее. Это была бы домашняя страница Google, если бы вы настроили тот же URL-адрес, что и я.

Обратите внимание, что у нас есть параметр запроса с именем id_token в URL-адресе ответа. Ценность этого будет нашим токеном JWT ID! Если вы расшифруете это и посмотрите на его полезные данные, вы увидите, что он содержит дополнительный адрес электронной почты и страну с заявками пользователя, которые мы запросили ранее с объектом запроса.

Что мы сделали, так это получили токен JWT ID с предпочтительным значением аудитории и некоторыми пользовательскими утверждениями более простым способом. Вы можете использовать любой другой метод, который также получит этот токен JWT ID.

Теперь, когда у нас есть токен JWT ID и экземпляр WSO2 IS, готовый к взаимодействию с Vault, давайте перейдем к HashiCorp Vault.

Настройка Vault и затем аутентификация

Для этого руководства я запущу Vault dev-сервер. Сервер разработки - это встроенный предварительно настроенный сервер, который не очень безопасен, но полезен для локальной игры с Vault. Это поможет нам проверить, как мы можем настроить аутентификацию JWT с помощью Vault.

Вам необходимо выполнить инструкции по установке хранилища и запуску сервера разработки и запустить сервер разработки хранилища.

Во-первых, нам нужно настроить URL-адрес обнаружения OIDC Vault, чтобы он указывал на экземпляр WSO2 IS как на поставщика OIDC. Мы также включим подписанный ЦС публичный сертификат WSO2 Identity Server.

curl \
        --header "X-Vault-Token: s.xP4tTq1Yu2UCXjwGSveWYvv4" \
        --request POST \
        --data '{"oidc_discovery_url": "https://wso2.ml:9443/oauth2/token","oidc_discovery_ca_pem":"-----BEGIN CERTIFICATE-----\nMIIFRjCCBC6gAwIBAgISA8bTJ5tl2FIN9wxw/2o2a/oPMA0GCSqGSIb3DQEBCwUAMEoxCzAJBgNVBAYTAlVTMRYwFAYDVQQKEw1MZXQncyBFbmNyeXB0MSMwIQYDVQQDExpMZXQncyBFbmNyeXB0IEF1dGhvcml0eSBYMzAeFw0xOTAzMjAwOTI0MzZaFw0xOTA2MTgwOTI0MzZaMBIxEDAOBgNVBAMTB3dzbzIubWwwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCNvf5/xx+8pVKQ2dhmKUj3CDQmBeNNviE4iuvGMEwpd+VtViKO8wWQ6ikrhpswnhGdZDK4OcnYLZbX9p+W7TFWkzIogIkxgAOUMDzkfpFcVxan+vH24Pn3H/+3xfhvq5j6oyBiHI4KfD5M4EEElm+sqFmkGYEELXzVd4Zr7N6LKP7N2uu9vB9brOLI3c7xBYWj1VmhcsnUSm7miWnmu842lleNQnKL0UB8dGea8Vj8lHSnAl2eZqGyAEbcahnZcL5JBzeYq7/drlX9APBtx0ZlNr3qa/vWVeXZJUi4Wl2urI9aKPO4B+WKoyA4r65vc5rO811sK19nqwDiHPEfPMv7AgMBAAGjggJcMIICWDAOBgNVHQ8BAf8EBAMCBaAwHQYDVR0lBBYwFAYIKwYBBQUHAwEGCCsGAQUFBwMCMAwGA1UdEwEB/wQCMAAwHQYDVR0OBBYEFLIErOBYEeEmSTl9xh8z++HVr2cGMB8GA1UdIwQYMBaAFKhKamMEfd265tE5t6ZFZe/zqOyhMG8GCCsGAQUFBwEBBGMwYTAuBggrBgEFBQcwAYYiaHR0cDovL29jc3AuaW50LXgzLmxldHNlbmNyeXB0Lm9yZzAvBggrBgEFBQcwAoYjaHR0cDovL2NlcnQuaW50LXgzLmxldHNlbmNyeXB0Lm9yZy8wEgYDVR0RBAswCYIHd3NvMi5tbDBMBgNVHSAERTBDMAgGBmeBDAECATA3BgsrBgEEAYLfEwEBATAoMCYGCCsGAQUFBwIBFhpodHRwOi8vY3BzLmxldHNlbmNyeXB0Lm9yZzCCAQQGCisGAQQB1nkCBAIEgfUEgfIA8AB2AHR+2oMxrTMQkSGcziVPQnDCv/1eQiAIxjc1eeYQe8xWAAABaZqhneAAAAQDAEcwRQIgO5+uvm24J8pjaBvWnKa8EWK7AguCPjnvHmZ6ul79hzMCIQCtqKaUznH03cLH7sSe6STzzrrAmvljtAsD1H8Weng84QB2AGPy283oO8wszwtyhCdXazOkjWF3j711pjixx2hUS9iNAAABaZqhnisAAAQDAEcwRQIhAPrHwX2N8pqafeRcDft3zkVMMLH2f3hZ4G578P/IkoSqAiAucC+AiFD9tm5uoH2uxxI1j/ZxypEV10OBouoLu1c39TANBgkqhkiG9w0BAQsFAAOCAQEAN+3orkveDvATF4kZOWSCRZvJ0qfMpdl70KI9rrtgb4z5yJN+aXLhElhxanpQ5IvRqLF1Ghf4z+1oTOxRgYI3lOgMbdF7xTHC7da5mBwTsriy/c8KbclT8ES0DEkHufNKdEMso5uQGZ4gKpRWbl6wXqndaJQ4g6sFhKae7tRvyHu7KOk+EWPfPbtGJLff7WiJrJHsifmDQhRCinmhNoA/kNErkgYYJ0Onq359DOFSzRc8glddRBvf/OqjaErp3OHVGwZ9JZ194zy1dH64KbzJ/pGyWcpFzjQmuCawszHVRrEXLKf1dkZpy5U9x/ql0YsG73Oj3HAyB/CS4dKeIPzRsg==\n-----END CERTIFICATE-----"}' \
        http://127.0.0.1:8200/v1/auth/jwt/config

Замените приведенное выше и сделайте запрос.

X-Vault-Token: замените его корневым токеном вашего сервера Vault Dev.

oidc_discovery_ca_pem: Замените это на подписанный CA публичный сертификат WSO2 IS. Вам необходимо включить переводы строк после и до тегов - - -BEGIN CERTIFICATE - - и - - - -END CERTIFICATE - - -.

Затем мы создадим роль в хранилище. Роль создается с ограничениями, и для роли предпринимается попытка входа в систему. Теперь ограничения, созданные с помощью этой роли, применяются к объектам, пытающимся войти в систему.

Роль интегрирована с логином JWT. Поэтому мы можем установить ограничения аутентификации в роли на основе токена JWT.

В этом примере мы ограничим нашу аутентификацию желаемой аудиторией. Только JWT, имеющий ожидаемую аудиторию, может войти в систему. Хранилище HashiCorp имеет множество таких ограничений, которые могут применяться с ролью. Вы можете сослаться на них в руководстве по API.

Давайте создадим демонстрацию роли . Эта роль требует, чтобы JWT запрашивал значение аудитории, https://admin.wso2.com, и он будет однозначно идентифицировать вошедшего в систему пользователя по запросу по электронной почте. . Вот почему мы запросили у ID Token дополнительные утверждения, чтобы они использовались в ограничениях ролей.

curl \
        --header "X-Vault-Token: s.xP4tTq1Yu2UCXjwGSveWYvv4" \
        --request POST \
        --data '{"bound_audiences": "https://admin.wso2.com","user_claim": "email"}' \
        http://127.0.0.1:8200/v1/auth/jwt/role/demo

Замените следующее в приведенном выше запросе и сделайте запрос.

X-Vault-Token: замените его корневым токеном вашего сервера Vault Dev.

Все в порядке. Теперь у нас есть роль в хранилище и JWT из WSO2 IS. Давайте войдем в HashiCorp Vault, используя эти два.

curl \
        --request POST \
        --data '{ \
        "jwt": "eyJ4NXQiOiJOMlF6TldFNFlqazRNamMyTmpVeU9Ea3dNR05qWldKbU9Ua3lNak5rWkdSak56WXdNRGcwTXciLCJraWQiOiJOMlF6TldFNFlqazRNamMyTmpVeU9Ea3dNR05qWldKbU9Ua3lNak5rWkdSak56WXdNRGcwTXciLCJhbGciOiJSUzI1NiJ9.eyJhdWQiOlsiV3RTTVJWeGVJdThfRDNaYjhUa2VjOEVBdFJRYSIsImh0dHBzOlwvXC9hZG1pbi53c28yLmNvbSJdLCJzdWIiOiJ0b20iLCJjb3VudHJ5IjoiU3JpIExhbmthIiwiYXpwIjoiV3RTTVJWeGVJdThfRDNaYjhUa2VjOEVBdFJRYSIsImFtciI6W10sImlzcyI6Imh0dHBzOlwvXC93c28yLm1sOjk0NDNcL29hdXRoMlwvdG9rZW4iLCJleHAiOjE1NTMxMDg3MzEsImlhdCI6MTU1MzEwNTEzMSwibm9uY2UiOiJuLTBTNl9XekEyTWoiLCJlbWFpbCI6InRvbUB3c28yLmNvbSIsInNpZCI6ImI4OWYyZDIwLTdlMGUtNDJkMy05ZmM4LTllZmY3YTRkYWU2MiJ9.RucQwZ9aHlO8ls6M4iXXntH7S_lalL2ep6_q_PO0IlJvxuu_2vdNCX13KbmqKC78IokHOP_sQNNicSA43oOQziiFtLuy5cDhE9JoU2FHvUBDFfxxtPmNeKs7WxxfHB4hYME67zdzY9QuG3iUPv3PqFY9Ox0ARH1ZZgVTzgDiEbLRuMr2IWgr9kS2NS5oI2RyVGvNe8gARz82KXaJX2EY1_3zbI7DJ_xqHNUwb9qoGqWTPEbaRnXfdZ1TchukUU_atLgoNHlbWhBdubGyXIOYtzvIRTZLXg4pg8OnlXxOTr88J8u0PmzH_R7rtI_K26jNsj1KeYK3ZINgSQjmoceIVg",\
        "role": "demo" \
        }' \
        http://127.0.0.1:8200/v1/auth/jwt/login

Замените приведенное выше и сделайте запрос.

jwt: Замените его корневым токеном вашего сервера Vault Dev.

У вас будет следующий успешный ответ. Обратите внимание, что в ответ включен client_token. Мы успешно обменяли наш токен JWT на токен Vault!

{"request_id":"ac1baa56-fe90-a5c1-7bcb-f15937ad459c","lease_id":"","renewable":false,"lease_duration":0,"data":null,"wrap_info":null,"warnings":null,"auth":{"client_token":"s.0xCc7CljMW4Sloxy0Lmw7Ykn","accessor":"PkrNAHRNvwCxWINqMeKHaGKv","policies":["default"],"token_policies":["default"],"metadata":{"role":"demo"},"lease_duration":3600,"renewable":true,"entity_id":"f74a2743-fc8e-e3e9-6fbf-6b882cb5fbf2","token_type":"service"}}

Теперь вы можете использовать этот токен хранилища в заголовке X-Vault-Token и создавать запросы к хранилищу.

Вы также можете попробовать войти в Vault с помощью этого токена, если вы настроили параметр пути для Vault во время установки.

vault login s.0xCc7CljMW4Sloxy0Lmw7Ykn

Что дает успешный ответ ниже.

Success! You are now authenticated. The token information displayed below
is already stored in the token helper. You do NOT need to run "vault login"
again. Future Vault requests will automatically use this token.
Key                  Value
---                  -----
token                s.0xCc7CljMW4Sloxy0Lmw7Ykn
token_accessor       PkrNAHRNvwCxWINqMeKHaGKv
token_duration       56m53s
token_renewable      true
token_policies       ["default"]
identity_policies    []
policies             ["default"]
token_meta_role      demo

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

Такие подробности выходят за рамки этого блога.

Для такой конфигурации, а также для полного использования возможностей Vault, пожалуйста, обратитесь к документации Vault.

Заворачивать

Вначале мы понимали, что такое HashiCorp Vault и какие проблемы оно решает. В этом контексте мы говорили о том, насколько важна аутентификация для Vault. Затем мы перешли к интеграции HashiCorp Vault с WSO2 Identity Server с использованием аутентификации JWT. Мы настроили обе сущности так, чтобы Vault мог проверять входящие запросы входа в систему JWT, запрашивая открытые ключи от WSO2 IS. Затем мы создали роль в Vault и назначили ей ограничения аутентификации JWT. После этого мы успешно смогли войти в Vault, используя токен JWT ID, предоставленный WSO2 IS, и обменять его на токен Vault.

WSO2 Identity Server - это полностью расширяемое решение IAM с открытым исходным кодом, которое используется для объединения и управления удостоверениями в корпоративной среде и среде облачных сервисов. Вы можете попробовать это здесь.