我有一个具有多个验证的对象。
批准模型的要点:https://gist.github.com/1579150(旁注,我知道电子邮件域验证器不起作用......)
关键是,如果这些验证失败,我希望对象保存,但然后在approval.issue = true上设置一个值。 Approval.issue是一个布尔字段,默认为false,但如果对象验证失败,我希望系统管理员能够看到它,然后适当地处理它。
为了使它更加白痴,最好有一些可以强制用户进行更改的验证,但有些可以免除,只会触发.issue字段为真。
例如,如果电子邮件属于正确的域,但系统中不存在该电子邮件,则会将其保存,但会设置issue =>真正。然后,我可以为Approvals设置一个简单的视图,其中:issue => :真正。然后管理员可以修改或删除错误的批准。
想法?
来自要点的代码:
class Approval < ActiveRecord::Base
class ApproverEmailValidator < ActiveModel::EachValidator
def validate_each(approval, attribute, value)
approval.errors[attribute] << "must be a valid e-mail address in our system" unless is_valid_email?(value)
end
protected
def is_valid_email?(address)
User.find_by_email(address)
end
end # End Approver Validator
class EmailDomainValidator < ActiveModel::EachValidator
def email_domain_is?(domain)
unless /ravennainteractive.com$/ =~ email(domain)
errors.add(:email, "You must Use an Eddie Bauer email address")
end
end
end #End Email Domain Validator
belongs_to :recommendation
attr_accessible :approval, :email, :user_id
validates :email, :email_domain
validates :next_approver_email, :approver_email => { :if => :recently_approved? }
before_save :create_next_approval
after_create :approval_notification
attr_accessor :next_approver_email
def recently_approved?
self.approved_changed? && self.approved?
end
def create_next_approval
next_approval = self.recommendation.approvals.build(:email => self.next_approver_email, :user_id => User.find_by_email(next_approver_email))
next_approval.save if next_approver_email.present? && recently_approved?
end
def email_domain_is?
unless /ravennainteractive.com$/ =~ email
errors.add(:email, "You must Use an Eddie Bauer email address")
end
end
private
def approval_notification
ApprovalMailer.needs_approval(self).deliver
end
end
答案 0 :(得分:0)
如果存在可疑输入,您可以实施Approval的观察者,它将在保存之前分析您的对象,并将问题设置为“true”。
更新:这是如何实现观察者的简短指南:
rails生成观察者 - 在此步骤之后,您将看到_observer.rb文件。
实施所需方法。这是从我的一个项目中提取的简单示例(看起来你应该使用“before_save”方法):
class HomeworkObserver < ActiveRecord::Observer
def after_create(homework)
TeacherMailer.send_later(:student_submitted_homework, homework)
end
def after_save(homework)
if (homework.checked)
StudentMailer.send_later(:teacher_checked_homework, homework)
end
end
end
此外,您需要通过将其添加到config / application.rb来启用观察者,例如:
config.active_record.observers = :homework_observer
官方文档:http://api.rubyonrails.org/classes/ActiveRecord/Observer.html