带命令行参数的鼻子测试脚本

时间:2009-11-02 10:41:57

标签: python command-line-arguments nose

我希望能够运行一个接受命令行参数的鼻子测试脚本。例如,类似的东西:

test.py

import nose, sys

def test():
    # do something with the command line arguments
    print sys.argv

if __name__ == '__main__':
    nose.runmodule()

但是,每当我使用命令行参数运行它时,我都会收到错误:

$ python test.py arg
E
======================================================================
ERROR: Failure: ImportError (No module named arg)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/site-packages/nose-0.11.1-py2.6.egg/nose/loader.py", line 368, in loadTestsFromName
    module = resolve_name(addr.module)
  File "/Library/Frameworks/Python.framework/Versions/2.6/lib/python2.6/site-packages/nose-0.11.1-py2.6.egg/nose/util.py", line 334, in resolve_name
    module = __import__('.'.join(parts_copy))
ImportError: No module named arg

----------------------------------------------------------------------
Ran 1 test in 0.001s

FAILED (errors=1)

显然,nose试图对sys.argv中传递的参数做一些事情。有没有办法让鼻子忽略这些论点?

5 个答案:

答案 0 :(得分:17)

好吧,我讨厌“你为什么要那样做?”答案和任何人一样,但我必须在这里做一个。我希望你不介意。

我认为做任何你想做的事都不在框架鼻子的范围内。 Nose适用于自动测试。如果必须传入命令行参数以使测试通过,那么它不会自动化。现在,你可以做的事情是这样的:

import sys

class test_something(object):
    def setUp(self):
        sys.argv[1] = 'arg'
        del sys.argv[2] # remember that -s is in sys.argv[2], see below
    def test_method(self):
        print sys.argv

如果你运行它,你得到这个输出:

[~] nosetests test_something.py -s
['/usr/local/bin/nosetests', 'arg']
.
----------------------------------------------------------------------
Ran 1 test in 0.001s

OK

(如果你想查看stdout上的内容,请记住传入-s标志)

但是,我可能仍然建议不要这样做,因为如果你能避免它,那么在自动化测试中弄乱全局状态通常是一个坏主意。我可能会做的是调整我想要测试的任何代码来获取argv列表。然后,您可以在测试期间传递您想要的任何内容,并在生产中传递sys.argv

<强>更新

  

我需要这样做的原因是   因为我正在测试多个   同一个库的实现。   测试那些实现是   我使用单鼻子脚本,   接受作为命令行   论证它应该的图书馆   导入进行测试。

听起来你可能想尝试编写一个鼻子插件。这很容易做到。 Here are the latest docs.

答案 1 :(得分:11)

您可以使用其他方法将内容输入代码:

import os

print os.getenv('KEY_THAT_MIGHT_EXIST', default_value)

然后记住在跑鼻子之前设置你的环境。

答案 2 :(得分:7)

我认为这是完全可以接受的情况。我还需要做类似的事情,以针对不同的场景(dev,qa,prod等)运行测试,并且我需要为每个环境提供正确的URL和配置。

我找到的解决方案是使用 nose-testconfig 插件(link here)。它不是完全传递命令行参数,而是创建包含所有参数的配置文件,然后在执行nose-tests时将此配置文件作为参数传递。

配置文件具有以下格式:

[group1]
env=qa

[urlConfig]
address=http://something

[dbConfig]
user=test
pass=test

您可以使用以下方式阅读参数:

from testconfig import config

print(config['dbConfig']['user'])

答案 3 :(得分:3)

现在我正在使用以下黑客:

args = sys.argv[1:]
sys.argv = sys.argv[0:1]

只是将参数读入局部变量,然后删除sys.argv中的所有其他参数,这样鼻子就不会被它们混淆。

答案 4 :(得分:2)

只是运行鼻子并传入参数将无法正常工作,因为鼻子会尝试将参数解释为鼻子参数,因此您会遇到所遇到的问题。

我不认为鼻子支持参数直接传递但是这个鼻子插件nose-testconfig允许你编写如下的测试:

from testconfig import config
def test_os_specific_code():
    os_name = config['os']['type']
    if os_name == 'nt':
        pass # some nt specific tests
    else:
        pass # tests for any other os