datetime_select的多参数错误
我的表单中有以下代码。
{:day => 'Day', :month => 'Month', :year => 'Year'}, :start_year => Date.today.year, :end_year => Date.today.year + 2, :minute_step => 15, :include_blank => false) %> if either one is blank.
当其中一个字段留空时, 我得到:
1 error(s) on assignment of multiparameter attributes
正在传递的参数是:
{"utf8"=>"✓", "authenticity_token"=>"kQpfsj5RxnDtxkvBdwPEFnX1fY6euKnMQeDRAkvJvIE=", "event"=>{"description"=>"", "venue"=>"", "street"=>"", "city"=>"", "country_id"=>"", "date_time(1i)"=>"", "date_time(2i)"=>"", "date_time(3i)"=>"", "date_time(4i)"=>"00", "date_time(5i)"=>"00", "ticket_url"=>""}, "x"=>"94", "y"=>"12"}
谁知道为什么会这样?
在这个链接上似乎有一个“脏”修复,但也许在Rails 3中有更好的解决方案?
基督教。 这是Rails中的一个错误,它检查数据库以推断多参数属性所需的类型。 我的猜测是你的“date_time”属性与数据库中的时间列没有关联。
我最近解决了这个问题,我想要一个非数据库属性来接受多参数属性,这是我能提出的最佳解决方案:
我发现自己想要设置一个attr_accessor
来处理一个带有f.datetime_select
帮助器的form_for
标签中的日期到我的模型。 所以这就是我所拥有的:
模型:
attr_accessor :my_time
视图:
<%= f.datetime_select :my_time %>
不幸的是,当我提交表单时,我得到了这个:
1 error(s) on assignment of multiparameter attributes
事实certificate,这实际上是一个Rails错误,已经提交了一张票。 与此同时,我们如何使这项工作? 我能找到的唯一具有远程吸引力的解决方案是使用attr_accessor
作为attr_accessor
的替代attr_accessor
。 所以…
模型:
composed_of :my_time, :class_name => 'Time', :mapping => %w(Time to_s), :constructor => Proc.new{ |item| item }, :converter => Proc.new{ |item| item }
我对composed_of
方法几乎一无所知,所以你应该对它进行自己的阅读,但我所知道的是它为给定的实例变量创建了一个reader和writer,更重要的是,setter接受了多参数属性。 我如何选择选项:
class_name:我们期望的类的名称。 在这种情况下, Time
mapping:第一个参数是类,第二个参数似乎适用于类的实例响应的任何方法。 我选择了to_s
构造函数:不确定这是如何工作的。 当@my_time
nil
时似乎被调用。
转换器:不确定这应该如何工作。 似乎是从my_time =调用,但似乎没有应用质量分配。 我遇到这个解决方案的一个问题是,时间是以UTC而不是环境的时区设置的。 所以不幸的是我们不能直接使用my_time,而是需要将其转换为适当的时区:
Time.zone.parse(my_time.to_s(:number))
ActiveRecord :: MultiparameterAssignmentErrors是什么意思?
def initialize(attributes={}) date_hack(attributes, "deliver_date") super(attributes) end def date_hack(attributes, property) keys, values = [], [] attributes.each_key {|k| keys << k if k =~ /#{property}/ }.sort keys.each { |k| values << attributes[k]; attributes.delete(k); } attributes[property] = values.join("-") end
使用没有数据库属性支持的日期下拉列表时遇到了同样的问题。 我写了一个小的Rack中间件来解决这个问题:
class DateParamsParser def initialize(app) @app = app end def call(env) if %w{POST PUT}.include? env['REQUEST_METHOD'] params = Rack::Utils.parse_query(env["rack.input"].read, "&") # selects only relevant params like 'date1(1i)' filtered_params = params.select{ |key, value| key =~ /\(\di\)/ } # delete date params filtered_params.each { |key, value| params.delete(key) } # returns something like {'date1' => [2012, 5, 14], 'date2' => [2002, 3, 28]} date_array_params = filtered_params.sort.reduce({}) do |array_params, keyvalue| date_key = keyvalue.first.match(/(.+)\(/)[1] + ']' array_params[date_key] ||= [] array_params[date_key] << keyvalue.last array_params end # Creates params with date strings like {'date1' => '2012-5-14', 'date2' => '2002-3-28'} date_params = Hash[date_array_params.map{ |key, date_array| [key, date_array.join('-')] }] params.merge! date_params env["rack.input"] = StringIO.new(Rack::Utils.build_query(params)) env["rack.input"].rewind end @app.call(env) end end
在application.rb中我放了
config.middleware.insert_before ActionDispatch::ParamsParser, "DateParamsParser"
请注意,我只在这里建立一个日期字符串。 因此,如果您还需要时间,则需要以不同方式构建date_params
。
我在下面的模型中遇到了同样的问题
class Reservation < ActiveRecord::Base attr_accessor :sid, :check_in, :credit_card_number, :expiration_date attr_accessible :expiration_date end
与到期日期字段相对应的表格:
<%= f.label :expiration_date %> <%= f.date_select(:expiration_date, start_year: Time.now.year + 3, :end_year => Time.now.year - 3, discard_day: true) %>
正如@gabeodess所提到的,问题是检查数据库以相应地推断出类型我为它做的解决方案是将以下代码添加到模型中以在这种情况下放置所需属性的类型:expiration_date所以模型被修改为下列
class Reservation < ActiveRecord::Base attr_accessor :sid, :check_in, :credit_card_number, :expiration_date attr_accessible :expiration_date columns_hash["expiration_date"] = ActiveRecord::ConnectionAdapters::Column.new("expiration_date", nil, "date") end
希望这很有用
从代码中删除:include_blank => false
。
<%= f.datetime_select(:date_time, :prompt => {:day => 'Day', :month => 'Month', :year => 'Year'}, :start_year => Date.today.year, :end_year => Date.today.year + 2, :minute_step => 15 %>
谢谢….
我遇到了同样的问题。 我刚为该属性添加了attr_accessible ,它运行正常。
希望能帮助到你。