Mocking the file system
When writing tests, it’s common to run up against code that relies on file system access. People often end up including a bunch of test fixtures along with their code. Tests might create some temporary space, copy fixtures in place, run code, make assertions about what was read or written, and then clean up. The result can be fragile when working across multiple operating systems and leads to long test run times. In cases like this, a mock file system provides an alternative.
The mock-fs
module
In Node, the fs
module provides file system access. The mock-fs
module allows the built-in fs
module to be temporarily backed by an in-memory file system during testing. The code below shows how a mock file system can be set up with a few directories and files:
With the mock file system in place, any code that uses the fs
module will have access your fake files.
And when you’re done working with mocks, you can restore access to the real file system.
The mock()
function allows you to create directories, regular files, or symlinks with additional configuration options. For example, you can set the file modification time, user or group id, permissions, and more. On POSIX-compliant systems (where process.getuid()
and process.getgid()
are available), file access is restricted based on the mode
setting. See the readme for more detail on usage.
How it works
The methods exported by Node’s fs
module delegate to methods provided by the native bindings. For example, fs.open()
and fs.openSync()
call binding.open()
. The mock-fs
package implements the binding
methods with an in-memory file system.
When you require('mock-fs')
, an internal copy of the fs
module with a settable binding is loaded. Methods from this modified module are copied to the fs
module’s exports, making it so that any other modules that require('fs')
get methods that are backed by a configurable binding
. From then on, calls to mock()
set the binding
to the in-memory backed one, and calls to mock.restore()
set the binding
back to the original, native implementation.