我正在尝试为我的rails应用程序设置用户注册端点,以便我可以在iOS再现中访问应用程序功能。我已经开始使用命名空间我的API,到目前为止已经设法使用Devise和JWT进行用户身份验证。
这很棒,但我还需要能够通过API注册用户。坦率地说,我不知道如何正确实现这一点。多个GOogle版本会显示outdated articles,使用deprecated token authenticatable,或者从未接听过。
以下是我认为最符合此问题的代码:
override func viewDidLoad()
{
super.viewDidLoad()
FIRDatabase.database().reference(withPath: "Main data").child("Home Image URLs").observeSingleEvent(of: .value, with: { (snapshot) in
if let snapString = snapshot.value as? String {
self.imageURLsVAR = snapString
self.imageURLs = self.imageURLsVAR.components(separatedBy: ",")
// self.label.text = String(self.imageURLs[1])
for i in 0..< imageURLs.count-1{
let imageview = UIImageView()
// imageview.image = homeImages[i]
dlURL = String(imageURLs[i])
DLImageLoader.sharedInstance().image(fromUrl: String(imageURLs[i]), imageView: imageview)
imageview.contentMode = .scaleAspectFit
let xPosition = self.view.frame.width * CGFloat(i)
imageview.frame = CGRect(x: xPosition, y: 0, width: self.imgScrollView.frame.width, height: self.imgScrollView.frame.height)
imgScrollView.contentSize.width = imgScrollView.frame.width * CGFloat(i + 1)
imgScrollView.addSubview(imageview)
view.sendSubview(toBack: imgScrollView)
}
}
}) { (error) in
print(error.localizedDescription)
}
}
namespace :api do
namespace :v1 do
devise_for :users, controllers: { registrations: 'api/v1/registrations' }
resources :classrooms
resources :notifications
end
end
end
class Api::V1::RegistrationsController < Devise::RegistrationsController
respond_to :json
def create
if params[:email].nil?
render :status => 400,
:json => {:message => 'User request must contain the user email.'}
return
elsif params[:password].nil?
render :status => 400,
:json => {:message => 'User request must contain the user password.'}
return
end
if params[:email]
duplicate_user = User.find_by_email(params[:email])
unless duplicate_user.nil?
render :status => 409,
:json => {:message => 'Duplicate email. A user already exists with that email address.'}
return
end
end
@user = User.create(user_params)
if @user.save!
render :json => {:user => @user}
else
render :status => 400,
:json => {:message => @user.errors.full_messages}
end
end
private
# Never trust parameters from the scary internet, only allow the white list through.
def user_params
devise_parameter_sanitizer.permit(:sign_up, keys: [:attribute, :first_name, :last_name, :access_code])
end
end
http://localhost:3000/api/v1/users
我非常感谢任何帮助,因为我渴望学习更多(并让它发挥作用!)。
这是我在发出生成用户的帖子请求后在服务器上得到的内容......
{
"message": [
"Email can't be blank",
"Password can't be blank",
"Access code is invalid [Beta]."
]
}
Started POST "/api/v1/users" for 127.0.0.1 at 2017-02-22 09:22:11 -0800
Processing by Api::V1::RegistrationsController#create as */*
Parameters: {"user"=>{"email"=>"user@sampleapi.com", "password"=>"[FILTERED]", "password_confirmation"=>"[FILTERED]", "access_code"=>"uiux"}}
User Load (0.4ms) SELECT "users".* FROM "users" WHERE "users"."email" IS NULL LIMIT $1 [["LIMIT", 1]]
Completed 400 Bad Request in 2ms (Views: 0.2ms | ActiveRecord: 0.4ms)
我很确定我此时的主要问题是我的参数的格式,因此任何正确方向的推动都会很棒。我确实找到了this post,但我觉得它有点难以理解它们的API工作原理......
答案 0 :(得分:4)
这是2个解决方案,选择你喜欢的解决方案。
覆盖devise_parameter_sanitizer:
DbDataReader
覆盖sign_up_params:
class ApplicationController < ActionController::Base
protected
def devise_parameter_sanitizer
if resource_class == User
User::ParameterSanitizer.new(User, :user, params)
else
super # Use the default one
end
end
end
如果您深入Devise ParameterSanitizer,则由于您的路线,resource_name将为def sign_up_params
params.require(:user).permit(:email, :password, :password_confirmation)
end
,而不仅仅是:api_v1_user
:
:user
错误resource_name将导致namespace :api do
namespace :v1 do
devise_for :users, controllers: { registrations: 'api/v1/registrations' }
end
end
始终返回空哈希sign_up_params
答案 1 :(得分:0)
你为什么不尝试这样的事情:
user = User.create(sign_up_params)
if user.save
render status: 200, json: @controller_blablabla.to_json
else
render :status => 400,
:json => {:message => @user.errors.full_messages}
end
甚至更好。您可以使用tiddle gem之类的东西来提高会话的安全性:
respond_to :json
def create
user = User.create(sign_up_params)
if user.save
token = Tiddle.create_and_return_token(user, request)
render json: user.as_json(authentication_token: token, email:
user.email), status: :created
return
else
warden.custom_failure!
render json: user.errors, status: :unprocessable_entity
end
end
您可以使用httpie --form
发出请求:
http --form POST :3000/users/sign_up Accept:'application/vnd.sign_up.v1+json' user[email]='he@llo.com' user[username]='hello' user[password]='123456789' user[password_confirmation]='123456789'
不要忘记:
def sign_up_params
params.require(:user).permit(:username, :email, :password, :password_confirmation)
end
我不知道自己错过了什么,让我知道如果我错了或出了什么问题我都没有意识到!
问候!