Rails nested routes for create method smart_listing - ruby-on-rails

I have two models: apartment and room. Apartment has_many rooms, and rooms belongs_to apartment. I use smart_listing gem as ajax form. I show my table in edit_apartment_path
= render 'rooms/index' # index is partial
And I add this to my apartment_controller
def edit
#rooms = smart_listing_create :rooms,
Room.where(apartment_id: params[:apartment_id]),
partial: "rooms/list"
end
Now I must set paths for my form
= simple_form_for object, url: object.new_record? ? apartment_rooms_path : apartment_room_path(id: object),
remote: true, html: {class: "form-horizontal"} do |f|
= f.input :title
= f.button :submit
I can edit my created room, but I can't create new room in apartment. My error:
ActionController::UrlGenerationError - No route matches {:action=>"edit", :apartment_id=>nil, :controller=>"rooms", :id=>#<Room id: 83, title: "dawawd">, created_at: "2016-02-11 10:36:30", updated_at: "2016-02-11 10:36:30", apartment_id: 4>} missing required keys: [:apartment_id]:
My routes
resources :apartments do
resources :rooms
end
Propably smart_listing not support nested routes. Anyone have idea? :)

here's simple example of nested routes with smart_listing. I think that should cover the subject.
I used Rails 4.2, ruby 2.2.0, smart_listing 1.1.2
config/routes.rb
resources :users do
resources :bios
end
root 'users#index'
models/user.rb
class User < ActiveRecord::Base
has_one :bio
accepts_nested_attributes_for :bio, allow_destroy: true
scope :like, ->(args) { where("email like '%#{args}%' OR name like '%#{args}%' OR surname like '%#{args}%'")}
end
models/bio.rb
class Bio < ActiveRecord::Base
belongs_to :user
end
controllers/users_controller.rb
class UsersController < ApplicationController
include SmartListing::Helper::ControllerExtensions
helper SmartListing::Helper
before_action :set_user, only: [:update, :destroy]
def index
users_scope = User.all.includes(:bio)
users_scope = users_scope.like(params[:filter]) if params[:filter]
# #users = smart_listing_create :users, users_scope, partial: "users/list", page_sizes: [5, 7, 13, 26]
#users = smart_listing_create(:users, users_scope, partial: 'users/list',
sort_attributes: [
[:name, 'name'],
[:surname, 'surname'],
[:email, 'email'],
[:city, 'bio.city'],
[:birthday, 'bio.birthday']
],
default_sort: { start_at: 'desc' }
)
end
def new
#user = User.new
#user.build_bio
end
def create
#user = User.new(user_params)
#user.save
end
def edit
#user = User.includes(:bio).find(params[:id])
#user.bio.build if #user.bio.nil?
end
def update
#user.update(user_params)
end
def delete
end
def destroy
#user.destroy
end
private
def set_user
#user = User.find(params[:id])
end
def user_params
params.require(:user).permit(:name, :surname, :email, :bio_attributes => [:birthday, :city])
end
end
views/users/index.html.haml
= smart_listing_controls_for(:users, {class: "form-inline text-right"}) do
.form-group.filter.input-append
= text_field_tag :filter, '', class: "search form-control",
placeholder: "Search...", autocomplete: :off
= smart_listing_render :users
views/users/_list.html.haml
- unless smart_listing.empty?
%table.table.table-striped
%thead
%th= smart_listing.sortable "Name", :name
%th= smart_listing.sortable "Surname", :surname
%th= smart_listing.sortable "Email", :email
%th= smart_listing.sortable "City", :city
%th= smart_listing.sortable "Birthday", :birthday
%tbody
- smart_listing.collection.each do |o|
%tr.editable{data: {id: o.id}}
= smart_listing.render object: o, partial: "users/user", locals: {object: o}
= smart_listing.item_new colspan: 6, link: new_user_path
= smart_listing.paginate
= smart_listing.pagination_per_page_links
- else
%p.warning No users
views/users/_user.html.haml
%td= object.name
%td= object.surname
%td= object.email
%td= object.bio.city
%td= object.bio.birthday
%td.actions= smart_listing_item_actions [ {name: :edit, url: edit_user_path(object)}, {name: :destroy, url: user_path(object), confirmation: "Are you sure you want to delete this?"}]
views/users/_form.html.haml
%td{colspan: 6}
= form_for object, url: object.new_record? ? users_path : user_path(object),
remote: true, html: {class: "form-horizontal"} do |f|
%p
Name:
= f.text_field :name
%p
Surname:
= f.text_field :surname
%p
Email:
= f.text_field :email
= f.fields_for :bio do |ff|
%p
Birthday
= ff.date_field :birthday
%p
City
= ff.text_field :city
= f.submit "Save", class: "btn btn-primary"
%button.btn.btn-link.cancel Cancel
views/users/create.js.erb
<%= smart_listing_item :users, :create, #user, #user.persisted? ? "users/user" : "users/form" %>
views/users/edit.js.erb
<%= smart_listing_item :users, :edit, #user, "users/form" %>
views/users/destroy.js.erb
<%= smart_listing_item :users, :destroy, #user %>
views/users/index.js.erb
<%= smart_listing_update(:users) %>
views/users/new.js.erb
<%= smart_listing_item :users, :new, #user, "users/form" %>
views/users/update.js.erb
<%= smart_listing_item :users, :update, #user, #user.valid? ? "users/user" : "users/form" %>

you should receive to form #apartment also, and in this case if your #room.persisted? form recive request to edit, else to create:
= simple_form_for [#apartment, #room], remote: true, html: {class: "form-horizontal"} do |f|
= f.input :title
= f.button :submit

Related

Rails Nested Form doesn't update. strong_params are setted right

Nested form (with simple_form gem) creates the record, but doesn't want to update it.
Checklist has many questions.
Question belongs to one checklist.
All strong params are setted.
So, in controller:
...
before_action :set_checklist, only: [:show, :edit, :update, :destroy]
...
def new
#checklist = Checklist.new
#checklist.questions.build
end
def create
#checklist = Checklist.new(checklist_params)
if #checklist.save
redirect_to checklists_url, notice: 'Checklist was successfully created.'
...
def edit
end
def update
if #checklist.update(checklist_params)
redirect_to #checklist, notice: 'Checklist was successfully updated.'
else
render :edit
end
end
...
private
def set_checklist
#checklist = Checklist.find(params[:id])
end
def checklist_params
params
.require(:checklist)
.permit(:title, :description,
questions_attributes: Question.attribute_names.map(&:to_sym).push(:_destroy))
end
in view form:
= simple_form_for(#checklist) do |f|
= f.error_notification
.form-inputs
= f.input :title
= f.input :description
...
%tbody.questions
= f.simple_fields_for :questions do |builder|
= render 'question_fields', f: builder
...
in _question_fields:
%tr.nested-fields
%td
= link_to_remove_association "remove", f, class: 'btn btn-primary btn-xs'
%td
= f.input :title, label: false
%td
= f.input :description, label: false
in checklist model:
has_many :questions, dependent: :destroy
accepts_nested_attributes_for :questions,
allow_destroy: true,
reject_if: proc { |att| att['title'].blank? }
in question model:
belongs_to :checklist, optional: true
Thank you
%tr.nested-fields
%td
= link_to_remove_association "remove", f, class: 'btn btn-primary btn-xs'
%td
= f.input :title, label: false
%td
= f.input :description, label: false
your partial is missing = f.hidden_field :id and = f.hidden_field :_destroy

Undefined method error in rails?

I have a model where students can enter information about themselves and others can view them. Since there are a lot of profiles, I have added a search section too. If they want only CS majors, they can select from a drop down. I had things like major, college... today I added "level", which is level of education and I get an error (Error shown at the end). I know this is long, but any help would be really really useful. Thanks!
(Userinfo is the student model)
My controller looks like this:
class UserinfosController < ApplicationController
before_action :find_userinfo, only: [:show, :edit, :update, :destroy, :log_impression]
def index
#userinfors = Userinfo.search(params[:search])
#search = Search.new
#college = Userinfo.uniq.pluck(:college)
#major = Userinfo.uniq.pluck(:major)
#level = Userinfo.uniq.pluck(:level)
end
def show
end
def new
#userinformation = current_user.build_userinfo
end
def create
#userinformation = current_user.build_userinfo(userinfo_params)
if #userinformation.save
redirect_to userinfo_path(#userinformation)
else
render 'new'
end
end
def edit
end
def update
if #userinformation.update(userinfo_params)
redirect_to userinfo_path(#userinformation)
else
render 'edit'
end
end
def destroy
#userinformation.destroy
redirect_to root_path
end
private
def userinfo_params
params.require(:userinfo).permit(:name, :email, :college, :gpa, :major, :token, :skills, :level)
end
def find_userinfo
#userinformation = Userinfo.friendly.find(params[:id])
end
end
My information fill out form (please note how the way of input is different in major and level of edu, maybe thats the problem?):
<%= simple_form_for #userinformation, :html => { :multipart => true } do |f| %>
<%= f.input :name, required: true, label: 'Full name' %>
<%= f.input :college, required: true, label: 'Name of college' %>
<%= f.input :gpa, required: true, label: 'Enter GPA' %>
<%= f.input :email, required: true, label: 'Enter email address' %>
<%= f.input :major, required: true, label: 'Major' %>
<%= f.input :level, collection: ["College undergrad", "College grad"], required: true, label: 'Level of education' %>
<%= f.input :skills, required: true, label: 'Skills' %>
<%= f.button :submit, 'Create account' %>
<% end %>
Search controller:
class SearchesController < ApplicationController
def new
#search = Search.new
#college = Userinfo.uniq.pluck(:college)
#major = Userinfo.uniq.pluck(:major)
#level = Userinfo.uniq.pluck(:level)
end
def create
#search = Search.create(search_params)
redirect_to #search
end
def show
#search = Search.find(params[:id])
end
private
def search_params
params.require(:search).permit(:keyword, :college, :min_gpa, :major, :token, :level )
end
end
Search model:
class Search < ActiveRecord::Base
def search_userinfos
userinfos = Userinfo.all
userinfos = userinfos.where(["name LIKE ?","%#{keyword}%"]) if keyword.present?
userinfos = userinfos.where(["college LIKE ?", college]) if college.present?
userinfos = userinfos.where(["cast(gpa as numeric) >= ?", min_gpa]) if min_gpa.present?
userinfos = userinfos.where(["major LIKE ?", major]) if major.present?
userinfos = userinfos.where(["level LIKE ?", level]) if level.present?
userinfos = userinfos.order("gpa")
return userinfos
end
end
This is where the search section is displayed (index view):
<%= simple_form_for #search do |s| %>
<%= s.input :keyword, label: 'Name' %>
<label>College</label>
<%= s.select :college, options_for_select(#college), :include_blank => true %>
<%= s.input :min_gpa, label: "Minimum GPA" %>
<label>Major</label>
<%= s.select :major, options_for_select(#major), :include_blank => true %>
<label>Job type</label>
<%= s.select :level, options_for_select(#level), :include_blank => true %>
<%= s.button :submit, "Search" %>
<% end %>
The error I get when I try to visit the index view:
NoMethodError in Userinfos#index
Showing app-path/index.html.erb where line #25 raised:
undefined method `level' for #<Search:0x000000139d6c38>
Line 25 is:
<%= s.select :level, options_for_select(#level), :include_blank => true %>
Everything works if I remove that line. When I show the education level in the user profile page, it works perfectly.
Schema for searches:
create_table "searches", force: :cascade do |t|
t.string "keyword"
t.string "college"
t.decimal "min_gpa"
t.string "major"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
As you commented, you do not have a level attribute in your Search model.
rails g migration add_level_to_searches level:string
And of course
rails db:migrate
Happy to help!

Rails - When assigning attributes, you must pass a hash as an argument 2

In my Rails 5 app, I have this error:
when I use this table to list the tags of a related object (in this case an Annotation)
<tbody>
<% object.tags.each do |tag| %>
<% unless tag.content.blank? %>
<tr>
<td style="word-wrap: break-word;" class="displaytagedit"><%= link_to tag.content, **[object, tag]**, method: :patch %></td>
It tries to open this link
http://localhost:3000/annotations/6/tags/24 (which appears correct)
and throws this error:
When assigning attributes, you must pass a hash as an argument.
On this part of my controller (below)
tagable = detect_tagable
#tag = tagable.tags.update(params[:id])
#tags = Tag.all
render '_tag_update'
end
It should call this form:
<%= simple_form_for #tag, html: { class: 'form-vertical', multipart: true },
wrapper: :horizontal_form,
wrapper_mappings: {
check_boxes: :horizontal_radio_and_checkboxes,
radio_buttons: :horizontal_radio_and_checkboxes,
file: :horizontal_file_input,
boolean: :horizontal_boolean
} do |f| %>
<%= f.error_notification %>
<%= f.input :content, placeholder: 'Tagged content', label: false %>
<%= f.association :tagtype, prompt: 'Select tag type', label: false, :collection => Tagtype.active.order(:name).where(:documenttype => object.documenttype_id) %>
<%= f.input :location, :as => :hidden, :input_html => { :value => 'x=0, y=0' }, label: false %>
<%= f.button :submit %>
<% end -%>
Tags are a reusable model on (for now) 2 objects.
This is the routes.rb
Rails.application.routes.draw do
root 'dashboard#index'
devise_for :users
resources :users, :documenttypes, :tagtypes, :business_partners
resources :documents do
resources :comments, :tags
get "pdf", on: :member
end
resources :annotations do
resources :comments, :tags
get "pdf", on: :member
end
Update
this is the tag controller:
class TagsController < ApplicationController
def create
tagable = detect_tagable
tagable.tags.create(tag_params)
redirect_to tagable_path(tagable)
end
def update
tagable = detect_tagable
#tag = tagable.tags.find(params[:id])
#tags = Tag.all
render '_tag_update'
end
def destroy
tagable = detect_tagable
#tag = tagable.tags.find(params[:id])
#tag.destroy
redirect_to tagable_path(tagable)
end
private
def tagable_path(tagable)
case tagable
when Document
document_path(tagable)
when Annotation
annotate_path(tagable)
else
fail 'Unknown tagable'
end
end
def detect_tagable
if params[:annotation_id]
Annotation.find(params[:annotation_id])
elsif params[:document_id]
Document.find(params[:document_id])
else
fail 'Tagable not found'
end
end
def tag_params
params.require(:tag).permit(:content, :location, :tagtype_id, annotation_attributes: { annotation_ids:[] }, document_attributes: { document_ids:[] })
end
end
Where is my error/mistake?
Can you show us your controller? probably it's a typo in object which really would be #object as this comment says
Anyway, send your controller code to confirm this
EDIT:
In your TagsController file you must set the update method like this:
def update
tagable = detect_tagable
#tag = tagable.tags.find(params[:id])
#tags = Tag.all #Or whatever query you want if you want to select more specific Tags
render '_tag_update'
end

Why I get Unpermitted parameters error when I try to save with HABTM check_box_tag?

Ruby version :
ruby 2.1.2p95 (2014-05-08 revision 45877) [x86_64-linux]
Rails version :
Rails 4.1.4
I have a HABTM association between two models : Product and Page. This association works well when I use the console with the following command :
Product.first.pages << Page.first
I inserted a check_box_tag in my products/_form.html.haml for displaying my pages. The check_box works well and I can check/uncheck all my pages.
The problem is when I try to submit the form, the modifications I have done in the checkbox are not saved. I have this problem in both ways.
I figured the problem is the Unpermitted parameters error in my log.
Started PATCH "/admin/pages/linge-de-lit" for 127.0.0.1 at 2014-09-23 23:13:40 +0200
Processing by Admin::PagesController#update as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"q/ZskL+Zijc8GMX9lF+EPgqc9uic9N9B/isWYHx7Cx0=", "page"=>{"category"=>"fabric", "title"=>"Linge de lit", "intro"=>"", "visibility"=>"1", "favorite"=>"0", "priority"=>"50", "product_ids"=>["", "1", "2"]}, "commit"=>"Save", "id"=>"linge-de-lit"}
Page Load (0.3ms) SELECT "pages".* FROM "pages" WHERE "pages"."slug" = 'linge-de-lit' ORDER BY "pages"."id" ASC LIMIT 1
Unpermitted parameters: product_ids
(0.3ms) begin transaction
Page Exists (0.3ms) SELECT 1 AS one FROM "pages" WHERE ("pages"."title" = 'Linge de lit' AND "pages"."id" != 5) LIMIT 1
(0.2ms) commit transaction
Redirected to http://localhost:3000/admin/pages/linge-de-lit
Completed 302 Found in 86ms (ActiveRecord: 1.1ms)
I think the problem is my strong parameters but I doesn't see where.
Here is my models :
class Product < ActiveRecord::Base
has_and_belongs_to_many :pages
end
class Page < ActiveRecord::Base
has_and_belongs_to_many :products
has_many :posts
validates :category, presence: true
validates :title, presence: true, length: {maximum: 20}, uniqueness: true
extend FriendlyId
friendly_id :title, :use => [:slugged, :finders]
before_save :default_values
def default_values
self.title = self.title.capitalize
end
#Scopes
scope :visible, -> { where(visibility: true) }
scope :favorite, -> { where(favorite: true) }
end
Here is my controllers :
class Admin::ProductsController < ApplicationController
before_action :set_product, only: [:show, :edit, :update, :destroy]
# GET /admin/products
def index
#products = Product.all
end
# GET /admin/products/1
def show
end
# GET /admin/products/new
def new
#product = Product.new
#pages = Page.all
end
# GET /admin/products/1/edit
def edit
#pages = Page.all
end
# POST /admin/products
def create
#product = Product.new(product_params)
if #product.save
redirect_to [:admin, #product], notice: 'Product was successfully created.'
else
render action: 'new'
end
end
# PATCH/PUT /admin/products/1
def update
if #product.update(product_params)
redirect_to [:admin, #product], notice: 'Product was successfully updated.'
else
render action: 'edit'
end
end
# DELETE /admin/products/1
def destroy
#product.destroy
redirect_to admin_products_url, notice: 'Product was successfully destroyed.'
end
private
# Use callbacks to share common setup or constraints between actions.
def set_product
#product = Product.find(params[:id])
end
# Only allow a trusted parameter "white list" through.
def product_params
params.require(:product).permit(:name, :description, :brand_id, :price, :minimum_price, :shop_disponibility, :web_disponibility, :purchase_link, :favorite, {:pages_ids => []})
end
end
class Admin::PagesController < ApplicationController
before_action :set_page, only: [:show, :edit, :update, :destroy]
# GET /admin/pages
def index
#pages = Page.all
end
# GET /admin/pages/1
def show
end
# GET /admin/pages/new
def new
#page = Page.new
#products = Product.all
end
# GET /admin/pages/1/edit
def edit
#products = Product.all
end
# POST /admin/pages
def create
#page = Page.new(page_params)
if #page.save
redirect_to [:admin, #page], notice: 'Page was successfully created.'
else
render action: 'new'
end
end
# PATCH/PUT /admin/pages/1
def update
if #page.update(page_params)
redirect_to [:admin, #page], notice: 'Page was successfully updated.'
else
render action: 'edit'
end
end
# DELETE /admin/pages/1
def destroy
#page.destroy
redirect_to admin_pages_url, notice: 'Page was successfully destroyed.'
end
private
# Use callbacks to share common setup or constraints between actions.
def set_page
#page = Page.find(params[:id])
end
# Only allow a trusted parameter "white list" through.
def page_params
params.require(:page).permit(:category, :title, :intro, :visibility, :favorite, :priority, :products_ids => [])
end
end
Here is my views :
# products/_form
= form_for([:admin, #product]) do |f|
- if #product.errors.any?
#error_explanation
%h2= "#{pluralize(#product.errors.count, "error")} prohibited this product from being saved:"
%ul
- #product.errors.full_messages.each do |msg|
%li= msg
.field
= f.label :name
= f.text_field :name
.field
= f.label :description
= f.text_area :description
.field
= f.label :brand_id
= f.text_field :brand_id
.field
= f.label :price
= f.text_field :price
.field
= f.label :minimum_price
= f.check_box :minimum_price
.field
= f.label :shop_disponibility
= f.check_box :shop_disponibility
.field
= f.label :web_disponibility
= f.check_box :web_disponibility
.field
= f.label :purchase_link
= f.text_field :purchase_link
.field
= f.label :favorite
= f.check_box :favorite
= hidden_field_tag "product[page_ids][]", nil
- Page.all.each do |page|
= check_box_tag "product[page_ids][]", page.id, #product.page_ids.include?(page.id), id: dom_id(page)
= label_tag dom_id(page), page.title
.actions
= f.submit 'Save'
# pages/_form
= form_for([:admin, #page]) do |f|
- if #page.errors.any?
#error_explanation
%h2= "#{pluralize(#page.errors.count, "error")} prohibited this page from being saved:"
%ul
- #page.errors.full_messages.each do |msg|
%li= msg
.field
= f.label :category
= f.select :category, options_for_select(#pages_categories), {:prompt => "- Sélectionner une catégorie -"}
.field
= f.label :title
= f.text_field :title
.field
= f.label :intro
= f.text_area :intro
.field
= f.label :visibility
= f.check_box :visibility
.field
= f.label :favorite
= f.check_box :favorite
.field
= f.label :priority
= f.number_field :priority
= hidden_field_tag "page[product_ids][]", nil
- Product.all.each do |product|
= check_box_tag "page[product_ids][]", product.id, #page.product_ids.include?(product.id), id: dom_id(product)
= label_tag dom_id(product), product.name
.actions
= f.submit 'Save'
There is a typo there :) Instead of
# Only allow a trusted parameter "white list" through.
def page_params
params.require(:page).permit(:category, :title, :intro, :visibility, :favorite, :priority, :products_ids => [])
end
It should be product_ids:
# Only allow a trusted parameter "white list" through.
def page_params
params.require(:page).permit(:category, :title, :intro, :visibility, :favorite, :priority, :product_ids => [])
end

Couldn't find Tour without an ID

I'm working on an app to book different types of tours. I have 3 tables - 1) reservations 2) tours 3) join table (reservations_tours). I'm trying to pass the tour id to reservations, but keep getting this error:
Couldn't find Tour without an ID
app/controllers/reservations_controller.rb:12:in `create'
Reservations controller:
class ReservationsController < ApplicationController
def index
end
def new
#reservation = Reservation.new
#tour = Tour.find(params[:tour_id])
end
def create
#tour = Tour.find(params[:tour_id])
#reservation = Reservation.new(reservation_params)
##reservation.tour = #tour # associate #reservation with video
if #reservation.save
Stripe.api_key = ENV["STRIPE_SECRET_KEY"]
Stripe::Charge.create(
:amount => 9000, # amount in cents, again
:currency => "usd",
:card => params[:stripeToken] # Get the credit card details submitted by the form
)
flash[:success] = "Your reservation has been booked for #{#reservation.date} for #{#reservation.passengers} person(s). Please save this info."
redirect_to new_tour_path
else
render 'new'
end
end
private
def reservation_params
params.require(:reservation).permit(:date, :passengers)
end
end
Tours controller:
class ToursController < ApplicationController
def index
end
def new
#tour = Tour.new
end
def create
#tour = Tour.new(tours_params)
if #tour.save
flash[:success] = "Tour #{#tour.name} has been successfully added."
redirect_to new_tour_path
else
flash[:error] = "The tour #{#tour.name} was not successfully saved. Please try again"
render 'new'
end
end
def show
#tour = Tour.find_by(id: params[:id])
#reservation = Reservation.new
end
def edit
end
def update
end
private
def tours_params
params.require(:tour).permit(:name, :amount)
end
end
Reservations view (new)
= javascript_include_tag "https://js.stripe.com/v2/"
= javascript_include_tag 'payment'
:javascript
Stripe.setPublishableKey("#{ENV['STRIPE_PUBLISHABLE_KEY']}");
.container
.row
.col-md-9
%h2= #tour.name
.col-md-3
%p= #tour.amount
= bootstrap_form_for(#reservation, html: { class: 'form-horizontal', id: 'payment-form'}) do |f|
= f.alert_message 'Please fix the errors below:'
= f.text_field :date
= f.text_field :passengers
%fieldset.credit_card
%span.payment-errors
.control-group
= label_tag :card_number, 'Credit card number:', class: 'control-label'
.controls
= text_field_tag :card_number, nil, name: nil, class: 'span3', data: {stripe: 'number'}
.control-group
= label_tag :security_code, 'Security code:', class: 'control-label'
.controls
= text_field_tag :security_code, nil, name: nil, class: 'span3', data: {stripe: 'cvc'}
.control-group
= label_tag :exp_date, 'Expiration:', class: 'control-label'
.controls
= select_month(Date.today, {add_month_numbers: true}, class: 'span2', data: {stripe: 'exp-month'})
= select_year(Date.today.year, {start_year: Date.today.year, end_year: Date.today.year + 4}, class: 'span1', data: {stripe: 'exp-year'})
%fieldset.actions.control-group
.controls
= f.submit 'Sign up'
Reservation model:
class Reservation < ActiveRecord::Base
has_many :reservations_tours, foreign_key: 'reservation_id'
has_many :tours, through: :reservations_tours
end
Tour model
class Tour < ActiveRecord::Base
has_many :reservations_tours, foreign_key: 'tour_id'
has_many :reservations, through: :reservations_tours
end
Join table
class ReservationsTours < ActiveRecord::Base
belongs_to :reservation, foreign_key: 'reservation_id'
belongs_to :tour, foreign_key: 'tour_id'
end
Routes:
Rails.application.routes.draw do
resources :reservations, only: [:new, :create]
resources :tours
end
You are trying to create a non existing relation. You have two basic options to create a relation in rails:
Provide a dropdown with existing tours in the reservations form
f.collection_select(:tour_id, Tour.all, :id, :name)
it will become available in the params[:reservation] array. You will have to permit the tour_id param in reservation_params
make a nested resource for reservations in config/routes.rb.
resources :tours do
resources :reservations
end
which will give you a POST url like /tours/:tour_id/reservations and provide you with params[:tour_id]

Resources