Reputation: 607
Thanks in advance for whoever tries or answer my issue.
I have City
Model, Area
model, User
model.
City
Model and Area
Model has "has_many" association
where as Area Model and User Model has "has many through" association
I want Area select menu to display According to City selected, While creating a new user when any item in city select menu is selected (ajax request is made), area select menu should show areas that belongs to that city.
This is my code please tell me where M i wrong. (Thanks)
(app/views/users/_form)
<%= form_for(@user, remote: true) do |f| %>
<div class="field">
<%= f.label :name %><br>
<%= f.text_field :name %>
</div>
<p>
<%=f.collection_select :city_id, City.order(:name), :id, :name, include_blank: true%>
</p>
<div class="a"></div>
<div class="actions">
<%= f.submit %>
</div>
<% end %>
(app/controllers/users_controller.rb)
class UsersController < ApplicationController
before_action :set_user, only: [:show, :edit, :update, :destroy]
def custom
@tilu = params[:city_id]
respond_to do |format|
format.js
end
end
# GET /users
# GET /users.json
def index
@users = User.all
end
# GET /users/1
# GET /users/1.json
def show
end
# GET /users/new
def new
@user = User.new
@areas= Area.all
end
# GET /users/1/edit
def edit
end
# POST /users
# POST /users.json
before_action :get_area, only:[:create]
def create
@user = User.new(user_params)
@user.area_ids = @area
respond_to do |format|
if @user.save
format.html { redirect_to @user, notice: 'User was successfully created.' }
format.json { render :show, status: :created, location: @user }
else
format.html { render :new }
format.json { render json: @user.errors, status: :unprocessable_entity }
end
end
end
# PATCH/PUT /users/1
# PATCH/PUT /users/1.json
def update
respond_to do |format|
if @user.update(user_params)
format.html { redirect_to @user, notice: 'User was successfully updated.' }
format.json { render :show, status: :ok, location: @user }
else
format.html { render :edit }
format.json { render json: @user.errors, status: :unprocessable_entity }
end
end
end
# DELETE /users/1
# DELETE /users/1.json
def destroy
@user.destroy
respond_to do |format|
format.html { redirect_to users_url, notice: 'User was successfully destroyed.' }
format.json { head :no_content }
end
end
private
# Use callbacks to share common setup or constraints between actions.
def set_user
@user = User.find(params[:id])
end
def get_area
@area = params[:user][:area_id]
end
# Never trust parameters from the scary internet, only allow the white list through.
def user_params
params.require(:user).permit(:name, :description,[:area_id])
end
end
(app/assets/javascripts/users.js.coffe)
jQuery ->
$(document).on 'change', '#user_city_id', (evt) ->
$.ajax '/users/custom',
type: 'GET'
dataType: 'html'
data: {
city_id: $('#user_city_id :selected').val()
}
error: (jqXHR, textStatus, errorThrown) ->
console.log("AJAX Error: #{textStatus}")
success: (data, textStatus, jqXHR) ->
console.log("Dynamic country select OK!")
(config/routes.rb)
Rails.application.routes.draw do
resources :users
resources :areas
resources :cities
get 'users/custom'
(app/views/users/_customTemplate.html.erb)
<%=f.collection_select :area_id, Area.where(city_id: @tilu), :id, :name, include_blank: true %>
last but not the least... (app/views/users/custom.js.erb)
$('.a').append("<%=j render 'customTemplate' %>");
ruby server console error
Started GET "/users/custom?city_id=1" for 127.0.0.1 at 2015-09-30 21:20:01 +0530 Processing by UsersController#show as HTML
Parameters: {"city_id"=>"1", "id"=>"custom"} User Load (0.3ms) SELECT "users".* FROM "users" WHERE "users"."id" = ? LIMIT 1 [["id", 0]] Completed 404 Not Found in 76ms (ActiveRecord: 0.3ms)ActiveRecord::RecordNotFound (Couldn't find User with 'id'=custom):
app/controllers/users_controller.rb:77:in `set_user'Rendered /usr/local/lib/ruby/gems/2.2.0/gems/actionpack-4.2.1/lib/action_dispatch/middleware/templates/rescues/_source.erb (4.1ms)
Browser console error
GET http://localhost:3000/users/custom?city_id=1 404 (Not Found)send @ jquery-4075e3b7b3964707c653f61b66f46dec.js?body=1:9665jQuery.extend.ajax @ jquery-4075e3b7b3964707c653f61b66f46dec.js?body=1:9216(anonymous function) @ users-c743c610a872f962fb75a7ac244905cd.js?body=1:4jQuery.event.dispatch @ jquery-4075e3b7b3964707c653f61b66f46dec.js?body=1:4671elemData.handle @ jquery-4075e3b7b3964707c653f61b66f46dec.js?body=1:4339ListPicker._handleMouseUp @ about:blank:544 users-c743c610a872f962fb75a7ac244905cd.js?body=1:11 AJAX Error: error
Upvotes: 3
Views: 5579
Reputation: 607
this example worked for me.. however I had to convert my colection_select to just select but never the less its working and Thanks to all those who tried to resolve the issue
[1]: https://kernelgarden.wordpress.com/2014/02/26/dynamic-select-boxes-in-rails-4/
Upvotes: 0
Reputation: 76774
Ok there are too many issues for me to pick through them; this is what I'd do:
You're looking for something called dynamic select menus. You mention this in the title, I just wanted to clarify the terminology.
Dynamic select menus should send an ajax request when you change the value in the select box. The process should be succinct (IE you only send an ID
to your controller), and you end up with a set of returned data to populate the next select box:
#config/routes.rb
resources :cities do
get "update", to: "users#custom" #-> url.com/cities/:city_id/update
end
resources :users #-> put this below so that the users/show method doesn't catch the above calls
#app/controllers/users_controller.rb
class UsersController < ApplicationController
def custom
@city = City.find params[:city_id]
respond_to do |format|
format.js
end
end
end
#app/views/users/custom.coffee
$('.a').append("<%=j render 'users/customTemplate' %>");
Above is the "backend". Here is the "Frontend":
#app/views/users/_form.html.erb (removed HTML to clean it up for this)
<%= form_for(@user, remote: true) do |f| %>
<%= f.text_field :name %>
<%= f.collection_select :city_id, City.order(:name), :id, :name, include_blank: true %>
<%= f.submit %>
<% end %>
#app/assets/javascripts/users.coffee
$(document).on 'change', '#user_city_id', (evt) ->
$.ajax '/cities/' + $(this).val() + '/update',
type: 'GET'
dataType: 'html'
data: {
city_id: $('#user_city_id :selected').val()
}
error: (jqXHR, textStatus, errorThrown) ->
console.log("AJAX Error: #{textStatus}")
success: (data, textStatus, jqXHR) ->
console.log("Dynamic country select OK!")
You'll gain a lot from watching this Railscast:
Upvotes: 3