PyTest设置或拆除变量

时间:2018-05-31 10:47:00

标签: python pytest

如何为每个PyTests重新实例化一个变量?

具体来说,我想每次都创建一个新的StringIO()对象。

我目前的代码是:

output = StringIO()

def info_to_string(text):
    output.write(text) 

def write_to_file(some_text):
    for row in some_text:
        info_to_string(row)

每次有新的测试夹具时,我都需要设置output

要测试的复制和可管理代码:

from io import StringIO
import pytest


output = StringIO()


def info_to_string(text):
    output.write(text)


def write_to_file(some_text):
    for row in some_text:
        info_to_string(row)


def test_1():
    write_to_file(['hello', 'there', 'what', 'is', 'up'])
    print(output)
    assert output.getvalue() == "hellotherewhatisup"


def test_2():
    write_to_file(['nothing', 'much'])
    assert output.getvalue() == "nothingmuch"
    #This will error as the output is "hellotherewhatisupnothingmuch" if run after test_1

所以每次测试都需要一个新的output = stringIO()

3 个答案:

答案 0 :(得分:1)

我不确定我是否理解你的问题,但你可以做类似下面的事情,每次将它传递给你的测试函数时都会创建一个新的StringIO实例。如果你想每次都返回一个不同的字符串,我不认为你正在寻找一个夹具,而只是一个通用的函数调用来为你工作。

import pytest
from StringIO import StringIO

@pytest.fixture(scope='function')
def info_to_string():
    output = StringIO()
    output.write('blah')
    return output

def test_something(info_to_string):
    assert isinstance(info_to_string, StringIO)
    assert info_to_string.getvalue() == 'blah'

答案 1 :(得分:1)

我认为测试文件写入操作的最简单方法是使用tempfile

但是,一旦提到StringIO作为测试策略的一部分,我的建议是将文件写入分为两部分。这为StringIO缓冲区提供了一个干净的入口点。

from pathlib import Path

from io import StringIO
import pytest

# Separate your data export to 2 functions, one operating 
# with a filename, other with a file object. 
def to_file(filename, content):
    path = Path(filename)
    if not path.exists():
        path.touch()
    with path.open('a') as f_obj:    
        write_to_file(f_obj, content)  

# This is code under test. It must not be connected to your
# test code in any way, even if you have some version of "monkey-patching"
# in mind.     
def write_to_file(file_object, content):
    """Dump *content* list of strings to *filename* with *writer*."""
    for x in content:
       file_object.write(str(x))    

# This is test with StringIO buffer
def test_write_to_file_with_buffer():
    buffer = StringIO()
    # note you make several calls to write_to_file in one test, not across tests
    # this helps keep tests isolated/independent
    write_to_file(buffer, ['hello', 'there', 'what', 'is', 'up']) 
    write_to_file(buffer, ['nothing', 'much'])
    assert buffer.getvalue() == 'hellotherewhatisupnothingmuch'

答案 2 :(得分:1)

如果有人在将来看到这个,我这样做的方法是创建一个类,重新初始化每个夹具

class WriteToString:
    def __init__(self):
        self.output = StringIO()

    def info_to_string(self, text):
        self.output.write(text)


@pytest.fixture
def write_to_string():
    return WriteToString()

并将测试更改为:

def test_2(write_to_string):
    write_to_file(['nothing', 'much'])
    assert write_to_string.output.getvalue() == "nothingmuch"