我有一个模型Appointment,它禁止使用过去的日期创建对象,或者如果字段日期在过去,则禁止更新。
class Appointment < ApplicationRecord
belongs_to :user
...
validate :not_past, on: [:create, :update]
private
...
def not_past
if day.past?
errors.add(:day, '...')
end
end
end
但我需要使用RSpec制作一个测试文件,以测试如果字段日期是过去的日期,它是否真的无法编辑。
require 'rails_helper'
RSpec.describe Appointment, type: :model do
...
it 'Cannot be edited if the date has past' do
@user = User.last
r = Appointment.new
r.day = (Time.now - 2.days).strftime("%d/%m/%Y")
r.hour = "10:00"
r.description = "Some Description"
r.duration = 1.0
r.user = @user
r.save!
x = Appointment.last
x.description = "Other"
expect(x.save).to be_falsey
end
...
end
问题是,由于一个错误禁止在过去一天创建Appointment对象,因此测试无法准确。
我该怎么做才能强迫,甚至可能制作一个有过去日期的假物体,这样我才能最终测试它?
您可以使用update_attribute来跳过验证。
it 'Cannot be edited if the date has past' do
@user = User.last
r = Appointment.new
r.day = (Time.now - 2.days).strftime("%d/%m/%Y")
r.hour = "10:00"
r.description = "Some Description"
r.duration = 1.0
r.user = @user
r.save!
x = Appointment.last
x.description = "Other"
r.update_attribute(:day, (Time.now - 2.days).strftime("%d/%m/%Y"))
expect(x.save).to be_falsey
end
此外,您的测试中有很多噪声(未断言的数据(,您应该通过创建辅助函数或使用工厂来避免这些噪声。
it 'Cannot be edited if the date has past' do
appointment = create_appointment
appointment.update_attribute(:day, (Time.now - 2.days).strftime("%d/%m/%Y"))
appointment.description = 'new'
assert(appointment.valid?).to eq false
end
def create_appointment
Appointment.create!(
day: Time.now.strftime("%d/%m/%Y"),
hour: '10:00',
description: 'description',
duration: 1.0,
user: User.last
)
end
此外,您还测试了falsey
,它也将匹配零值。在这种情况下,您要做的是用eq false
测试false
。