I am using Devise for my users in my rails app.
In my user model i have column randomID, this column is uquinesse for each user
and i generate it when the user sign-up
In the user model i have also addBY, i use that because the user need the randomID of another user for sign-up
So i will have tree relation between all users
all works fine, but my brobleme now is if the user enter the wrong randomID,
i must check if exist in my DATABASE or not
if the value exist i let the user sign-up
else i display a message error
any ideas
Simply call a function to check for a value existence before your create action.
in your users_controller.rb:
class UsersController < ApplicationController
before_action :check_for_token, only: :create
...
private
def check_for_token
redirect_to root_path unless User.exists?(:randomID => params[:addBY])
end
end
Related
I'm stuck with an implementation for a project I'm working on. Using rails 7 with devise, all users can sign in so I have the methods authenticate_user! and current_user, which, again, works fine.
I've introduced a Customer model. For now, I do not want the customer to register with password etc, I want them to click a link, sent to them from my application, then visit a page:
# Observer
class CustomerObserver < ActiveRecord::Observer
def after_create(customer)
secret_param = customer.to_sgid(expires_in: nil).to_s
url = ENV['HOST'] + "?csig=#{secret_param}"
# Send email with the url...
end
end
Once customer clicks that link, they should be taken to a special page and should have access to this controller only.
Been looking at GlobalID and not sure how to use the for: name in .to_sgid so that I could restrict the customer to access only the CustomersController and the show action.
In all controllers I have before_action :authenticate_user!. First thing came to mine is overriding that method. Feels wrong. How to have a customer access the CustomersController via the signed link and still be protected from unauthorize users?
I'm currently exploring this method where I could potentially have the customer model authenticatable? This means having two logins, one for user and other for customer. Would be nice to have one sign in path /sign_in/ for both user and customer. I feel this post is changing its direction.
How about some lazy check like this;
before_action :authenticate_user!, :if => :check_csig
# ...
private
def check_csig
# if csig param do not exists, call the authenticate_user!
true unless params[:csig].exists?
# if csig param exists and csig is valid do not call the authenticate_user!
false if check_csig
true
end
OR
before_action :authenticate_user!, :except => [:csgi]
before_action :check_csgi, :only => [:csgi]
# ...
private
def check_csig
#check if csgi is valid
end
I am using devise for user registration/login, after the user has successfully signed up, I want to show a page/a dialog box and redirect to another page based on user response. How can I do that?
User Model (By devise)
username
password
Student Model
name
student_id
Teacher Model
name
grade
First_page:
signup signin links
Signup link will show the devise views/devise/registrations/new.html.erb page.
After successful signup, it takes the user to root page. I have defined the root page in routes.rb:
` Rails.application.routes.draw do
devise_for :users
resources :students, :teachers
# For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html
root to: "students#index"
end `
At this point, the application doesn't have any idea who the user is.
So, I want to get the identity information(student/teacher) from the user.
How will I get this information?
Student/Teacher controller:
`class StudentsController < ApplicationController
before_action :authenticate_user!, only: [:new, :create]
def index
#students = Student.all
end
def new
#student = Student.new
end
def create
current_user.create_student(student_params)
redirect_to root_path
end
private
def student_params
params.require(:student).permit(:name, :skypid)
end
end`
After the user has successfully signed in, I want to ask if the user is a student or teacher. Based on what they select, redirect them to a student form page or teacher form page.
How can I do that in rails?
Thank you
You can write a custom after_sign_in_path_for function in your ApplicationController assuming you're using all the default Devise controllers otherwise. Any named path helper or other route that it returns will be where the user is redirected, so you could do something simple like always redirect to a selection page that presents the options and handles the choice on a subsequent action:
def after_sign_in_path_for(resource)
user_type_selection_path # whatever route in your app manages the selection
end
Alternately, you could invoke a custom method on the user model in that function to make a choice right there:
def after_sign_in_path_for(resource)
resource.student? ? student_path : teacher_path
end
You could hybridize these of course as well to do the latter when the selection has already been made and redirect otherwise, with something similar to the following:
def after_sign_in_path_for(resource)
if resource.user_type_chosen?
resource.student? ? student_path : teacher_path
else
user_type_selection_path
end
Bear in mind that none of those functions or paths are real, since I can't be more specific on the information you've provided, but hopefully this gets you headed in the right direction. The after_sign_in_path_for hook is your primary tool here, unless you get into the world of overriding the default devise controllers and interrupting the usual workflow there to accommodate this step, which doesn't seem strictly necessary by your description.
I'm trying to store a list of permissions within a session variable after a user signs up or logs in to their account. The following code only works when a user logs into a currently saved account. What method do I need to override to save the permissions when the account is created via sign up?
class UserSessionsController < Devise::SessionsController
after_action :after_login, :only => :create
def after_login
session[:permissions] = current_user.list_permissions
end
end
class Users::RegistrationsController < Devise::RegistrationsController
after_action :after_signup, :only => :create
def after_signup
## your data permissions
end
It might be necessary to inject via resource. In this case try (i commented it out quickly, just in case you wondering whats going on):
class Users::RegistrationsController < Devise::RegistrationsController
def create
## GET THE SIGN UP DATA
super do |resource|
##CHECK IF DATA IS VALID
if params[:your_data]
##SET THE RESOURCE TO THE DATA
resource.your_data = params[:your_data]
##CHECK (IF NECESSARY) DATA TO TYPE
if resource.you == 2
## SAVE IT
resource.save_with_your_data
## SAVE WITH STANDARD SETTINGS
else
resource.save
end
end
end
end
end
What method do I need to override to save the permissions when the account is created via sign up?
It seems like you want to store this information in the database when the user is created. Remember that current_user will give you the entire database record in the object, and then you can do whatever you need with it. I wouldn't recommend messing the session directly, instead, work with the current_user object that Devise provides.
I was wondering how you flip the flow of a website.
Example:
Normally a visitor needs an user login to write a summary.
When the visitor come to the page and click create summary, are the visitor normally redirect to sign up page.
How to flip the flow. So you can write a summary without login. And when you click next, you need to login or create a user. User decides to create an user and the summary are created with an association or the user have a login and it also creates and association.
How to create this with devise?
I suggest the following approach:
After creating the summary, store its ID in a session variable. Then, when the user signs in, if any summary IDs are found in their session, associate them with the signed in user
For example:
class SummaryController < ApplicationController
def create
#summary = Summary.create!(params[:summary])
unless user_signed_in?
session[:anon_summary_ids] ||= []
session[:anon_summary_ids] << #summary.id
redirect_to(user_sign_in_path, :notice => "Thanks for the summary! Please sign in...")
end
end
end
class ApplicationController
before_filter :associate_summaries, :if => [:user_signed_in?, :anon_summaries?]
private
def anon_summaries?
session[:anon_summary_ids].try(:any?)
end
def associate_summaries
Summary.where(:id => session[:anon_summary_ids], :user_id => nil).update_all(:user_id => current_user.id)
session[:anon_summary_ids] = nil
end
end
How can I configure my Rails app such that after the form to create a new user is submitted (through devise), I redirect to my own desired page ?
Thank you
After the create user form is submitted the user is created and then logged in so the page you are being redirected to is actually the after log in page. If you only want to change this page when a user is created you can set session["#{resource_name}_return_to"] in a custom registration controller like this:
class Users::RegistrationsController < Devise::RegistrationsController
def create
session["#{resource_name}_return_to"] = some_custom_path
super
end
end
You can also create a root route for your user object in routes.rb which will redirect all users whenever they log in:
match "user_root" => "users#home"
Finally you can define the after_sign_in_path_for(resource_or_scope) method in your application_controller and this will allow you to conditionally redirect users:
def after_sign_in_path_for(resource_or_scope)
if resource_or_scope.is_a?(User)
some_custom_path
else
super
end
end