【问题标题】:Is there a way to test environment defined dynamic validations in a model with RSpec?有没有办法在 RSpec 模型中测试环境定义的动态验证?
【发布时间】:2014-12-22 16:55:53
【问题描述】:

我有一个模型,其中一些验证是根据它们正在运行的环境(通过 ENV 变量)动态定义的。

例如,我在开发和测试中使用ENV['NETWORK'] 变量设置为'testnet3' 网络,并在生产中设置为'bitcoin' 网络。然后,假设我有一个名为 Transaction 的模型,其动态验证集如下:

Transaction < ActiveRecord::Base
  validates :output_address,
    presence: output_address_presence_requirement_for ENV['NETWORK'] 
end

# somewhere exists the 'output_address_presence_requirement_for' function

def output_address_presence_requirement_for(network)
  if network == 'testnet3'
    false
  else
    true
  end
end

然后,我有两组规范:一组用于模型在使用“比特币”网络(生产)时的行为,另一组用于使用“testnet3”网络(开发/测试)时的行为。它们在单独运行每个文件时按预期工作,但在一个接一个地运行时,例如在rspec spec/models 上,更改 ENV 变量的值似乎没有效果,第二组规范失败。

我尝试过使用climate_control,对 ENV 的调用进行存根,甚至直接设置 ENV 变量的值,每种情况的结果都相同:如果单独运行,则测试通过,如果第二组测试失败,则将它们作为一个整体运行。

似乎 RSpec 在运行一组测试时重用了相同的 Rails 环境,并且在调用第一组测试时定义了模型验证,但在调用第二组测试时没有重新定义。

我可以根据使用的网络使用具有不同验证的不同模型来存储信息,但我想避免它,因为它需要控制器上更复杂的逻辑和更多规范。

是否可以在 RSpec 方面做一些事情,使其在运行规范文件之前刷新环境?

【问题讨论】:

    标签: ruby-on-rails validation rspec model


    【解决方案1】:

    简单来说:

    我想一旦你完全运行测试,文件是必需的,并且验证器被定义一次

    因此,即使您在测试中更改了ENV['NETWORK'] 的值,presence 键的值也保持不变。

    使用每次验证对象时读取环境变量的验证方法。

    这是您分享的示例代码示例:

    validate :validator_name
    
    def validator_name
      if (ENV['NETWORK'] != 'testnet3') && output_address.blank?
        # add errors here
      end
    end
    

    【讨论】:

    • 这种方法非常有效地存根 ENV 并且还使用了climate_control。
    猜你喜欢
    • 2017-08-20
    • 1970-01-01
    • 1970-01-01
    • 2011-11-24
    • 2014-12-01
    • 1970-01-01
    • 2023-03-19
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多