Ошибка воспроизведения инструкций Auth0 в «Ruby On Rails API: аутентификация» - PullRequest
3 голосов
/ 04 августа 2020

Я успешно использовал быстрый старт «Ruby On Rails API: Authentication» . Создал API, и все работает нормально. Затем я попытался воссоздать код, но включив все это в существующее приложение Rails, и получил ошибку.

Демонстрация (работавшая для меня раньше) включает этот вызов гема JWT:

JWT.decode(token, nil, # <----
    true, # Verify the signature of this token
    algorithm: "RS256",
    iss: "https://" + ENV["AUTH0_DOMAIN"],
    verify_iss: true,
    aud: ENV["AUTH0_AUDIENCE"],
    verify_aud: true)

Второй параметр с назначенным nil в демонстрации работает, но в моем проекте приводит к ошибке JWT, понимая, что параметр, используемый для public_key, не должен быть нулевым. Но в демонстрации он равен нулю и работает (ОБНОВЛЕНИЕ: сообщение nil, похоже, исходит из ссылки на другой объект). Я вроде новичок ie с JWT имеет значение.

Сообщение об ошибке:

undefined method `verify' for nil:NilClass
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/security_utils.rb:20:in `verify_rsa'

-------------------------------
Backtrace:
-------------------------------

  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/security_utils.rb:20:in `verify_rsa'
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/algos/rsa.rb:15:in `verify'
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/signature.rb:44:in `verify'
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/decode.rb:42:in `verify_signature'
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt/decode.rb:26:in `decode_segments'
  /usr/local/bundle/gems/jwt-2.2.1/lib/jwt.rb:28:in `decode'
  /api/lib/json_web_token.rb:10:in `verify'
  /api/app/controllers/concerns/secured.rb:71:in `auth_token'
  /api/app/controllers/concerns/secured.rb:50:in `authenticate_request!'

json_web_token.rb и secured.rb идентичны образцу. jwt-2.2.1 это одна и та же версия гема, используемая в обеих средах.

Единственное различие, которое я обнаружил между средами демонстрации и моего унаследованного проекта, - это версия Rails, 5 в демонстрации и 4.x в моей . Я не могу выполнить обновление прямо сейчас, поэтому, если вы думаете, что в другом случае я делаю неправильно, это было бы полезно.

Обновление 2: включая образец кода

I Я включаю сюда код для метода jwks_ha sh, он одинаков для обеих сред. Я просто добавил к оригиналу строки логгера. Вы можете увидеть различия в выводе для обеих сред ниже.

def self.jwks_hash
    Rails.logger.warn '---> hashing'
    Rails.logger.warn "https://#{Rails.application.secrets.auth0_domain}/.well-known/jwks.json"
    jwks_raw = Net::HTTP.get URI("https://#{Rails.application.secrets.auth0_domain}/.well-known/jwks.json")
    Rails.logger.warn jwks_raw
    jwks_keys = Array(JSON.parse(jwks_raw)['keys'])
    Rails.logger.warn '---> jwks_keys'
    Rails.logger.warn jwks_keys  # Check output of this below ?
    Hash[
      jwks_keys
      .map do |k|
        [
          k['kid'],
          OpenSSL::X509::Certificate.new(
            Base64.decode64(k['x5c'].first)
          ).public_key
        ]
      end
    ]
  end

Вывод в рабочей демонстрации:

W, [...]  WARN -- : [{"alg"=>"RS256", "kty"=>"RSA", "use"=>"sig", "n"=>"yDsoJbr45jlrCDQSu8X6ZAko......"]}]

W, [...]  WARN -- : {"alg"=>"RS256", "typ"=>"JWT", "kid"=>"YHEH94lH9itYZUhLx3hee"}

Вывод в моем проекте:

W, [...]  WARN -- : [{"alg"=>"RS256", "kty"=>"RSA", "use"=>"sig", "n"=>"yDsoJbr45jlrCDQSu8X6ZAko......"]}]

W, [...]  WARN -- : [{"alg"=>"RS256", "kty"=>"RSA", "use"=>"sig", "n"=>"yDsoJbr45jlrCDQSu8X6ZAko......"]}]

Второй элемент - это единственная разница между прогонами, которые я смог найти.

1 Ответ

1 голос
/ 06 августа 2020

Демонстрация извлекает ключ publi c в функции self.jwks_hash, а ключ publi c выглядит как nil при просмотре файла с ошибкой security_util.rb . Таким образом, похоже, вам не хватает шага для получения ключа publi c.

Когда вы кодируете с помощью RS256 или другого алгоритма, вам нужно декодировать с помощью ключа. Только когда вы используете 'none', вам не нужен ключ для декодирования. Подробнее см. в документации .

...