Authlogic ignoring password parameter - ruby-on-rails

Authlogic seems to be ignoring the password parameter when creating a new user. Here's my users_controller class:
class Api::V1::UsersController < ApplicationController
def create
#user = User.new(user_params)
respond_to do |format|
if #user.save
format.json { render :json => #user, :status => :created}
else
format.json { render :json => #user.errors, :status => :unprocessable_entity }
end
end
end
private
def user_params
params.require(:user).permit(:username, :email, :password)
end
end
And my user model:
class User < ActiveRecord::Base
acts_as_authentic do |c|
c.require_password_confirmation = false
end
end
When I send a POST request to /api/v1/users/ with a username, email and password parameter, authlogic says that the password cannot be blank even though it isn't. Here's whats printed out by rails:
Started POST "/api/v1/users/" for 127.0.0.1 at 2013-06-22 00:03:30 -0400
Processing by Api::V1::UsersController#create as */*
Parameters: {"email"=>"someemail#website.com", "password"=>"[FILTERED]", "username"=>"myUser", "user"=>{"username"=>"myUser", "email"=>"someemail#website.com"}}
(0.2ms) BEGIN
User Exists (0.4ms) SELECT 1 AS one FROM "users" WHERE LOWER("users"."email") = LOWER('someemail#website.com') LIMIT 1
User Exists (0.2ms) SELECT 1 AS one FROM "users" WHERE LOWER("users"."username") = LOWER('myUser') LIMIT 1
User Exists (0.3ms) SELECT 1 AS one FROM "users" WHERE "users"."persistence_token" = '7b72bab3627914d33e83e4efe1c5a9dab190750efb227698c8b5b6be7a7ccf118160d8e12623078543e0f4e5f31eb30828799cb0d97fb2af195daee894c79902' LIMIT 1
(0.2ms) ROLLBACK
Completed 422 Unprocessable Entity in 33ms (Views: 0.2ms | ActiveRecord: 3.2ms)
I'm using the latest authlogic and Ruby 2/Rails 4.

Take a look at an excerpt from Rails log:
{"email"=>"someemail#website.com", "password"=>"[FILTERED]", "username"=>"myUser", "user"=>{"username"=>"myUser", "email"=>"someemail#website.com"}}
It looks like you send slightly wrong parameters. To be recognized by Authlogic, password parameter should go under user key in parameters hash. I.e. that line from Rails log should look like this (pay attention to the end of string):
{"email"=>"someemail#website.com", "password"=>"[FILTERED]", "username"=>"myUser", "user"=>{"username"=>"myUser", "email"=>"someemail#website.com", "password" => "[FILTERED]"}}
To fix it, you can do a hack like this:
private
def user_params
params.require(:user).permit(:username, :email).merge(:password => :password)
end
Alternatively, you can adjust the parameters sent from the client side (for example, using user[password] parameter's name instead of just password when sending HTTP POST request).

try this out:-
acts_as_authentic do |config|
config.check_passwords_against_database = false
config.validate_password_field = false
config.crypted_password_field = false
end

Related

ActionController::ParameterMissing (param is missing or the value is empty: account)

Gurus,
Need help with RoR API
I see all the required parameters are being sent, however the server does not like one or some of it.
controller:
def create
#account = Account.new(account_params)
if #account.save
render json: #account, status: :created, location: #account
else
render json: #account.errors, status: :unprocessable_entity
end
end
def account_params
params.require(:account).permit(:client_id, :currency_id, :name, :type, :institution)
end
call looks like this:
Started POST "/accounts?name=TD-Trading&currency_id=1&institution=TD%20Waterhouse&type=Investment&client_id=1" for ::1 at 2020-11-27 01:16:08 -0700
Processing by AccountsController#create as /
Parameters: {"name"=>"TD-Trading", "currency_id"=>"1", "institution"=>"TD Waterhouse", "type"=>"Investment", "client_id"=>"1"}
Client Load (0.4ms) SELECT "clients".* FROM "clients" WHERE "clients"."email" = $1 ORDER BY "clients"."id" ASC LIMIT $2 [["email", "akaghzi#gmail.com"], ["LIMIT", 1]]
Completed 400 Bad Request in 271ms (ActiveRecord: 0.4ms | Allocations: 1706)
ActionController::ParameterMissing (param is missing or the value is empty: account):
app/controllers/accounts_controller.rb:55:in account_params' app/controllers/accounts_controller.rb:21:in create'
This piece of code:
def account_params
params.require(:account).permit(:client_id, :currency_id, :name, :type, :institution)
end
Is saying that it expects an account hash with inside that the attributes. Your logs shows you send all attributes not wrapped inside an account hash.
You can solve this by wrapping the params inside a account hash or remove the require(:account) part from the account_params.

Date failing to update, but returning true for Update (Rails ActiveRecord)

I have a Rails model called user that has a birthday field with type date in Postgres.
My first issue is that I'm not sure how to update the value of a user. If I pass in a string like "10/10/1980", it does not update.
The second issue is that even when the birthday is not updated, Rails returns true for the User.update(user_params) action
My two questions:
How can I update a date field?
How can I make sure that rails throws an error if an incorrect date is passed in?
How can I update a date field?
Update method from controller below. Fairly standard from scaffolding.
# PATCH/PUT /users/1
# PATCH/PUT /users/1.json
def update
respond_to do |format|
puts(user_params)
if #user.update(user_params)
format.html { redirect_to #user, notice: 'User was successfully updated.' }
format.json { render :show, status: :ok, location: #user }
else
format.html { render :edit }
format.json { render json: #user.errors, status: :unprocessable_entity }
end
end
end
Edit: Params:
def user_params
params.require(:user)
.permit(:points, :payment_option, :first_name, :last_name,
:payment_email, :phone_number, :facebook_id, :profile_pic_url,
:locale, :timezone, :gender, :email, :country, :city,
:age_group, :birthday, :employment_status, :occupation,
:education_level, :income_bracket)
end
Rails log (note that I added a puts(user_params) after the update statement.
Started PATCH "/api/v1/users/1" for 127.0.0.1 at 2017-12-07 19:16:37 +0800
Processing by UsersController#update as JSON
Parameters: {"user"=>{"birthday"=>"12dsafkljfsldk"}, "id"=>"1"}
User Load (0.3ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 LIMIT $2 [["id", 1], ["LIMIT", 1]]
Can't verify CSRF token authenticity.
{"birthday"=>"10/10/1900"}
(0.2ms) BEGIN
(0.1ms) COMMIT
Rendering users/show.json.jbuilder
Rendered users/_user.json.jbuilder (0.6ms)
Rendered users/show.json.jbuilder (1.6ms)
Completed 200 OK in 31ms (Views: 5.9ms | ActiveRecord: 3.1ms)
I was hoping that I could use before_update to parse the date string into a Date object before saving, but it doesn't look like self.birthday is even showing up in the model.
Place this line in your ApplicationController
protect_from_forgery with: :null_session, if: Proc.new { |c| c.request.format == 'application/json' }
If it doesn't work then. Try to skip the action
skip_before_action :verify_authenticity_token

Carrierwave Cloudinary image upload works but null values returned right after upload

First of all, let me say - Cloudinary and Carrierwave are both amazing. Carrierwave, super simple image uploading.
Cloudinary offering free plan with 10GB of storage, very generous.
My Problem
I'm basically testing Cloudinary with Carrierwave.
I've got them both to work in the sense that when I create a new user (or update existing one) with an image file attachment using Postman app on my Mac, the images actually do get saved on the Cloudinary CDN and the URL values in my database afterwards but the JSON response values for avatar are null:
The problem you can see in the returned response, the avatar field all contains null values.
However, when I view my index action of my UsersController in my browser, the avatar values show up:
Any ideas what might be causing this issue?
Could it be that by the time the User entity is created/updated, Cloudinary hasn't finish uploading the info quite in time yet and so Carrierwave saves the value as null and later, when Cloudinary has finished processing, it makes a callback to Carrierwave to update the values?
I'm not doing anything fancy, just basic code:
UsersController
class UsersController < ApplicationController
def index
users = User.all
render json: users
end
def create
user = User.new(user_params)
if user.save
render json: user, status: :created
else
render json: user.errors, status: :unprocessable_entity
end
end
def update
# simple test, change to params id later
user = User.where(id: 3)
if user.update(user_params)
render json: user, status: :ok
else
render json: user.errors, status: :unprocessable_entity
end
end
private
def user_params
params.permit(:id, :first_name, :last_name, :email, :password, :password_confirmation, :avatar)
end
end
Mac Terminal output
Processing by UsersController#update as */*
Parameters: {"avatar"=>#<ActionDispatch::Http::UploadedFile:0x007fa39caad5b0 #tempfile=#<Tempfile:/var/folders/sk/tjj1jxkd62ngkhfxmh8yc04r0000gn/T/RackMultipart20170918-2307-lw2ga8.jpg>, #original_filename="doc.jpg", #content_type="image/jpeg", #headers="Content-Disposition: form-data; name=\"avatar\"; filename=\"doc.jpg\"\r\nContent-Type: image/jpeg\r\n">, "first_name"=>"Emmett", "last_name"=>"Brown", "id"=>"3"}
Can't verify CSRF token authenticity.
User Load (0.1ms) SELECT "users".* FROM "users" WHERE "users"."id" = ? [["id", 3]]
(0.1ms) begin transaction
SQL (0.4ms) UPDATE "users" SET "first_name" = ?, "avatar" = ?, "updated_at" = ? WHERE "users"."id" = ? [["first_name", "Emmett"], ["avatar", "kzc9ghjln9gfoowhzudi.png"], ["updated_at", "2017-09-18 02:55:59.269637"], ["id", 3]]
SQL (0.1ms) UPDATE "users" SET "avatar" = 'image/upload/v1505703360/kzc9ghjln9gfoowhzudi.png' WHERE "users"."id" = ? [["id", 3]]
(2.7ms) commit transaction
[active_model_serializers] Rendered ActiveModel::Serializer::CollectionSerializer with ActiveModelSerializers::Adapter::JsonApi (3.52ms)
Completed 200 OK in 3259ms (Views: 14.9ms | ActiveRecord: 4.0ms)
Hopefully it's some silly mistake or quick configuration option that I am not aware of and not some bug on either Carrierwave or Cloudinary's side.
Has anyone encountered this problem before?
Umm...okay, I think I found a solution/work around?
Maybe some Rails or Carrierwave devs can explain to me why I need to do this to fix the problem:
def create
user = User.new(user_params)
if user.save
# -------------------------------------------------
# NEED TO RELOAD FOR CARRIERWAVE
# -------------------------------------------------
user.reload
render json: user, status: :created
else
render json: user.errors, status: :unprocessable_entity
end
end
Seems like an extra step which can impact system performance.
I shouldn't need to do this right?

Unable to process POST request for create action in controller

I am using paperclip-5.0.0, and Rails 5.0.2.This is my code in controller
class PawsController < ApplicationController
before_action :set_paw, only: [:show, :edit]
def index
#paws = Paw.all
end
def show
end
def new
#paw = Paw.new
end
def edit
end
def create
#paw = Paw.new(paw_params)
respond_to do |format|
if #paw.save
format.html { redirect_to #paw, notice: 'Paw was successfully created.' }
format.json { render :show, status: :created, location: #paw }
else
format.html { render :new }
format.json { render json: #paw.errors, status: :unprocessable_entity }
end
end
end
private
# Use callbacks to share common setup or constraints between actions.
def set_paw
#paw = Paw.find(params[:id])
end
def paw_params
params.require(:paw).permit(:avatar,:name) if params[:avatar]
end
end
Avatar here is the column for paw which stores images.In model I have added required validations for paperclip and validation for presence of name.
Problem: In rails console I am successfully able to open the image file from my computer and add it to the paw model i.e. #paw.save returns true in console, but in the browser it redirects me to the new_paw_url with two errors.
Name can't be blank. and
Avatar can't be blank.
There are no exceptions or errors thrown in between the process.I have no idea how should I fix this.
ActiveRecord::SchemaMigration Load (0.2ms) SELECT "schema_migrations".* FROM "schema_migrations"
Processing by PawsController#create as HTML
Parameters: {"utf8"=>"✓","authenticity_token"=>"zKpb2XFEG4FqX3aVQx9oyyGI9x2NpmF+lmt4eZy/3p3VZr2eWYvHLaEjS5AvisJ6iEbRm61SJkJSuTpMx4c0JA==", "paw"=>{"name"=>"Sheru", "gender"=>"Male", "breed"=>"", "dob"=>"", "avatar"=>#<ActionDispatch::Http::UploadedFile:0x005608576e1f30 #tempfile=#<Tempfile:/tmp/RackMultipart20170323-14343-1o95nqx.jpg>, #original_filename="art.jpg", #content_type="image/jpeg", #headers="Content-Disposition: form-data; name=\"paw[avatar]\"; filename=\"art.jpg\"\r\nContent-Type: image/jpeg\r\n">}, "commit"=>"Upload"}
(0.1ms) begin transaction
(0.1ms) rollback transaction
(0.1ms) begin transaction
(0.1ms) rollback transaction
Rendering paws/new.html.erb within layouts/application
Rendered paws/_form.html.erb (15.8ms)
Rendered paws/new.html.erb within layouts/application (17.3ms)
Rendered layouts/_navbar.html.erb (0.6ms)
Completed 200 OK in 326ms (Views: 287.5ms | ActiveRecord: 2.0ms)
Feel free to ask for any other code snippets from me.
Your paw_params method is breaking it. Remove the if statement and it should work. The problem you're having is that the params you're recieving through your controller are nested in the params[paw] hash and not the params hash. Your paw_params if statement should be
params.require(:paw).permit(:avatar,:name) if params[:paw][:avatar]
Look at the console of your params hash and you'll see that Rails will nest all params submitted via a form helper within the class name of the object. In this case it's paw.
"paw"=>{"name"=>"Sheru", "gender"=>"Male", "breed"=>"", "dob"=>"", "avatar"=>#<ActionDispatch::Http::UploadedFile:0x005608576e1f30
More obviously:
params[:name] #nil
params[:paw][:name] #"Sheru"
Also, it's not a good practice to add conditionals for strong_paramaters based on the presence of certain attributes. If someone submits a name without an avatar, the name wont be permitted due to strong_parameters but would give the user poor feedback. Instead you should use validations in your Paw model that requires the presence of both the name and avatar.

Rails Rest-Post Params hash not written

I m building my first REST API using Rails and have a simple question which I am unable to solve.
Basically i am not able to write a params hash into the database from a http PUSH request.
I have the following user controller under the Api namespace with the create action.
class Api::UserController < ApplicationController
http_basic_authenticate_with :name => "test", :password => "test"
skip_before_action :verify_authenticity_token
def create
#user = User.create(params[:user])
respond_to do |format|
if #user.save
format.json{render json: #user, status: :created, location: #user} #render create full response
else
format.json{render json: #user.errors, status: :unprocessable_entity}
end
end
end
end
The route to this action is
POST /api/user(.:format) api/user#create{:format=>"json"}
The user model has a name and a address string not contained.
To test the REST call i setup the firefox plugins RESTeasy and RESTclient
with this URL http://localhost:3000/api/user/
and this body
{
"name": "timoteo",
"address": "berlin"
}
So far so good. Now after sending this package Webrick gives me this output:
Started POST "/api/user" for ::1 at 2015-08-03 17:06:50 +0200
Processing by Api::UserController#create as JSON
Parameters: {"name"=>"timoteo", "address"=>"berlin"}
(1.2ms) BEGIN
SQL (0.6ms) INSERT INTO "users" ("created_at", "updated_at") VALUES ($1, $2) RETURNING "id" [["created_at", "2015-08-03 15:06:50.646169"], ["updated_at", "2015-08-03 15:06:50.646169"]]
(42.8ms) COMMIT
(0.3ms) BEGIN
(0.3ms) COMMIT
Completed 201 Created in 66ms (Views: 1.4ms | ActiveRecord: 48.1ms)
neglecting the two parameter and an empty empty record like this one gets stored in the database(also the REST clients show me the same)
{"id":19,"name":null,"address":null,"created_at":"2015-08-03T15:06:50.646Z","updated_at":"2015-08-03T15:06:50.646Z"}
Can someone give me a hint what might have gone wrong during the way. I assume it is something with the params hash but i could not figure it out yet.
Add validation to your model:
class User < ActiveRecord::Base
validates_presence_of :name
validates_presence_of :address
end
That will disallow saving record with blank attributes.
Then, change your #save call to #persisted? in your controller (because record is created immediately after #create is called, it is already saved or failed)
if #user.persisted?
format.json{render json: #user, status: :created, location: #user} #render create full response
else
format.json{render json: #user.errors, status: :unprocessable_entity}
end
UPD. You could also benefit from whitelisting parameters which you accept:
#user = User.create(params.require(:name, :address))
This way Rails will respond with error, saying parameter is missing, and will not assign any other attributes to user (which you don't want to be assigned).
Your params of { "name": "timoteo", "address": "berlin" } are incorrect when your user creation is #user = User.create(params[:user])
You params should look more like:{ "user": { "name": "timoteo", "address": "berlin" } } because you're accessing params[:user] so the user attributes need to belong to the user section of your params.
Adding Validations may help if its incorrect to save a User with no name/address too.
class User < ActiveRecord::Base
validates :name, presence: true
validates :address, presence: true
# etc...
end

Resources