以ruby形式嵌套的ajax表单

时间:2015-09-24 11:58:11

标签: ruby-on-rails ajax

提前感谢任何试图解决我的问题的人。 我是新手,所以请帮忙,我有

rails g scaffold City name:string
rails g scaffold Area name:string city:references
rails g scaffold User name:string brief:text
rails g migration CreateAreasUsers id:false area:references user:references

rake db:migrate

CreateAreasUsers是表连接bw区域和用户

CityAreas已预先填充

两个问题

1)如何在用户表单中添加功能,以便:areas_users(连接表)也会更新。

2)城市和区域是单独的模型,那么我如何更改城市的选择标记并选择区域标记(但区域取决于城市) 像:

<div id="foo">
<select>
 <% @cities.each do |city|%>
  <option value="<%=city.id%>"> <%=city.name%> </option>
 <%end%>
<select/>

 <div id="bar">
    <select>
     <% @areas.each do |area|%>
      <option value="<%=area.id%>"> <%=area.name%> </option>
     <%end%>
    <select/>
    </div>

div foo应与新用户表单中的div栏互换 请帮忙。

1 个答案:

答案 0 :(得分:1)

好的,既然你是Rails的新手,我会解释你需要知道的事情。

<强>协会

首先,您正在处理ActiveRecord associations。我猜你有一些关于它们如何工作的想法,因为你已经提出了相关的问题。

如果您需要了解详细信息,那么您一直在建立has_and_belongs_to_many关系:

enter image description here

这不需要任何额外的模型 - 它使您能够直接使用连接表本身调用相关数据。

-

回答你的第一个问题:

  

如何在用户表单中添加功能,以便:areas_users(加入   表)也已更新。

答案是通过habtm关联传递适当的数据:

#app/models/user.rb
class User < ActiveRecord::Base
    has_and_belongs_to_many :areas
end

#app/models/area.rb
class Area < ActiveRecord::Base
   has_and_belongs_to_many :users
end

这允许您分别引用@user.areas@area.users,包括表单:

#app/views/users/new.html.erb
<%= form_for @user do |f| %>
   <%= f.select :areas, Area.all, multiple: true %>
<% end %>

通常您将accepts_nested_attributes_for用于此类功能。这是一个稍微不同的问题,我不得不用另一篇文章来解释。

然后,您可以使用以下内容更改@user对象:

#app/controllers/users_controller.rb
class UsersController < ApplicationController
   def create
       @user = User.new user_params
   end

   private 

   def user_params
       params.require(:user).permit(:user, :params, :areas)
   end
end

关于你的第二个问题:

  

城市和区域是单独的模型,因此如何更改选择标记   区域选择标记的城市(但区域取决于城市),如

这是一个更多的参与。

首先,您需要正确设置关联。我根据你发布的内容推荐了以上内容;我不是一个心灵读者,所以如果它错了,那是因为你没有正确解释自己。

最重要的是,您的CityArea模型需要具有以下关联:

#app/models/city.rb
class City < ActiveRecord::Base
    belongs_to :area
end 

#app/models/area.rb
class Area < ActiveRecord::Base
    has_many :cities
end

这意味着您可以致电@city.area@area.cities。因此,您将能够按如下方式加载表单:

         

您需要做的是为selectbox创建一种从服务器中提取关联值的方法。虽然可能有gem或更简单的方法来做这件事,但我会在你心情的时候为你写它:

#config/routes.rb
resources :areas do
    get ":id/cities", to: "areas#show" # -> we'll be using the 'show' action
end 

#app/controllers/areas_controller.rb
class AreasController < ApplicationController
    def show
       @area = Area.find params[:id]
       respond_to do |format|
          format.html
          format.json { render json: @area.cities }
       end
    end
end

这为我们提供了一个钩子,我们可以使用Ajax在选择区域时拉动相关城市:

#app/assets/javascripts/application.js
$("select.areas").on("change", function(){
   id = $(this).val();
   $.ajax({
      url: id + "/cities"
      success: function(data) {
         cities = JSON.Parse(data);
         $('select.cities').find('option').remove();
         $.each(cities, function(index, item) {
            $("select#cities").append( // Append an object to the inside of the select box
            $("<option></option>") // Yes you can do this.
               .text(item.description)
               .val(item.id)
            );
        });
      }
   });
});