gpt4 book ai didi

ruby - 如何避免过度测试私有(private)方法的行为?

转载 作者:数据小太阳 更新时间:2023-10-29 08:56:25 25 4
gpt4 key购买 nike

鉴于:

  • 测试私有(private)方法不是一个好的做法。
  • 具有许多公共(public)方法的接口(interface)也不是一个好的做法。

假设我有以下代码:

module RedisHelper
private

def key_for(id)
[prefix, id].join('-')
end

def prefix
self.class.name.split('::').last.underscore
end
end
class X
include RedisHelper

def perform(id)
key = key_for(id)
redis.sadd(key, [:bar])
end
end
class Y
include RedisHelper

def perform(id)
key = key_for(id)
redis.set(key, :foo)
end
end

测试 key_for/prefix 方法的行为而不过度测试它们的最佳方法是什么?我不想在测试类 XY 时重复它的逻辑。

我认为将 RedisHelper 的方法公开是不好的,因为它们在 XY 中也是公开的。

最佳答案

直接回答

直接测试模块:

def test_redis_key_namespacing
dummy_class = Class.new do # this anonymous class will not pollute namespace
include RedisHelper

public :key_for

def self.name
'Dummy'
end
end

assert_equal 'Dummy-hello', dummy_class.new.key_for('hello')
end

总体建议

我建议不要使用 RedisHelper 模块。尝试将“Redis 命名空间代码”逻辑保持在一起并与其他代码分开是件好事,但您真正拥有的是到处都是“Redis 命名空间代码”。

key_forXY 中——它们必须在每次调用 redis 时自己处理命名空间。此外,key_forprefix 都可以在任何这些类中调用(子类任何其他包含的模块) 即使它们都是“Redis 命名空间”的内部。

看起来“Redis 键命名空间”是您应用程序中的一个重要概念。它被不同的不相关区域在多个地方重复使用。让它成为“一件事”:

class NsRedis
key_methods = Redis.instance_methods(false).select do |m|
Redis.instance_method(m).parameters.first == [:req, :key]
end

# some metaprogramming, but it's static, much better than method_missing!
key_methods.each do |m_name|
define_method(m_name) do |key, *args|
Redis.current.public_send("#{@namespace}:#{key}", *args)
end
end

def initialize(namespace)
@namespace = namespace
end
end

# Now, anywhere you're going to need it, including tests:
class X
def initialize
@redis = NsRedis.new(self.class.name)
end

def do_something
@redis.set(:my_key, 'my_val') # "unaware" of the namespacing at usage
end
end

关于ruby - 如何避免过度测试私有(private)方法的行为?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55731560/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com