Search code examples
ruby-on-railshttp-redirectdevisemodel

Devise Redirect After Signup: What is super


I want to redirect to a page after signup.

Here is my registrations_controller.rb for devise:

class Users::RegistrationsController < Devise::RegistrationsController
  include ApplicationHelper
  layout "signup_layout", only: [:create, :new]
  def create
    super
    redirect_to("create_company") #Can't use this
  end

  def new
    super
  end

  def edit
    super
  end
end

Only problem is that I can't use redirect_to("create_company") because:

Render and/or redirect were called multiple times in this action. Please note that you may only call render OR redirect, and at most once per action. Also note that neither redirect nor render terminate execution of the action, so if you want to exit an action after redirecting, you need to do something like "redirect_to(...) and return".

I would like to know what super is. Because it seems super is what is trying to redirecting redirect_to("create_company").

My question is how can I redirect to a page after signup & retreive the user_id of the newly created account on the following page.

Thank you.


Solution

  • super is used to call the parent class method when you are overriding it in a subclass:

    class Parent
      def self.foo *args, **kwargs
        puts args.inspect if args.any?
        puts kwargs.inspect if kwargs.any?
      end
    end
    
    class Child < Parent
      def self.foo *args, **kwargs
        super
      end
    end
    
    irb(main):052:0> Child.foo(1, 2, 'foo', bar: 'baz')
    [1, 2, "foo"]
    {:bar=>"baz"}
    => nil
    

    When you call super with no arguments it simply forwards all the received arguments & block to the superclass method.

    In Devise you simply need to override the after_sign_up_path_for method.

    def after_sign_up_path_for(user)
      new_company_path
    end
    

    Another issue is that redirect_to("create_company") will not work. At least not in the way you think. redirect_to takes a string, a hash or a model and is often pretty smart at figuring out what to do.

    However when you pass a string it either needs to be a path or a full URI. Passing the name of named route as a string will not work. Instead if you have a named route you need to use the route helper, for example:

    redirect_to new_company_path
    

    If you use rails build in resource and resource macros (if you are not you should be) to create routes it will create such helpers for you.

    Run rake routes to see a list of routes and the names.


    This is what your complete controller would look like. There is no need to have the create, new and edit actions as you are not actually doing any overrides.

    class Users::RegistrationsController < Devise::RegistrationsController
      layout "signup_layout", only: [:create, :new]
    
      private
      def after_sign_up_path_for(user)
        new_company_path
      end
    end