This is part of my app in rails:
How to get values in the controller of posts from the check boxes?
I want to get the array of ids got from the check boxes.
The post is created, but I can not access the array of ids got from the check boxes.
class Categoryofpost < ActiveRecord::Base
belongs_to :post
belongs_to :category
end
............................
In views/posts/new.html.erb
<%= form_for #post do |p| %>
<%= p.label :title %>
<%= p.text_field :title %>
<br>
<%= p.label :body %>
<%= p.text_area :body %>
<br>
<p>Related to : </p>
<br>
<%= p.collection_check_boxes :category_ids, Category.all, :id, :name %>
<br>
<%= p.submit "Create" %>
<% end %>
class Category < ActiveRecord::Base
belongs_to :user
validates :name, uniqueness: true
has_many :categoryofposts
has_many :related_posts, class_name: "Post", through: :categoryofposts , source: :post
end
....................
In the posts controler
def create
#post_params = post_params
##post_params[:user_id] = 1 #session[:user_id]
#post = Post.new(#post_params)
if #post.save
# #cat = get_categories
# #cat.each do |c|
# Categoryofpost.create(post_id: #post.id, category_id: c)
# end
redirect_to #post, notice: "The post has been posted successfully."
else
render action: :new, alert: "The post has not been posted."
end
end
protected
def post_params
params.require(:post).permit(:title, :body, categoy_ids: [])
end
def get_categories
params.require(:post).permit(categoy_ids: [])
end
class Post < ActiveRecord::Base
belongs_to :user, dependent: :destroy
has_many :categoryofposts
has_many :categories, through: :categoryofposts
end
You have a typo in your post_params method.It should be
def post_params
params.require(:post).permit(:title, :body, category_ids: [])
end
Notice category_ids.
Related
I have a project with the below scenario
Three Objects:
Client:The real world client
User: The who uses the portal
Department: The Client for whome the user works (XYZ.com,ABC.com)
The signup page have: FirstName,username,password,ClientName,Email
Client have only one field value: The client Name
FirstName,username,password,ClientName,Email are of user
Now what I want is to create a Department with ClientName as the Name of the Department and associate the user with the ID of the department.
User have a field department_id
Even with your reformulation, it is still not clear. So I'll go with my own interpretation. ALso, you didn't specify if you were using Mongoid or ActiveRecord. I'll go with a somewhat Mongoid style as it produces clean modelisation, but feel free to replace with ActiveRecord stuff.
Models
class User
has_one :department
has_one :client
accepts_nested_attributes_for :client
accepts_nested_attributes_for :department
field :first_name
field :password
field :username
field :email
class Client
belongs_to :user
field :name
class Department
belongs_to :user
field :name
your_controller.rb
def new
#user = User.new
#user.client = Client.new
#user.department = Department.new
end
def create
if #user = User.create(user_params)
redirect_to #user
else
render 'new'
end
end
private
def user_params
# Set department.name as client.name
if params[:user] and params[:user][:department] and params[:user][:client]
params[:user][:department][:name] = params[:user][:client][:name]
end
params.require[:user].permit(
:first_name, :password, :username, :email,
client_attributes: [:id, :name],
department_attributes: [:id, :name]
)
end
_form.html.erb
<%= form_for :user do |user| %>
<%= user.text_field(:name) %>
...
<%= user.fields_for :client do |client| %>
<%= client.text_field(:name) %>
<% end %>
<%= user.fields_for :department do |department| %>
<p class="text-info">A department will be created with the same name as the client</p>
<% end %>
<% end %>
I've always had trouble with has_many :through relationships on join tables and am stuck again on where I'm going wrong. I think it might be in my controller as I'm still getting to grips with how it all works.
I have three models:
class Role < ActiveRecord::Base
has_many :assignments, inverse_of: :role
has_many :employees, :through => :assignments
accepts_nested_attributes_for :assignments
end
class Employee < ActiveRecord::Base
has_many :assignments, inverse_of: :employee
has_many :roles, :through => :assignments
accepts_nested_attributes_for :assignments
end
class Assignment < ActiveRecord::Base
belongs_to :employee, inverse_of: :assignment
belongs_to :role, inverse_of: :assignment
accepts_nested_attributes_for :employee
accepts_nested_attributes_for :role
end
I'd like to be able to set the pre-created role for an employee when creating or editing an employee. My New Employee form is as follows:
<%= semantic_form_for #employee do |f| %>
<%= render 'shared/error_messages' %>
<%= f.inputs do %>
<%= f.input :first_name %>
<%= f.input :last_name %>
<%= f.input :email %>
<%= f.input :password %>
<%= f.input :password_confirmation %>
<%= semantic_fields_for :roles do |role| %>
<%= role.input :role, :as => :select, :collection => Role.all %>
<%= role.semantic_fields_for :assignments do |assignment| %>
<%= assignment.input :start_date, :as => :date_select %>
<%= assignment.input :end_date, :as => :date_select %>
<%= assignment.input :assignment_no %>
<%= assignment.input :assignment_id %>
<% end %>
<% end %>
<% end %>
<%= f.actions do %>
<%= f.action :submit, :as => :button %>
<%= f.action :cancel, :as => :link %>
<% end %>
<% end %>
and finally my Employee Controller is:
class EmployeesController < ApplicationController
before_action :set_employee, only: [:show, :edit, :update, :destroy]
def index
#employees = Employee.paginate(page: params[:page])
end
def show
end
def new
#employee = Employee.new
role = #employee.roles.build
end
def edit
#employee = Employee.find(params[:id])
end
def create
#employee = Employee.new(employee_params)
if #employee.save
#employee.send_activation_email
flash[:info] = "Please check your email to activate your account."
redirect_to root_url
else
render 'new'
end
end
def update
respond_to do |format|
if #employee.update(employee_params)
flash[:success] = "Profile updated"
format.html { redirect_to #employee, notice: 'Employee was successfully updated.' }
format.json { render :show, status: :ok, location: #employee }
else
format.html { render :edit }
format.json { render json: #employee.errors, status: :unprocessable_entity }
end
end
end
def destroy
Employee.find(params[:id]).destroy
flash[:success] = "Employee deleted"
respond_to do |format|
format.html { redirect_to employees_url, notice: 'Employee was successfully destroyed.' }
format.json { head :no_content }
end
end
private
# Use callbacks to share common setup or constraints between actions.
def set_employee
#employee = Employee.find(params[:id])
end
# Never trust parameters from the scary internet, only allow the white list through.
def employee_params
params.require(:employee).permit(:avatar, :email, :first_name, :last_name, :password, :assignments_attributes => [:employee_id, :role_id, :roles_attributes => [:id, :employee_id, :PID]])
end
end
I appreciate that this subject is always on Stackoverflow, but I can't seem to translate any of the problems into where I am. Any help would be greatly appreciated!
The console output is as follows:
Started POST "/employees" for 127.0.0.1 at 2015-05-16 18:05:34 +0200
source=rack-timeout id=d5933405c94d9c2e8bca3332564528ec timeout=60000ms service=25ms state=active
Processing by EmployeesController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"TgHHELkt2zXUtS474WwGeHcmfKKw/broHxRdhlsF1P4JyGoa+03rchb6mfxbOSXKdrPgcJMeBCyIlCMHqPlQBA==", "employee"=>{"first_name"=>"John", "last_name"=>"Smith", "email"=>"john#smith.com", "password"=>"[FILTERED]", "password_confirmation"=>"[FILTERED]"}, "roles"=>{"role"=>"2", "assignments"=>{"start_date(1i)"=>"2012", "start_date(2i)"=>"7", "start_date(3i)"=>"5", "end_date(1i)"=>"2016", "end_date(2i)"=>"3", "end_date(3i)"=>"1", "assignment_no"=>"4", "assignment_id"=>"A3392822"}}, "button"=>""}
Unpermitted parameter: password_confirmation
(0.2ms) BEGIN
source=rack-timeout id=d5933405c94d9c2e8bca3332564528ec timeout=60000ms service=1113ms state=active
SQL (70.3ms) INSERT INTO "employees" ("email", "first_name", "last_name", "password_digest", "created_at", "updated_at", "activation_digest") VALUES ($1, $2, $3, $4, $5, $6, $7) RETURNING "id" [["email", "john#smith.com"], ["first_name", "John"], ["last_name", "Smith"], ["password_digest", "$2a$10$g3PNppheVZ8AFnnKuWg6secBdGev0NlCXjUx.RXsky03Xl9L3CubO"], ["created_at", "2015-05-16 16:05:35.422312"], ["updated_at", "2015-05-16 16:05:35.422312"], ["activation_digest", "$2a$10$L0yFuvmlJon7fWod6lHj..O7yDRaqwqTlTkJgD7Evqx.dA4pDTlBC"]]
(133.0ms) COMMIT
(I'm working on a very slow computer!)
I am new to ruby on rails espacially nestes forms. I am trying to create an author and a book in the same form knowing that there's a many to many relationshio between them my code is presented below.
book.rb
class Book < ActiveRecord::Base
has_many :exemplaires
has_many :talks, inverse_of: :book
has_many :subjects, through: :writings
has_many :writings
has_many :authors, through: :talks
accepts_nested_attributes_for :authors
validates :title, presence: true
end
author.rb:
class Author < ActiveRecord::Base
has_many :talks
has_many :books, through: :talks
end
talk.rb
class Talk < ActiveRecord::Base
belongs_to :book
belongs_to :author
end
book_controller.rb
class BooksController < ApplicationController
def index
end
def list
#books= Book.all
end
def new
#book = Book.new
#author=#book.authors.new
end
def create
#book= Book.new(book_params)
if #book.save
flash[:notice]='goood'
redirect_to admin_manage_path
else
flash[:alert]='ouups'
redirect_to root_url
end
end
private
def book_params
params.require(:book).permit(:title, :pages, :resume, :authors_attributes)
end
end
books\new.html.erb
<h1>Add new book</h1>
<%= form_for(#book) do |form| %>
<%= form.label :title %>
<%= form.text_field :title %>
<%= form.fields_for :authors do |tag_form| %>
<%= tag_form.label :f_name %>
<%= tag_form.text_field :f_name %>
<% end %>
<%= form.submit "Submit" %>
<% end %>
what i got as error
Processing by BooksController#create as HTML
Parameters: {"utf8"=>"✓", "authenticity_token"=>"qpGng8tOiC/B5VX2tphuhAe+Wq1vx7it1vEO6XmwZmI=", "book"=>{"title"=>"booooooooooooook", "authors_attributes"=>{"0"=>{"f_name"=>"auuuuuuuuuuuuuuuuuthor"}}}, "commit"=>"Submit"}
Unpermitted parameters: authors_attributes
You need to whitelist the authors_attributes fields too:
def book_params
params.require(:book).permit(:title, :pages, :resume, authors_attributes: [:f_name])
end
I am using rails 4.0.4 with nested_form 0.3.2 to build an app that allows users to organize movies in lists.
I have these main models, a List model (I've excluded things such as validations):
class List < ActiveRecord::Base
belongs_to :user
has_many :list_movie_pairs
has_many :movies, :through => :list_movie_pairs
accepts_nested_attributes_for :list_movie_pairs, :allow_destroy => true
accepts_nested_attributes_for :movies, :allow_destroy => true
end
A Movie model:
class Movie < ActiveRecord::Base
has_many :list_movie_pairs
has_many :lists, :through => :list_movie_pairs
has_many :reviews
end
A ListMoviePair model for the many-to-many relationship:
class ListMoviePair < ActiveRecord::Base
belongs_to :list
belongs_to :movie
validates_presence_of :list_id, :movie_id
validates_uniqueness_of :movie_id, scope: :list_id
end
I am trying to build an interface for the user to add movies to a created list. These routes serve my purpose:
get "/users/:username/lists/:id/add" => "lists#add_movies", :as => :user_list_list_movie_pairs
post "/users/:username/lists/:id/add" => "lists#submit_movies"
These are the classes in my ListsController that should make this possible:
def add_movies
#pair = list.list_movie_pairs.new # "list" is a helper that returns the current list
end
def submit_movies
#list = current_user.lists.find(params[:id])
#pair = #list.list_movie_pairs.new(pair_params)
if #pair.save
redirect_to user_list_path(current_user.username, #list)
else
render :add_movies
end
end
def list_params
params.require(:list).permit(:name, :description, :private, \
list_movie_pairs_attributes: [:id, :list_id, :movie_id, :_destroy], \
movies_attributes: [:id, :title, :_destroy])
end
And this is the form in my view
<%= nested_form_for [current_user, list, #pair] do |f| %>
<%= f.fields_for :movies do |movie_form| %>
<%= movie_form.text_field :title %>
<%= movie_form.link_to_remove "Remove movie" %>
<% end %>
<%= f.link_to_add "Add movie", :movies %>
<% end %>
I get this error when trying to access the view:
Invalid association. Make sure that accepts_nested_attributes_for is used for :movies association.
Which pops at this line:
<%= f.link_to_add "Add movie", :movies %>
Note 1: I am using the Devise gem for users, hence the "current_user" helper;
Note 2: I have tried using both "movies" and "list_movie_pairs", i.e.:
f.fields for :list_movie_pairs
and
f.link_to_add "Add movie", :list_movie_pairs
in my view, neither association seems to work
Your code in the view should be like this
<%= nested_form_for [current_user, list, #pair] do |f| %>
<%= f.fields_for :movies do |movie_form| %>
<%= movie_form.text_field :title %>
<%= movie_form.link_to_remove "Remove movie" %>
<%= movie_form.link_to_add "Add movie", :movies %> #note the change here
<% end %>
<% end %>
Update
There are several issues in your code
1.In your List model,this line is not required
accepts_nested_attributes_for :movies, :allow_destroy => true #not requied
2.In your ListsController,you have this line
#pair = #list.list_movie_pairs.new(pair_params)
It should be
#pair = #list.list_movie_pairs.new(list_params) because you have list_params method not pair_params
I am a newbie to Ruby on Rails and have scoured Stackoverflow and the internet to the best of my abilities and am still stumped.
In my set-up, a Rating belongs_to a Product and has_many Comments. I'm using simple-form and trying to use nested fields_for to add RatingComment through the Rating form. Interestingly, when using the singular form of :rating_comment, the field is displayed. But as expected, I get the unpermitted parameter error when trying to save. When I use plural :rating_comments, the field disappears. This is similar to this SO posting, but adding #rating.rating_comments.build to new action still does not work for me. I've tried restarting the server many times, and even reset the database to no avail. Would appreciate any assistance as I've been struggling with this issue for the past few days.
Note: I've also taken out what I think is irrelevant code from the snippets below. If I need to show more information, please do let me know. Thanks in advance!
routes.rb
resources :ratings, only: [:new, :create, :edit, :update, :destroy] do
resources :rating_comments, shallow: true
end
rating.rb
class Rating < ActiveRecord::Base
belongs_to :product
belongs_to :user
has_many :rating_comments, foreign_key: "rating_id", dependent: :destroy
accepts_nested_attributes_for :rating_comments, reject_if: :all_blank
end
rating_comment.rb
class RatingComment < ActiveRecord::Base
belongs_to :rating
validates :rating_id, presence: true
end
ratings_controller.rb
class RatingsController < ApplicationController
before_action :signed_in_user, only: [:create, :new, :show]
def new
#product = Product.find(params[:id])
#rating = #product.ratings.new
#rating.rating_comments.build
end
def create
#product = Product.find(params[:product_id])
#rating = #product.ratings.build(rating_params)
#rating.user_id = current_user.id
...
private
def rating_params
params.require(:rating).permit(:user_id, :product_id, :rating, rating_comments_attributes: [:rating_id, :content])
end
end
ratings/_new_rating_form.html.erb
<%= simple_form_for([#product, #rating], html: { class: 'form-horizontal' }) do |f| %>
<%= f.error_notification %>
<%= f.input :rating, collection: 1..10, as: :radio_buttons,
item_wrapper_class: 'inline', checked: 5 %>
<%= f.simple_fields_for :rating_comments do |rc| %>
<fieldset>
<%= rc.input :content, label: "Comments" %>
</fieldset>
<% end %>
<%= f.error :base %>
<%= f.button :submit, "Submit" %>
<% end %>
Very embarrassed to admit that it turns out that I had the view written in the wrong action. Once I put it in the new.html, it finally worked.