【问题标题】:ruby-jwt encode, decode with RS256 algorithmruby-jwt 编码,使用 RS256 算法解码
【发布时间】:2018-03-06 04:45:24
【问题描述】:

在 RSA256 算法中编码和解码令牌时,我们似乎总是初始化和使用相同的私钥:

payload = {:data => 'test'}
rsa_private = OpenSSL::PKey::RSA.generate 2048
rsa_public = rsa_private.public_key

token = JWT.encode payload, rsa_private, 'RS256'
# eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiJ9.eyJ0ZXN0IjoiZGF0YSJ9.c2FynXNyi6_PeKxrDGxfS3OLwQ8lTDbWBWdq7oMviCy2ZfFpzvW2E_odCWJrbLof-eplHCsKzW7MGAntHMALXgclm_Cs9i2Exi6BZHzpr9suYkrhIjwqV1tCgMBCQpdeMwIq6SyKVjgH3L51ivIt0-GDDPDH1Rcut3jRQzp3Q35bg3tcI2iVg7t3Msvl9QrxXAdYNFiS5KXH22aJZ8X_O2HgqVYBXfSB1ygTYUmKTIIyLbntPQ7R22rFko1knGWOgQCoYXwbtpuKRZVFrxX958L2gUWgb4jEQNf3fhOtkBm1mJpj-7BGst00o8g_3P2zHy-3aKgpPo1XlKQGjRrrxA
puts token

decoded_token = JWT.decode token, rsa_public, true, { :algorithm => 'RS256' }

# Array
# [
#   {"data"=>"test"}, # payload
#   {"alg"=>"RS256"} # header
# ]
puts decoded_token

但是在 Rails 5.1 应用程序中最好的方法是什么?

【问题讨论】:

  • 您的意思是,您想在每次使用时生成不同的密钥?
  • @ben,不,相反。我以前使用过 HMAC,可以只使用 Rails 生成的密钥。使用 RSA256 就不同了。我总是必须使用相同的私钥来编码和解码令牌。这就是为什么我要问并想知道在 Rails 中使用它是否有一些提示和技巧,因为我没有提供私钥并且必须自己创建它:OpenSSL::PKey::RSA.generate 2048
  • 否则,如果你创建一个新的 rsa 私钥并尝试解码之前生成的 rsa 密钥创建的令牌,你会得到JWT::VerificationError: Signature verification raised
  • 我知道。我还是不明白你的意思对不起
  • 为什么不把 KEY=OpenSSL::PKey::RSA.generate(2048) 放在初始化器中?

标签: ruby-on-rails jwt


【解决方案1】:

我想出了如何解决这个问题。 所以我有一个类JsonWebToken,有2个类方法:encodedecode定义如下:

class JsonWebToken

  ALGO = 'RS256'

  class << self

    def encode(payload, exp = 2.hours.from_now)
      # set expiry to 2 hours from creation time
      payload[:exp] = exp.to_i
      JWT.encode(payload, private_key, ALGO)
    end

    def decode(token)
      body = JWT.decode(token, private_key.public_key, true, algorithm: ALGO)[0]
      HashWithIndifferentAccess.new body
      # rescue from expiry exception
    rescue JWT::ExpiredSignature, JWT::VerificationError => e
      # raise custom error to be handled by custom handler
      raise ExceptionHandler::ExpiredSignature, e.message
    end  

    private

      def private_key
        @rsa_private ||= OpenSSL::PKey::RSA.generate 2048
      end
  end

end

如果需要,我只是使用另一种私有静态方法来生成 rsa 私钥。

【讨论】:

  • 非常有帮助。这行得通。谢谢你。问题:你在其他地方使用@rsa_private 吗?
  • @Kobi:不,我不会在任何地方使用@rsa_private
  • 但是,如果您的 Web 服务器在多个实例上运行,那么每个实例现在都使用不同的私钥。如果浏览器并不总是连接到同一个服务器实例(粘性会话),则由服务器实例 A 创建的 jwt 在服务器实例 B 上将无效。
猜你喜欢
  • 2020-04-25
  • 1970-01-01
  • 2018-08-26
  • 2019-04-06
  • 2021-10-31
  • 2018-04-12
  • 2017-02-08
  • 2020-05-15
  • 2021-01-04
相关资源
最近更新 更多