0

我正在使用 Starling 和 Workling 来处理我的应用程序中的后台任务,这是一个 Swoopo 风格的拍卖网站。在这种情况下,后台任务是一个通知系统,用于监控拍卖并通知获胜者。在创建拍卖对象时调用监视器。我的问题是我的监控代码找不到它应该监控的拍卖。这是代码:

失败的单元测试:

class AuctionTest < ActiveSupport::TestCase
  test "are monitored when created" do
    auction = Auction.new(
      :name => "A TV",
      :markdown => "A large TV",
      :starting_bid => 0.01,
      :bid_increment => 0.01,
      :starts_at => Time.now(),
      :ends_at => Time.now() + 5.seconds,
      :active => true
    )
    auction.save
    Bid.place(@current_user, auction)

    sleep(10) #when bids are placed, time is added to the end of the auction so wait

    assert auction.won?
    assert_equal @current_user.id, auction.winner_id
  end
end

工人代码:

class AuctionsWorker < Workling::Base
  def monitor(options)
    active = true
    ends_at = options[:original_ends_at]
    while active
      auction = Auction.find(options[:auction_id]) #this is the record that cannot be found
      if auction.won?
        active = false
        winner = User.find(auction.high_bidder).id
        auction.update_attribute(:winner_id, winner)
      else
        until Time.now() >= ends_at
          sleep(1)
        end
      end
    end
  end
end

调用工人的代码:

class Auction < ActiveRecord::Base
  def after_create
    AuctionsWorker.asynch_monitor(:auction_id => self.id, :original_ends_at => self.ends_at) if self.active?
  end
end

每次运行测试时,我都会收到一条错误消息,告诉我无法找到提供给工作人员的拍卖。

有没有人有任何想法?如果有帮助,我在 Mac OSX 10.6.2 Macbook Pro 上使用 rails 2.3.5、sqlite3 和最新的 Starling、Workling 以及所有其他相关的 gem。

感谢您的所有意见。

4

1 回答 1

0

你应该因为创建“swoopo 式”拍卖而被否决,我为帮助你而感到肮脏。

after_create() 在 Base.save 之后调用尚未保存的新对象(不存在记录)

所以 after_create 有点用词不当 - 记录还没有真正创建。

http://api.rubyonrails.org/classes/ActiveRecord/Callbacks.html#M002142

您可以添加自己的 id 字段,并让工作进程在数据库中搜索该 id,每次找不到它时休眠几秒钟(最多达到一些预设的失败限制)。

或者 - 您可以尝试 github 上的几个 after_commit 插件之一,这些插件在数据库更新后被调用。

这是一个:

http://github.com/delynn/after_commit

于 2010-02-10T00:46:14.000 回答