You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
119 lines
4.1 KiB
119 lines
4.1 KiB
.. _auto_patch:
|
|
|
|
Automatically find and patch file functions and modules
|
|
=======================================================
|
|
The ``fake_filesystem_unittest`` module automatically finds all real file
|
|
functions and modules, and stubs them out with the fake file system functions and modules.
|
|
The pyfakefs source code contains files that demonstrate this usage model:
|
|
|
|
- ``example.py`` is the software under test. In production, it uses the
|
|
real file system.
|
|
- ``example_test.py`` tests ``example.py``. During testing, the pyfakefs fake
|
|
file system is used by ``example_test.py`` and ``example.py`` alike.
|
|
|
|
Software Under Test
|
|
-------------------
|
|
``example.py`` contains a few functions that manipulate files. For instance:
|
|
|
|
.. code:: python
|
|
|
|
def create_file(path):
|
|
'''Create the specified file and add some content to it. Use the open()
|
|
built in function.
|
|
|
|
For example, the following file operations occur in the fake file system.
|
|
In the real file system, we would not even have permission to write /test:
|
|
|
|
>>> os.path.isdir('/test')
|
|
False
|
|
>>> os.mkdir('/test')
|
|
>>> os.path.isdir('/test')
|
|
True
|
|
>>> os.path.exists('/test/file.txt')
|
|
False
|
|
>>> create_file('/test/file.txt')
|
|
>>> os.path.exists('/test/file.txt')
|
|
True
|
|
>>> with open('/test/file.txt') as f:
|
|
... f.readlines()
|
|
["This is test file '/test/file.txt'.\\n", 'It was created using the open() function.\\n']
|
|
'''
|
|
with open(path, 'w') as f:
|
|
f.write("This is test file '{}'.\n".format(path))
|
|
f.write("It was created using the open() function.\n")
|
|
|
|
No functional code in ``example.py`` even hints at a fake file system. In
|
|
production, ``create_file()`` invokes the real file functions ``open()`` and
|
|
``write()``.
|
|
|
|
Unit Tests and Doctests
|
|
-----------------------
|
|
``example_test.py`` contains unit tests for ``example.py``. ``example.py``
|
|
contains the doctests, as you can see above.
|
|
|
|
The module ``fake_filesystem_unittest`` contains code that finds all real file
|
|
functions and modules, and stubs these out with the fake file system functions
|
|
and modules:
|
|
|
|
.. code:: python
|
|
|
|
import os
|
|
import unittest
|
|
from pyfakefs import fake_filesystem_unittest
|
|
# The module under test is example:
|
|
import example
|
|
|
|
Doctests
|
|
~~~~~~~~
|
|
``example_test.py`` defines ``load_tests()``, which runs the doctests in
|
|
``example.py``:
|
|
|
|
.. code:: python
|
|
|
|
def load_tests(loader, tests, ignore):
|
|
'''Load the pyfakefs/example.py doctest tests into unittest.'''
|
|
return fake_filesystem_unittest.load_doctests(loader, tests, ignore, example)
|
|
|
|
|
|
Everything, including all imported modules and the test, is stubbed out
|
|
with the fake filesystem. Thus you can use familiar file functions like
|
|
``os.mkdir()`` as part of your test fixture and they too will operate on the
|
|
fake file system.
|
|
|
|
Unit Test Class
|
|
~~~~~~~~~~~~~~~
|
|
Next comes the ``unittest`` test class. This class is derived from
|
|
``fake_filesystem_unittest.TestCase``, which is in turn derived from
|
|
``unittest.TestClass``:
|
|
|
|
.. code:: python
|
|
|
|
class TestExample(fake_filesystem_unittest.TestCase):
|
|
|
|
def setUp(self):
|
|
self.setUpPyfakefs()
|
|
|
|
def tearDown(self):
|
|
# It is no longer necessary to add self.tearDownPyfakefs()
|
|
pass
|
|
|
|
def test_create_file(self):
|
|
'''Test example.create_file()'''
|
|
# The os module has been replaced with the fake os module so all of the
|
|
# following occurs in the fake filesystem.
|
|
self.assertFalse(os.path.isdir('/test'))
|
|
os.mkdir('/test')
|
|
self.assertTrue(os.path.isdir('/test'))
|
|
|
|
self.assertFalse(os.path.exists('/test/file.txt'))
|
|
example.create_file('/test/file.txt')
|
|
self.assertTrue(os.path.exists('/test/file.txt'))
|
|
|
|
...
|
|
|
|
|
|
Just add ``self.setUpPyfakefs()`` in ``setUp()``. You need add nothing to
|
|
``tearDown()``. Write your tests as usual. From ``self.setUpPyfakefs()`` to
|
|
the end of your ``tearDown()`` method, all file operations will use the fake
|
|
file system.
|