Я использую Auth0 для аутентификации в моем веб-приложении. Я использую ASP.NET Core v1.0.0 и Angular 2 rc5, и я мало знаю об аутентификации / безопасности в целом.

В документации Auth0 для ASP.NET Core Web Apiесть два варианта для алгоритма JWT: RS256 и HS256. Это может быть глупый вопрос, но:

В чем разница между RS256 и HS256? Какие варианты использования (если применимо)?

Ответы (4)

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

  • RS256 (подпись RSA с SHA-256) - это асимметричный алгоритм , который использует пару открытого / закрытого ключей: у поставщика удостоверений есть закрытый (секретный ) ключ, используемый для генерации подписи, а потребитель JWT получает открытый ключ для проверки подписи. Поскольку открытый ключ, в отличие от закрытого, не требует защиты, большинство поставщиков удостоверений делают его легко доступным для получения и использования потребителями (обычно через URL-адрес метаданных).

  • HS256 (HMAC с SHA-256), с другой стороны, включает комбинацию хеш-функции и одного (секретного) ключа, который используется совместно двумя сторонами, используемыми для генерации хеш, который будет служить подписью. Поскольку один и тот же ключ используется как для генерации подписи, так и для ее проверки, необходимо позаботиться о том, чтобы ключ не был скомпрометирован.

Если вы будете разрабатывать приложение, использующее JWT, вы можете безопасно использовать HS256, потому что у вас будет контроль над тем, кто использует секретные ключи. Если, с другой стороны, у вас нет контроля над клиентом или у вас нет возможности защитить секретный ключ, RS256 будет более подходящим вариантом, поскольку потребителю нужно знать только открытый (общий) ключ.

Поскольку открытый ключ обычно предоставляется из конечных точек метаданных, клиенты могут быть запрограммированы на автоматическое получение открытого ключа. В этом случае (как в случае с библиотеками .Net Core) у вас будет меньше работы по настройке (библиотеки получат открытый ключ с сервера). С другой стороны, симметричные ключи необходимо обменивать по внешнему каналу (обеспечивая безопасный канал связи) и обновлять вручную при смене ключа подписи.

Auth0 предоставляет конечные точки метаданных для протоколов OIDC, SAML и WS-Fed, из которых можно получить открытые ключи. Вы можете увидеть эти конечные точки в разделе «Расширенные настройки» клиента.

Конечная точка метаданных OIDC, например, принимает форму https: // {account domain} /. Well-known / openid-configuration. Если вы перейдете по этому URL-адресу, вы увидите объект JSON со ссылкой на https: // {account domain} /. Well-known / jwks.json, который содержит открытый ключ (или ключи) учетной записи, представленной как JSON Web Key Set.

Если вы посмотрите образцы RS256, вы увидите, что вам не нужно нигде настраивать открытый ключ: он автоматически извлекается фреймворком.

Есть разница в производительности.

Проще говоря, HS256 примерно на 1 порядок быстрее, чем RS256 для проверки, но примерно на 2 порядка быстрее, чем RS256 для выдачи (подписи).

 640,251  91,464.3 ops/s
  86,123  12,303.3 ops/s (RS256 verify)
   7,046   1,006.5 ops/s (RS256 sign)

Не зацикливайтесь на реальных числах, просто думайте о них по отношению друг к другу.

[Program.cs]

класс Программа
{
    static void Main (строка [] аргументы)
    {
        foreach (продолжительность var в новом [] {1, 3, 5, 7})
        {
            var t = TimeSpan.FromSeconds (продолжительность);

            byte [] publicKey, privateKey;

            используя (var rsa = new RSACryptoServiceProvider ())
            {
                publicKey = rsa.ExportCspBlob (ложь);
                privateKey = rsa.ExportCspBlob (правда);
            }

            byte [] key = новый байт [64];

            используя (var rng = new RNGCryptoServiceProvider ())
            {
                rng.GetBytes (ключ);
            }

            var s1 = новый секундомер ();
            var n1 = 0;

            используя (var hs256 = new HMACSHA256 (key))
            {
                в то время как (s1.Elapsed 

В криптографии используются два типа алгоритмов:

Symmetric algorithms

A single key is used to encrypt data. When encrypted with the key, the data can be decrypted using the same key. If, for example, Mary encrypts a message using the key "my-secret" and sends it to John, he will be able to decrypt the message correctly with the same key "my-secret".

Асимметричные алгоритмы

Два ключа используются для шифрования и дешифрования сообщений. В то время как один ключ (открытый) используется для шифрования сообщения, другой ключ (закрытый) может использоваться только для его расшифровки. Таким образом, Джон может сгенерировать как открытый, так и закрытый ключи, а затем отправить Мэри только открытый ключ, чтобы зашифровать ее сообщение. Сообщение можно расшифровать только с помощью закрытого ключа.

Сценарий HS256 и RS256

Эти алгоритмы НЕ используются для шифрования / дешифрования данных. Скорее они используются для проверки происхождения или подлинности данных. Когда Мэри нужно отправить открытое сообщение Джону, и ему нужно убедиться, что сообщение действительно от Мэри, можно использовать HS256 или RS256.

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

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

короткий ответ, специфичный для OAuth2,

  • HS256 пользовательский клиентский секрет для генерации подписи токена, и тот же секрет требуется для проверки токена в серверной части. Таким образом, у вас должна быть копия этого секрета на вашем внутреннем сервере для проверки подписи.
  • RS256 использовать шифрование с открытым ключом для подписи токена. Подпись (хэш) будет создана с использованием закрытого ключа, и она может быть проверена с помощью открытого ключа. Таким образом, нет необходимости в закрытом ключе или секрете клиента для хранения на внутреннем сервере, но внутренний сервер будет извлекать открытый ключ из URL-адреса конфигурации openid в вашем клиенте (https: // [tenant] /.well- known / openid-configuration) для проверки токена. Параметр KID внутри access_toekn будет использоваться для определения правильного ключа (общедоступного) из конфигурации openid.

2022 WebDevInsider