【问题标题】:How to test that related object receives a method call in an after_save callback?如何测试相关对象在 after_save 回调中接收方法调用?
【发布时间】:2023-03-11 06:38:02
【问题描述】:

我有一个简单的模型,它有一个after_save 回调,用于在状态更改时更新相关模型上的一些内容:

class Model < ApplicationRecord
  has_many :related_records
  after_update :check_change
  enum :status { 'status1', 'status2'}

  def check_change
    return unless saved_change_to_status?

    related_records.each(&:schedule_email)
  end

现在我想用 Rspec 测试这个方法。我先测试了方法是否被调用,成功了:

it "should be called"
  expect(subject).to receive(:check_change)
  subject.save
end

现在我想检查每条相关记录是否收到schedule_email方法:

  it 'should call method on related records' do
    subject.update(status: 'status2')
    subject.emails.each do |msg|
      expect(msg).to receive(:schedule_email)
    end
  end

不知何故,这不起作用。在没有任何运气的情况下,我还尝试在期望之后调用update。我无法理解出了什么问题。有什么想法吗?

编辑:我还在方法中的保护子句之后创建了一个断点。在测试期间它停止执行,所以我假设 schedule_email 方法正在所有相关记录上被调用......我应该以不同的方式expect 吗?

【问题讨论】:

    标签: ruby-on-rails rspec


    【解决方案1】:

    expect(msg).to receive(:schedule_email) 应该在实际测试调用之前进行,以正确设置消息期望。所以它宁愿是:

    it 'should call method on related records' do
      subject.emails.each do |msg|
        expect(msg).to receive(:schedule_email)
      end
      subject.update(status: 'status2')
    end
    

    【讨论】:

    • 我也测试过......但仍然没有运气:(
    • 我将related_records.each(&amp;:schedule_email) 部分重构为它自己的(私有)方法,当我expect(subject).to receive(:schedule_emails) 时称为schedule_emails,它通过了。不幸的是,这仍然不能让我测试该方法的功能。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2013-03-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-01-06
    • 1970-01-01
    • 2012-02-10
    相关资源
    最近更新 更多