【发布时间】:2019-05-05 22:14:16
【问题描述】:
我编写了一个遵循标准复式记账法的会计系统。
有一个称为“试算表”的双重记账功能,您可以在其中验证整个系统是否正确,因为当您运行它时,它始终等于0.00
我已经编写了测试并且总是在系统“停止”时运行我的试算表,但是在为大量记录播种期间写入大量数据库负载的情况下,我注意到我的试算表在 10 次尝试中有 1 次是错误的。
当它处于静止状态(没有插入)时,它总是在 0.00 正确。
当我插入事务时,它们总是在事务中,如下所示:
2000.times do |i|
ActiveRecord::Base.transaction do
puts "#{i} ==================================================================="
entry = JournalEntry.create!(description: 'Purchase mower on credit', user: user)
entry.line_items.create!(amount: Money.from_amount(1551.75).cents, account: property.accounts.find_by(name: 'Equipment'), side: :debit)
entry.line_items.create!(amount: Money.from_amount(1551.75).cents, account: property.accounts.find_by(name: 'Accounts Payable'), side: :credit)
end
end
它在负载下中断的事实让我觉得我不了解 Rails 事务如何工作的重要内容......
这可能是什么原因造成的?
FWIW 我的试算表函数 (GeneralLedger.new(property).trial_balance) 执行以下伪 SQL(NOT 在事务中):
SELECT sum(...) WHERE account = 'asset'
SELECT sum(...) WHERE account = 'liability'
SELECT sum(...) WHERE account = 'equity'
SELECT sum(...) WHERE account = 'income'
SELECT sum(...) WHERE account = 'expense'
然后我根据会计公式将它们加在一起得到 0.00:
def trial_balance
balance_category(:asset) - (balance_category(:liability) + balance_category(:equity) + balance_category(:income) - balance_category(:expense))
end
balance_category 函数触发每个 SELECT 总共 5 次,每个类别一次。
因为它返回 0 这意味着它在插入中途时以某种方式进行选择............我不知道这是怎么发生的?
我可以理解如果日记帐分录/行项目的创建不在事务中并且它正在选择中途插入的行,但它应该只在事务结束后从整个组中选择?
【问题讨论】:
-
您需要执行
SELECT account, SUM(...) WHERE account IN ('asset', 'liability', ...) GROUP BY account,因为这可能是一次性声明。 Rails 通过在where(account: [ 'asset', ... ])类型范围内使用数组来支持这一点。 -
我在一分钟前才真正意识到这一点????????♂️它是因为在单独进行选择时添加了有效交易。如果您将其标记为答案,那就错了,也许您可以输入实际的语法。谢谢!
标签: ruby-on-rails ruby postgresql activerecord ruby-on-rails-5