【发布时间】:2020-06-13 15:14:51
【问题描述】:
使用 auth 和 JWT 制作了一个 ror api 来提供一个 react 应用程序。在开发环境(本地主机)中一切正常。一旦我部署到heroku,我就开始出现这个错误。我按照 heroku 的 rails 文档进行部署:https://devcenter.heroku.com/articles/getting-started-with-rails5
当我尝试“注册”或“签名”时,请求失败,状态码为 500。真正奇怪的是,在 heroku rails 控制台中创建了用户,但我没有在 json 中取回我的令牌。这是我的反应应用程序的调用:
axios.post('https://hidden-ocean-49877.herokuapp.com/signup', {withCredentials: true,
name: name, email: email, password: password, password_confirmation: passwordConfirmation})
.then(response => {
login(true);
tokenize(response.data.auth_token);
}).catch(error => console.log(error));
这是heroku日志中的日志:
2020-02-29T21:43:16.041318+00:00 heroku[router]: at=info method=POST path="/signup" host=hidden-ocean-49877.herokuapp.com request_id=7cd577ad-c7c5-4fa7-aa99-91b4b8e49772 fwd="189.214.5.88" dyno=web.1 connect=1ms service=977ms status=500 bytes=421 protocol=https
2020-02-29T21:43:16.038685+00:00 app[web.1]: I, [2020-02-29T21:43:16.038582 #4] INFO -- : [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772] Completed 500 Internal Server Error in 925ms (ActiveRecord: 29.5ms)
2020-02-29T21:43:16.039125+00:00 app[web.1]: F, [2020-02-29T21:43:16.039063 #4] FATAL -- : [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772]
2020-02-29T21:43:16.039179+00:00 app[web.1]: F, [2020-02-29T21:43:16.039120 #4] FATAL -- : [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772] TypeError (no implicit conversion of nil into String):
2020-02-29T21:43:16.039221+00:00 app[web.1]: F, [2020-02-29T21:43:16.039178 #4] FATAL -- : [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772]
2020-02-29T21:43:16.039264+00:00 app[web.1]: F, [2020-02-29T21:43:16.039226 #4] FATAL -- : [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772] app/lib/json_web_token.rb:9:in `encode'
2020-02-29T21:43:16.039264+00:00 app[web.1]: [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772] app/auth/authenticate_user.rb:9:in `call'
2020-02-29T21:43:16.039264+00:00 app[web.1]: [7cd577ad-c7c5-4fa7-aa99-91b4b8e49772] app/controllers/users_controller.rb:6:in `create'
上面描述的文件是这样的:
用户控制器
class UsersController < ApplicationController
skip_before_action :authorize_request, only: :create
def create
user = User.create!(user_params)
auth_token = AuthenticateUser.new(user.email, user.password).call
response = { message: Message.account_created, auth_token: auth_token }
json_response(response, :created)
end
private
def user_params
params.permit(
:name,
:email,
:password,
:password_confirmation
)
end
end
在 app/auth/authenticate_user.rb 中:
class AuthenticateUser
def initialize(email, password)
@email = email
@password = password
end
# Service entry point
def call
JsonWebToken.encode(user_id: user.id) if user
end
private
attr_reader :email, :password
def user
user = User.find_by(email: email)
return user if user && user.authenticate(password)
raise(ExceptionHandler::AuthenticationError, Message.invalid_credentials)
end
end
在 app/lib/json_web_token.rb 中:
class JsonWebToken
# secret to encode and decode token
HMAC_SECRET = Rails.application.secrets.secret_key_base
def self.encode(payload, exp = 24.hours.from_now)
# set expiry to 24 hours from creation time
payload[:exp] = exp.to_i
# sign token with application secret
JWT.encode(payload, HMAC_SECRET)
end
def self.decode(token)
# get payload; first index in decoded Array
body = JWT.decode(token, HMAC_SECRET)[0]
HashWithIndifferentAccess.new body
# rescue from all decode errors
rescue JWT::DecodeError => e
# raise custom error to be handled by custom handler
raise ExceptionHandler::InvalidToken, e.message
end
end
【问题讨论】:
标签: ruby-on-rails heroku axios