Class: Peatio::Auth::JWTAuthenticator

Inherits:
Object
  • Object
show all
Defined in:
lib/peatio/auth/jwt_authenticator.rb

Overview

JWTAuthenticator used to authenticate user using JWT.

It allows configuration of JWT verification through following ENV variables (all optional):

  • JWT_ISSUER

  • JWT_AUDIENCE

  • JWT_ALGORITHM (default: RS256)

  • JWT_DEFAULT_LEEWAY

  • JWT_ISSUED_AT_LEEWAY

  • JWT_EXPIRATION_LEEWAY

  • JWT_NOT_BEFORE_LEEWAY

Examples:

Token validation

rsa_private = OpenSSL::PKey::RSA.generate(2048)
rsa_public = rsa_private.public_key

payload = {
  iat: Time.now.to_i,
  exp: (Time.now + 60).to_i,
  sub: "session",
  iss: "barong",
  aud: [
    "peatio",
    "barong",
  ],
  jti: "BEF5617B7B2762DDE61702F5",
  uid: "TEST123",
  email: "[email protected]",
  role: "admin",
  level: 4,
  state: "active",
}

token = JWT.encode(payload, rsa_private, "RS256")

auth = Peatio::Auth::JWTAuthenticator.new(rsa_public)
auth.authenticate!("Bearer #{token}")

See Also:

Instance Method Summary collapse

Constructor Details

#initialize(public_key, private_key = nil) ⇒ JWTAuthenticator

Creates new authenticator with given public key.



52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
# File 'lib/peatio/auth/jwt_authenticator.rb', line 52

def initialize(public_key, private_key = nil)
  @public_key = public_key
  @private_key = private_key

  @verify_options = {
    verify_expiration: true,
    verify_not_before: true,
    iss: ENV["JWT_ISSUER"],
    verify_iss: !ENV["JWT_ISSUER"].nil?,
    verify_iat: true,
    verify_jti: true,
    aud: ENV["JWT_AUDIENCE"].to_s.split(",").reject(&:empty?),
    verify_aud: !ENV["JWT_AUDIENCE"].nil?,
    sub: "session",
    verify_sub: true,
    algorithms: [ENV["JWT_ALGORITHM"] || "RS256"],
    leeway: ENV["JWT_DEFAULT_LEEWAY"].yield_self { |n| n.to_i unless n.nil? },
    iat_leeway: ENV["JWT_ISSUED_AT_LEEWAY"].yield_self { |n| n.to_i unless n.nil? },
    exp_leeway: ENV["JWT_EXPIRATION_LEEWAY"].yield_self { |n| n.to_i unless n.nil? },
    nbf_leeway: ENV["JWT_NOT_BEFORE_LEEWAY"].yield_self { |n| n.to_i unless n.nil? },
  }.compact

  @encode_options = {
    algorithm: @verify_options[:algorithms].first,
  }.compact
end

Instance Method Details

#authenticate!(token) ⇒ Hash

Decodes and verifies JWT. Returns payload from JWT or raises an exception

Raises:



86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/peatio/auth/jwt_authenticator.rb', line 86

def authenticate!(token)
  token_type, token_value = token.to_s.split(" ")

  unless token_type == "Bearer"
    raise(Peatio::Auth::Error, "Token type is not provided or invalid.")
  end

  decode_and_verify_token(token_value)
rescue => error
  case error
  when Peatio::Auth::Error
    raise(error)
  else
    raise(Peatio::Auth::Error, error.message)
  end
end

#encode(payload) ⇒ String

Encodes given payload and produces JWT.

Raises:

  • (ArgumentError)

    If no private key was passed to constructor.



109
110
111
112
113
# File 'lib/peatio/auth/jwt_authenticator.rb', line 109

def encode(payload)
  raise(::ArgumentError, "No private key given.") if @private_key.nil?

  JWT.encode(payload, @private_key, @encode_options[:algorithm])
end