反序列化失败,提示__new__()只需要1个参数,但给出了2个参数。

3
当我尝试加载一个pickle列表时,它会提示:
>>> import pickle
>>> with open('tests/unit/support/modules_state.samples2.6') as f:
...     print(pickle.load(f))
...     
Traceback (most recent call last):
  File "<console>", line 2, in <module>
  File "/usr/lib/python2.6/pickle.py", line 1370, in load
    return Unpickler(file).load()
  File "/usr/lib/python2.6/pickle.py", line 858, in load
    dispatch[key](self)
  File "/usr/lib/python2.6/pickle.py", line 1083, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)

以下是加载/转储腌制列表的代码:

这里是加载/转储腌制列表的代码:

class FakeModuleNameGenerator(str):
    def __new__(cls):
        return super(FakeModuleNameGenerator, cls).__new__(cls, binascii.b2a_hex(os.urandom(15)))


class FakeModule(object):
    def __new__(cls, *args, **kwargs):
        return choice([object(), TestDouble()])


class SamplesIterator(object):
    MAX_SAMPLE_LENGTH = os.getenv('MAX_SAMPLE_LENGTH', 12) if is_executing_under_continuous_integration_server() else 6

    def __iter__(self):
        for sample_length in range(1, SamplesIterator.MAX_SAMPLE_LENGTH):
            combinations = [(FakeModuleNameGenerator(), FakeModule()) for i in range(0, sample_length)]

            for r in range(1, sample_length + 1):
                logger.info("Generating sample in length %d with r=%d" % (sample_length, r))
                yield itertools.combinations_with_replacement(combinations, r)


def load_samples():
    if is_executing_under_continuous_integration_server() and os.getenv('USE_CACHES_SAMPLES', 'false') != 'true':
        list(itertools.chain.from_iterable(SamplesIterator()))

    import platform

    version = '%s.%s' % (
        sys.version_info[0], sys.version_info[1]) if platform.python_implementation() != 'PyPy' else 'pypy'
    samples_file = '%s%s' % (get_support_path(), 'modules_state.samples-%s' % version)

    if os.path.exists(samples_file) and os.path.getsize(samples_file) == 0 or not os.path.exists(samples_file):
        with open(samples_file, 'wb') as f:
            samples = list(itertools.chain.from_iterable(SamplesIterator()))

            try:
                return samples
            finally:
                pickle.dump(samples, f, pickle.HIGHEST_PROTOCOL)
    else:
        with open(samples_file, 'rb') as f:
            return pickle.load(f)

您可以看到我正在以二进制模式读写。

以下是在加载列表之前执行相同代码的完整tox输出(第一次执行代码时执行。之后,列表已缓存):

/usr/bin/python2.7 /usr/local/bin/tox
GLOB sdist-make: /home/omer/Documents/Projects/Python/nose2-testsuite/setup.py
py26 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py26 runtests: commands[0]
.................................................................................................................................
----------------------------------------------------------------------
Ran 129 tests in 0.034s

OK
py27 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py27 runtests: commands[0]
.................................................................................................................................
----------------------------------------------------------------------
Ran 129 tests in 0.029s

OK
py33 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py33 runtests: commands[0]
.................................................................................................................................
----------------------------------------------------------------------
Ran 129 tests in 0.034s

OK
pypy inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
pypy runtests: commands[0]
.................................................................................................................................
----------------------------------------------------------------------
Ran 129 tests in 0.058s

OK
___________________________________ summary ____________________________________
  py26: commands succeeded
  py27: commands succeeded
  py33: commands succeeded
  pypy: commands succeeded
  congratulations :)

Process finished with exit code 0

一切正常时,我们都感到非常高兴,对吧?现在再次运行tox,以下是结果:

/usr/bin/python2.7 /usr/local/bin/tox
GLOB sdist-make: /home/omer/Documents/Projects/Python/nose2-testsuite/setup.py
py26 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py26 runtests: commands[0]
EE...........
======================================================================
ERROR: tests.functional.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.functional.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py26/lib/python2.6/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py26/lib/python2.6/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/functional/test_isolators.py", line 14, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
  File "/usr/lib/python2.6/pickle.py", line 1370, in load
    return Unpickler(file).load()
  File "/usr/lib/python2.6/pickle.py", line 858, in load
    dispatch[key](self)
  File "/usr/lib/python2.6/pickle.py", line 1083, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


======================================================================
ERROR: tests.unit.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.unit.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py26/lib/python2.6/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py26/lib/python2.6/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/unit/test_isolators.py", line 48, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
  File "/usr/lib/python2.6/pickle.py", line 1370, in load
    return Unpickler(file).load()
  File "/usr/lib/python2.6/pickle.py", line 858, in load
    dispatch[key](self)
  File "/usr/lib/python2.6/pickle.py", line 1083, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


----------------------------------------------------------------------
Ran 13 tests in 0.002s

FAILED (errors=2)
ERROR: InvocationError: '/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py26/bin/nose2'
py27 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py27 runtests: commands[0]
EE...........
======================================================================
ERROR: tests.functional.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.functional.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py27/local/lib/python2.7/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py27/local/lib/python2.7/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/functional/test_isolators.py", line 14, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
  File "/usr/lib/python2.7/pickle.py", line 1378, in load
    return Unpickler(file).load()
  File "/usr/lib/python2.7/pickle.py", line 858, in load
    dispatch[key](self)
  File "/usr/lib/python2.7/pickle.py", line 1083, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


======================================================================
ERROR: tests.unit.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.unit.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py27/local/lib/python2.7/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py27/local/lib/python2.7/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/unit/test_isolators.py", line 48, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
  File "/usr/lib/python2.7/pickle.py", line 1378, in load
    return Unpickler(file).load()
  File "/usr/lib/python2.7/pickle.py", line 858, in load
    dispatch[key](self)
  File "/usr/lib/python2.7/pickle.py", line 1083, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


----------------------------------------------------------------------
Ran 13 tests in 0.002s

FAILED (errors=2)
ERROR: InvocationError: '/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py27/bin/nose2'
py33 inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
py33 runtests: commands[0]
EE...........
======================================================================
ERROR: tests.functional.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/usr/lib/python3.3/unittest/case.py", line 385, in _executeTestPart
    function()
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/loader.py", line 113, in testFailure
    raise exception
ImportError: Failed to import test module: tests.functional.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/functional/test_isolators.py", line 14, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
TypeError: __new__() takes 1 positional argument but 2 were given


======================================================================
ERROR: tests.unit.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
Traceback (most recent call last):
  File "/usr/lib/python3.3/unittest/case.py", line 385, in _executeTestPart
    function()
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/loader.py", line 113, in testFailure
    raise exception
ImportError: Failed to import test module: tests.unit.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/lib/python3.3/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/unit/test_isolators.py", line 48, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
TypeError: __new__() takes 1 positional argument but 2 were given


----------------------------------------------------------------------
Ran 13 tests in 0.002s

FAILED (errors=2)
ERROR: InvocationError: '/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/py33/bin/nose2'
pypy inst-nodeps: /home/omer/Documents/Projects/Python/nose2-testsuite/.tox/dist/nose2-testsuite-0.1.0.zip
pypy runtests: commands[0]
EE...........
======================================================================
ERROR: tests.functional.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.functional.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/pypy/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/pypy/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/functional/test_isolators.py", line 14, in <module>
ERROR: InvocationError: '/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/pypy/bin/nose2'
    for current_modules_state in load_samples():
___________________________________ summary ____________________________________
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
ERROR:   py26: commands failed
    return pickle.load(f)
ERROR:   py27: commands failed
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 1421, in load
ERROR:   py33: commands failed
    return Unpickler(file).load()
ERROR:   pypy: commands failed
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 901, in load
    dispatch[key](self)
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 1126, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


======================================================================
ERROR: tests.unit.test_isolators (nose2.loader.ModuleImportFailure)
----------------------------------------------------------------------
ImportError: Failed to import test module: tests.unit.test_isolators
Traceback (most recent call last):
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/pypy/site-packages/nose2/plugins/loader/discovery.py", line 188, in _find_tests_in_file
    module = util.module_from_name(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/.tox/pypy/site-packages/nose2/util.py", line 78, in module_from_name
    __import__(name)
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/unit/test_isolators.py", line 48, in <module>
    for current_modules_state in load_samples():
  File "/home/omer/Documents/Projects/Python/nose2-testsuite/tests/common/support/isolators.py", line 63, in load_samples
    return pickle.load(f)
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 1421, in load
    return Unpickler(file).load()
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 901, in load
    dispatch[key](self)
  File "/usr/lib/pypy/lib-python/2.7/pickle.py", line 1126, in load_newobj
    obj = cls.__new__(cls, *args)
TypeError: __new__() takes exactly 1 argument (2 given)


----------------------------------------------------------------------
Ran 13 tests in 0.004s

FAILED (errors=2)

Process finished with exit code 1

我不认为这是错误,但我在文档中读到:请务必以二进制模式打开使用协议>=1创建的pickle文件。 - Martin Maillard
我们可能会认为modules_state.samples2.6只是一些随机损坏的文件。您需要向我们展示一个代码示例,该示例可以正确地将对象进行pickle,但在取消pickle时失败。 - Armin Rigo
1个回答

4

我找到了!

问题就在这里:

class FakeModuleNameGenerator(str):
    @classmethod
    def __new__(cls, *args, **kwargs):
        return str(binascii.b2a_hex(os.urandom(15)))

由于该类继承自str,因此__new__必须接受另一个参数。糟糕!


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接