Fetch the Password and confirmation field of a Model object in Rails - ruby-on-rails

Is there any way to fetch the password and password_confirmation field of a Model object in Rails.? Say for example, I have an user object
user = User.find(1)
Now, I want to fetch the value of the password field like this.
password = user.password
confirmation = user.password_confirmation.
I tried this, but it is returning nil.
I know, this is a security issue if they allow these fields to be accessible., But, I want to fetch these values for a feature to be implemented in our application.

Assuming you are using Devise, the only attribute related to the user's password is encrypted_password, it will return the BCrypt encrypted password. You can also read the password_salt User attribute.
You can see all Devise User Model attributes with: User.column_names

Related

Rails validate uniqueness based on another field on the same table

I have a table of users, this table has two columns: email (unique, index) and new_email (index).
When the user needs to change his email, the new_email saves this new address until confirmation. I need to validate it against the email column so I don't get a uniqueness error when I try and confirm it, updating the email field.
I already tried scope, but it doesn't seem to work in my case.
As this is a legacy project, I can't change this flow/structure. So I'm looking for a "rails way" to do this validation.

Rails devise reset password fails if user record contains invalid data

I have an existing application in production where we have added new mandatory fields to the user record. As a result, the forgot password function is failing. I believe the failure occurs in the following method in recoverable.rb
# Update password saving the record and clearing token. Returns true if
# the passwords are valid and the record was saved, false otherwise.
def reset_password(new_password, new_password_confirmation)
if new_password.present?
self.password = new_password
self.password_confirmation = new_password_confirmation
save
else
errors.add(:password, :blank)
false
end
end
The new attributes cannot be generated mechanically. Only the user himself will know the correct values. Does anyone know of a way to get around this problem?
The only idea that I've come up with so far is as follows:
use a rake script to populate the new fields with values that I know would never occur in real life but would be accepted by the model validation rule
when the user logs in, detect if the user record contains invalid data and force them to do an update. In the user edit form, I would use some javascript to change the bogus values to blank.
You could use a custom validation context to make sure the validations on these added fields are only run when a user edits their profile, but skipped when (for example) Devise saves the user record.
In the User model, add an on:-clause to these validations
validates_presence_of :recently_added_mandatory_field, on: :user_updates_profile
And in the appropriate controller action, add this validation context when calling #valid? or #save:
# Existing code uses `#user.valid?` -> change to:
if #user.valid?(:user_updates_profile)
…
# Existing code uses `#user.save` -> change to:
if #user.save(context: :user_updates_profile)
…
See here for a full description of validation contexts: https://api.rubyonrails.org/classes/ActiveModel/Validations/ClassMethods.html#method-i-validates

Encrypt password in postgres jsonb

At my company we're designing a new flow for our user to register. User and Company are very closely tied to each other. Due to several reasons we can't create the user and the company one after the other but we need to create them at the same time.
However as our form is on several steps, we collect all the user input in a separate Registration model in a jsonb attribute and then create the user and company at the end of the process from this intermediate model.
One of the problem is that we collect the user password. However as we're storing the registration in our database, the password is exposed.
How would you try to protect this?
EDIT: We're using Bcrypt to encrypt password
I have not tried this but I guess this will work. You can use the following code to encrypt the password before storing it as intermediate json.
my_password = BCrypt::Password.create("my password")
If you have designed the User model properly, there will be a password_digest field in your table. So while saving encrypted password, use:
#user.password_digest = my_password
instead of
#user.password = my_password
where you expect encryption to take place in the background.

How to know plain text of :encrypted_password, in devise?

If i use has_secure_password, i have whitelist are: password, password_confirmation, and password_digest. With password is the plain text of password_digest, which was encrypted by bcrypt.
But when i use devise with my user model, it has only encrypted_password field, I don't know how to know plain text of password. The schema doesn't has password field. I uasually use rails consle to debug. So anyone can help me how to know the plain text of encrypted_password.
There is no way to get the plain-text password from the encrypted_password field.
But, you can change the password and set it to any string you choose by setting the password attribute of the user model. For example:
user = User.find(34)
user.password = "some password"
user.save!
The whole point of using a hash function to store a password is that there is no way to reverse the hash function. This is why it is called a one way function.
The only way is to try all possible passwords until the hash function results in the same hash as you have. This what the passwords crackers like hashcat do, but they use GPUs the parallelise the process. If you have chosen a long and complex password then the time to do this will be longer than would be feasible for an attacker to complete.
Using a hash function that is expensive in either CPU time or memory requirement, is also important in protecting the passwords. See Password Key Derivation functions.

Rails3 User Changed Password, how do I change the current session password?

I have the need to let the user change their password. I'd like to switch the password in the session to reflect this new password, without logging them out.
def set_auth username, password
# test username and password here?
auth_object = AuthCookie.new
auth_object.set_username username
auth_object.set_password password
session[:user_login] = auth_object
end
I use something like the above, but it doesn't seem to work in changing the current session's password to the new one the use just entered.
What am I doing wrong?
Don't save your whole auth object in the session, the most important thing is you should not save password info in the session. Rails default session storage is cookie based, just base64 encode string. So if you save user password info in the session, there is security problem.
Just put the user identify in the session, for example, the user_id. session[:user_id] = user_id

Resources