【发布时间】:2020-02-14 01:33:20
【问题描述】:
我能够创建一个订单表单,用户可以在其中填写一个bike_type,然后表单会呈现属于这个bike_type 的自行车。
- 订单通过连接表链接到自行车(因为它们之间存在多对多关系)。
- 自行车属于bike_type
- bike_type 属于bike_store
问题
当表单重新呈现时,例如(i) 引发验证,因此再次呈现“新”操作或 (ii) 当我想编辑订单时:
- 所有字段都使用以前的数据重新填充,但 bike_type 和 Bike 字段除外(这些字段为空)。
代码
订单控制器
class OrdersController < ApplicationController
def new
@bike_store = BikeStore.find(params[:bike_store_id])
@order = Order.new
@order.order_bikes.build
@bike_type_list = @bike_store.bike_types
@bikes = []
# Display bikes for category
if params[:bike_type].present?
@bikes = BikeType.find(params[:bike_type]).bikes
end
if request.xhr?
respond_to do |format|
format.json {
render json: {bikes: @bikes}
}
end
end
authorize @order
end
def create
@order = Order.new(order_params)
@bike_store = BikeStore.find(params[:bike_store_id])
@order.bike_store = @bike_store
authorize @order
@order.save
if @order.save
redirect_to bike_store_path(@bike_store)
else
@bike_type_list = @bike_store.bike_types
render 'new'
end
end
def edit
@bike_store = BikeStore.find(params[:bike_store_id])
@order = Order.find(params[:id])
@bike_type_list = @bike_store.bike_types
@bikes = @order.bikes
authorize @order
end
def update
@bike_store = BikeStore.find(params[:bike_store_id])
@order = Order.find(params[:id])
@bikes = @order.bikes
if @order.update(order_params)
redirect_to redirect_to bike_store_path(@bike_store)
else
render 'edit'
end
authorize @order
end
private
def set_order
@order = Order.find(params[:id])
end
def order_params
params.require(:order).permit(:arrival, :departure, :payment,
order_bikes_attributes: [:id, :bike_id, :bike_quantity, :_destroy,
bikes_attributes: [:id,:name, :bike_type_id,
bike_types_attributes: [:id, :name]]])
end
end
视图/订单/_form
<%= simple_form_for [@bike_store, @order] do |f|%>
<%= f.simple_fields_for :order_bikes do |order_bike| %>
<%= order_bike.simple_fields_for :bikes do |bike| %>
<%= bike.input :bike_type, collection: @bike_type_list, input_html:{
id: "bike_type"
}%>
<%= order_bike.association :bike, collection: @bikes, input_html:{
value: @bikes.object_id,
id: "dynamic-bikes"
} %>
<% end %>
<% end %>
<% end %>
<script >
// dynamic bikes for change category
$(document).on("change", "#bike_type", function(){
var bike_type = $(this).val();
$.ajax({
url: "/bike_stores/<%= @bike_store.id %>/orders/new",
method: "GET",
dataType: "json",
data: {bike_type: bike_type},
error: function (xhr, status, error) {
console.error('AJAX Error: ' + status + error);
},
success: function (response) {
var bikes = response["bikes"];
$("#dynamic-bikes").empty();
$("#dynamic-bikes").append('<option>Select bike</option>');
for(var i=0; i< bikes.length; i++){
$("#dynamic-bikes").append('<option value="' + bikes[i]["id"] + '">' + bikes[i]["name"] + '</option>');
}
}
});
});
// dynamic bikes for releading form (e.g. new)
$(document).ready(function(){
var bike_type = $("#bike_type").val();
$.ajax({
url: "/bike_stores/<%= @bike_store.id %>/orders/new",
method: "GET",
dataType: "json",
data: {bike_type: bike_type},
error: function (xhr, status, error) {
console.error('AJAX Error: ' + status + error);
},
success: function (response) {
var bikes = response["bikes"];
$("#dynamic-bikes").empty();
$("#dynamic-bikes").append('<option>Select bike</option>');
for(var i=0; i< bikes.length; i++){
$("#dynamic-bikes").append('<option value="' + bikes[i]["id"] + '">' + bikes[i]["name"] + '</option>');
}
}
});
});
</script>
【问题讨论】:
-
用户没有理由传递那么多信息。尤其是嵌套属性。用户应该只传递指向标准化产品表的 id 及其数量。我认为您基本上只是在这里给自己一个巨大的质量分配漏洞。
-
@Max,这是一个有趣的观点,因为我目前正在做的事情似乎确实过于复杂和脆弱。由于这是我第一次在类似电子商务的环境中工作,我将提出一个新问题,其中包含更多概念性问题,如何解决处理订单、bike_types 和相关自行车的问题。
标签: javascript jquery ruby-on-rails activerecord simple-form