title: How to nest devise_invitable such that a user can be invited to only 1 hotel
body: <p><strong>Goal</strong></p>
  
  <p>I would like to let a user.admin invite a user to only one of its hotels with the <code>devise_invite</code> gem. </p>
  
  <p>=> <code>User</code> and <code>Hotel</code> are connected via a Join table <code>UserHotel</code>.</p>
  
  <p><strong>Issue</strong></p>
  
  <p>I started to doubt the way I set up devise(_invitable). With the way I currently set it up, I am not able to create the user_hotel Join_table and/or add the specific hotel params to the invited user, see output below for checks: </p>
  
  <ul>
  <li><p>controller
  <code>&gt;&gt; @user.hotels =&gt; #&lt;ActiveRecord::Associations::CollectionProxy []&gt;</code></p></li>
  <li><p>console:</p></li>
  </ul>
  
  <pre><code>pry(main)&gt; User.invitation_not_accepted.last.hotels
    User Load (0.6ms)  SELECT  "users".* FROM "users" WHERE "users"."invitation_token" IS NOT NULL AND "users"."invitation_accepted_at" IS NULL ORDER BY "users"."id" DESC LIMIT $1  [["LIMIT", 1]]
    Hotel Load (0.4ms)  SELECT "hotels".* FROM "hotels" INNER JOIN "user_hotels" ON "hotels"."id" = "user_hotels"."hotel_id" WHERE "user_hotels"."user_id" = $1  [["user_id", 49]]
  =&gt; []
  </code></pre>
  
  <p><strong>UPDATE</strong></p>
  
  <p>The issue seems to be in the many-to-many relationship between user and hotel. When I break my controller 'new' action after <code>hotel.user.new</code> and test it I het the following:</p>
  
  <ul>
  <li><code>&gt;&gt; @user.hotels =&gt; #&lt;ActiveRecord::Associations::CollectionProxy []&gt;</code></li>
  <li><code>&gt;&gt; @hotel.users =&gt; #&lt;ActiveRecord::Associations::CollectionProxy [#&lt;User id: 2, email: "test@hotmail.com", created_at: "2019-11-05 14:17:46", updated_at: "2019-11-05 15:04:22", role: "admin"&gt;, #&lt;User id: nil, email: "", created_at: nil, updated_at: nil, role: "admin"&gt;]&gt;</code></li>
  </ul>
  
  <p><strong>Note</strong>
  I set up users with devise, such that my users controller is build up as:</p>
  
  <ul>
  <li>users/confirmations_controller.rb</li>
  <li>users/invitations_controller.rb</li>
  <li>users/omniauth_callbacks_controller.rb</li>
  <li>users/password_controller.rb</li>
  <li>users/registrations_controller.rb</li>
  <li>users/sessions_controller.rb</li>
  <li>users/unlocks_controller.rb</li>
  </ul>
  
  <p><strong>Code</strong></p>
  
  <p>routes</p>
  
  <pre><code>Rails.application.routes.draw do
  
    devise_for :users
  
    resources :hotels do
  devise_for :users, :controllers =&gt; { :invitations =&gt; 'users/invitations' }
    end
  end
  </code></pre>
  
  <p>models</p>
  
  <pre><code>class User &lt; ApplicationRecord
    # Include default devise modules. Others available are:
    # :confirmable, :lockable, :timeoutable, :trackable and :omniauthable
    has_many :user_hotels, dependent: :destroy
    has_many :hotels, through: :user_hotels
    accepts_nested_attributes_for :user_hotels
    enum role: [:owner, :admin, :employee]
    after_initialize :set_default_role, :if =&gt; :new_record?
  
    def set_default_role
      self.role ||= :admin
    end
  
    devise :invitable, :database_authenticatable, :registerable,
           :recoverable, :rememberable, :validatable, :invitable
  end
  
  class UserHotel &lt; ApplicationRecord
    belongs_to :hotel
    belongs_to :user
  end
  
  class Hotel &lt; ApplicationRecord
    has_many :user_hotels, dependent: :destroy
    has_many :users, through: :user_hotels
    accepts_nested_attributes_for :users, allow_destroy: true, reject_if: -&gt;(attrs) { attrs['email'].blank? || attrs['role'].blank?}
  end
  </code></pre>
  
  <p>views/hotels/show</p>
  
  <p><code>&lt;%= link_to "invite new user", new_user_hotel_invitation_path(@hotel)%&gt;</code></p>
  
  <p>controllers/users/invitations_controller.rb</p>
  
  <pre><code>class Users::InvitationsController &lt; Devise::InvitationsController
    def new
      @hotel = Hotel.find(params[:hotel_id])
      @user = @hotel.users.new
    end
  
    def create
      @hotel = Hotel.find(params[:hotel_id])
      @user = @hotel.users.new(hotel_user_params)
      @user.invite!
    end
  
    private
    def hotel_user_params
      params.require(:user).permit(:email, :role,
        hotel_users_attributes: [:hotel_id])
    end
  end
  </code></pre>
  
  <p>views/invitations/new.html.erb</p>
  
  <pre><code>&lt;h2&gt;&lt;%= t "devise.invitations.new.header" %&gt;&lt;/h2&gt;
  
  &lt;%= simple_form_for(resource, as: resource_name, url: user_hotel_invitation_path(@hotel), html: { method: :post }) do |f| %&gt;  &lt;%= f.error_notification %&gt;
  
    &lt;% resource.class.invite_key_fields.each do |field| -%&gt;
      &lt;div class="form-inputs"&gt;
        &lt;%= f.input field %&gt;
      &lt;/div&gt;
    &lt;% end -%&gt;
  
        &lt;%= f.input :role, collection: [:owner, :admin, :employee] %&gt;
    &lt;div class="form-actions"&gt;
      &lt;%= f.button :submit, t("devise.invitations.new.submit_button") %&gt;
    &lt;/div&gt;
  &lt;% end %&gt;
  </code></pre>