I am really new to rails. im using devise gem. now,im trying to implement forget password field in my application.I have been working for hours, but I haven't really had any results. How do I set this up? I am using rails 4
class User < ActiveRecord::Base
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable
devise :database_authenticatable, #:registerable,
:recoverable, :rememberable, :trackable, :validatable
enum role: [:creator, :editor, :curator, :super_admin]
enum status: {:inprogress => 1, :completed => 2}
#has_many :albums
has_many :order_states
has_many :products, through: :order_states
has_many :tagging
has_many :pictures, through: :tagging
def self.authenticate(username, password)
user = User.find_for_authentication(email: username)
if user
user.valid_password?(password) ? user : nil
else
nil
end
end
def generate_authentication_token
token = SecureRandom.hex
self.update_columns(auth_token: token, token_created_at: Time.zone.now)
token
end
end
Related
I have two models that have a has_many association to the same object. I have a User, an Admin, and Visits.
Users has_many Visits
Admins has_many Visits
Every time I create a Visit with a User it works, but when I do it with an Admin it gives me an error:
ActiveRecord::AssociationTypeMismatch.
The full error is this:
User(#70282715553200) expected, got #<Admin id: 2, email: "admin#gmail.com", created_at: "2019-02-07 12:08:40", updated_at: "2019-02-07 12:08:40"> which is an instance of Admin(#70282709528720)
def create
#visit = #service.visits.new(visit_params)
if user_signed_in?
#visit.user = current_user
else
#visit.user = current_admin
end
if #visit.save
redirect_to service_visits_path(#service)
else
redirect_to #services
end
end
==============================
class Admin < ApplicationRecord
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable, :trackable and
# :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :validatable
has_many :visits, dependent: :destroy
end
==============================
class User < ApplicationRecord
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable, :trackable and
# :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :validatable
has_many :visits, dependent: :destroy
end
==============================
class Visit < ApplicationRecord
belongs_to :user
belongs_to :admin
belongs_to :service
end
Unless you've got some kind of polymorphism going on, which isn't documented, I'd try and change this:
if user_signed_in?
#visit.user = current_user
else
#visit.user = current_admin
end
To this:
if user_signed_in?
#visit.user = current_user
else
#visit.admin = current_admin # this line
end
Your Visit model says a visit has both one User, and one Admin, so you have to assign the current_admin to the #visit.admin, not #visit.user.
If you're using Rails 5, you'll also need to update your model as below:
class Visit < ApplicationRecord
belongs_to :user, optional: true
belongs_to :admin, optional: true
belongs_to :service
end
As I note in my comment below, the suggestion from #bo-oz should be given considerable consideration. I haven't seen User and Admin tables typically split out as you've done in production applications. The concept of 'admin' is typically handled as a separate Role model (the rolify gem is good for this), or more simply as a boolean on the User model.
I think what you are trying to do us just plain wrong. An Admin is a User as well. You should remove the Admin model entirely. If you need to assign additional capabilities / rights to someone, you should either create an additional attribute (admin boolean yes/no), or create some kind of Role Based model. Have a look at Rolify gem.
class User < ApplicationRecord
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable, :trackable and
:omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :validatable
has_many :visits, dependent: :destroy
def is_admin?
// return true if user is admin
end
end
class Visit < ApplicationRecord
belongs_to :user
belongs_to :service
end
def create
#visit = #service.visits.new(visit_params)
if user_signed_in?
#visit.user = current_user
else
if #visit.save
redirect_to service_visits_path(#service)
else
redirect_to #services
end
One warning though.... the user is mandatory is this relationship, so this would break if someone is not logged in! Think about it... either don't create a Visit, or create an Anonynous visit.
I work on project (ruby '2.2.0', rails '4.2.3') which use both standard devise user management (for web page) and devise_token_auth (for API part of the service). Everything works fine unless I
include DeviseTokenAuth::Concerns::User
in the models/user.rb. Then sending confirmation emails after user registration does not occur.
I would be grateful for the solution of this problem.
My models/user.rb:
class User < ActiveRecord::Base
# Include devise modules.
devise :invitable, :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable,
:confirmable, :omniauthable
include DeviseTokenAuth::Concerns::User
enum role: [:user, :vip, :admin]
after_initialize :set_default_role, :if => :new_record?
def set_default_role
self.role ||= :user
end
end
routes.rb:
Rails.application.routes.draw do
# standard devise routes available at /users
# NOTE: make sure this comes first!!!
devise_for :users
# token auth routes available at /api/v1/auth
namespace :api do
scope :v1 do
mount_devise_token_auth_for 'User', at: 'auth'
end
end
end
I got the same problem to you. This workaround helped me
class User < ActiveRecord::Base
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable,
:confirmable
include DeviseTokenAuth::Concerns::User
after_create :send_confirmation_email, if: -> { !Rails.env.test? && User.devise_modules.include?(:confirmable) }
private
def send_confirmation_email
self.send_confirmation_instructions
end
end
How can I create a customer class I want to be a Devise User with a role = 1.
I have my User model:
class User < ActiveRecord::Base
enum role: [:user, :customer, :admin, :producer]
after_initialize :set_default_role, :if => :new_record?
def set_default_role
self.role ||= :user
end
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable, :registerable
devise :invitable, :database_authenticatable, :confirmable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
end
And my Customer model
class Customer < User
end
I can specify in the customersController what is a customer like this :
# GET /customers
def index
#customers = Customer.where(:role => 1).page(params[:page])
end
But How can I modify my Customer model to self know he is a User with role = 1 so I can only get my Customers like this :
#customers = Customer.all
if you exactly need Customer.all you should looking for STI(single table inheritance) which already resolve what you trying to do
Rails 4.1
Ruby 2.0
Credential.rb
class Credential < ActiveRecord::Base
belongs_to :category
has_many :user
validates :name, :login, :password, presence: true
attr_accessor :encryption_key
attr_encrypted :login, key: :encryption_key
attr_encrypted :password, key: :encryption_key
end
User.rb
class User < ActiveRecord::Base
# Include default devise modules. Others available are:
# :confirmable, :lockable, :timeoutable and :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
has_many :credentials
def you
"You are <b>#{email}</b>"
end
end
CredentialsController.rb
class CredentialsController < ApplicationController
before_filter :authenticate_user!
def create
#credential = current_user.credentials.new
#credential.encryption_key = session[:master_key]
#credential.update(credential_params)
if #credential.save
redirect_to credential_path(#credential), notice: "Password entry created successfully."
else
render "new"
end
end
The line:
#credential.update(credential_params)
throws an exception
undefined method 'each' for #<User:0x4de4f58>
You need to edit your associations. You have credentials that has_many :user and users that has_many :credentials. The one with the foreign key should be a belongs_to not has_many. If you're attempting to make a many-to-many relationship, then either use has_many_and_belongs_to or a join table. Further, it should be has_many :users and not has_many :user. That should resolve your error.
I can easily to test if a user has certain role by
if user.has_role? :admin
How do I get a user's role name?
Something like
users = User.all
user.each{ |user|
puts user.role or users.role_name ?
}
User model
class User < ActiveRecord::Base
rolify
# Include default devise modules. Others available are:
# :token_authenticatable, :confirmable,
# :lockable, :timeoutable and :omniauthable
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :trackable, :validatable
# Setup accessible (or protected) attributes for your model
attr_accessible :email, :password, :password_confirmation, :remember_me ,:username,:first_name,:last_name
# attr_accessible :title, :body
end
role model
class Role < ActiveRecord::Base
has_and_belongs_to_many :users, :join_table => :users_roles
belongs_to :resource, :polymorphic => true
attr_accessible :name,:id
scopify
end
you can use
user.roles.first.name