我试图根据Railscast第033集插件制作一个Ruby Gem。我创建了gem并将其作为stringify-time
上传到Rubygems.org,但是setter方法无效。
宝石的主要部分
module StringifyTime
def stringify_time(*names)
names.each do |name|
define_method "#{name}_string" do
read_attribute(name).to_s(:db) unless read_attribute(name).nil?
end
define_method "#{name}_string=" do |time_str|
begin
write_attribute("#{name}", Time.zone.parse(time_str))
rescue ArgumentError
instance_variable_set("@#{name}_invalid", true)
end
end
define_method "#{name}_invalid?" do
instance_variable_get("@#{name}_invalid")
end
end
end
end
ActiveRecord::Base.send(:extend, StringifyTime)
传入属性符号,并创建getter和setter方法。 getter方法有效,但是当我尝试通过表单更新属性时,数据不会被保存。
使用任务模型中的stringify_time
方法
class Task < ActiveRecord::Base
validates_presence_of :name
stringify_time :due_at
# def due_at_string
# due_at.to_s(:db)
# end
# def due_at_string=(due_at_str)
# self.due_at = Time.parse(due_at_str)
# rescue ArgumentError
# @due_at_invalid = true
# end
def validate
errors.add :due_at, 'is invalid' if due_at_invalid? # @due_at_invalid
end
end
当我取消注释我手动编写的setter方法时,我可以编辑属性。
答案 0 :(得分:0)
在我尝试在rails控制台中使用生成的方法之后,如评论中建议的@ matjis-van-zuijlen,我能够更新due_at
属性。问题是我没有在控制器中将:due_at_string
列入白名单。
def task_params
params.require(:task).permit(:name, :due_at, :due_at_string)
end