Overview of proxyquire
masterrequire to make overriding dependencies during testing easy and unobtrusive. It allows you to stub modules without changing your source code. Non-overridden methods of a module behave like the original by default.repository·master·Indexed 25 days ago
https://github.com/thlorenz/proxyquireA Node.js tool that proxies the require function to allow overriding dependencies during testing. It enables stubbing modules without changing source code, supporting features like callThru control, module reloading via noPreserveCache(), and global overrides using @global and @runtimeGlobal properties.
require to make overriding dependencies during testing easy and unobtrusive. It allows you to stub modules without changing your source code. Non-overridden methods of a module behave like the original by default.To test how your code behaves when a module is missing (e.g., inside a try/catch block), set the stub for that module to null. This works even if the module is actually present on the system.
var foo = proxyquire('./foo', { cluster: null });To override dependencies in your tests, import proxyquire and call it with the path to the module you want to test and an object containing your stubs.
Note: Module paths in the stubs object must be relative to the tested module, not the test file itself. Specify them exactly as they appear in the require statements inside the module being tested.
var proxyquire = require('proxyquire');
// Stubbing a dependency named 'path' in the module './foo'
var foo = proxyquire('./foo', { 'path': pathStub });proxyquire v0.3.x has been removed. If your codebase relies on the older API, you must pin your proxyquire version to ~0.6 in your package.json to maintain functionality.You can use proxyquire to load a module while simultaneously providing stubs for its dependencies. This is typically done by passing an object where keys are the dependency paths and values are the stub objects.
/*
* Option a) Resolve and override in one step
*/
var foo = proxyquire('../foo', {
'./bar': { toAtm: function (val) { return 0; } }
});
/*
* Option b) Resolve with empty stub and add overrides later
*/
var barStub = { };
var foo = proxyquire('../foo', { './bar': barStub });
// Add override
barStub.toAtm = function (val) { return 0; };You can control whether all future stubs resolved by a proxyquire instance default to calling through or not.
require('proxyquire').noCallThru().proxyquire.callThru() to restore default behavior.You can override a global noCallThru() setting for a specific module by passing '@noCallThru': false in that module's stub configuration.
If a module performs a require call inside a function (at runtime) rather than at the top level (during module initialization), use the @runtimeGlobal property.
This ensures that the stub is applied every time the module is requested via require at runtime, because the module cache is bypassed. Use this only if you cannot guarantee that your modules have static require behavior, as it can lead to subtle bugs.
var stubs = {
'd': {
method: function(val) {
console.info('hello world');
},
'@runtimeGlobal': true
}
};By default, proxyquire behaves like Node.js require and pulls modules from the cache. To ensure a module is loaded fresh every time (to reset state or re-initialize), use noPreserveCache().
To return to standard Node.js caching behavior, use preserveCache().
If you are overriding a module that exports a function directly, you can still attach special properties like @global by using Object.assign or by assigning properties to a named function variable.
function foo () {}
proxyquire('./bar', {
foo: Object.assign(foo, {'@global': true})
});The primary API for proxyquire is proxyquire({string} request, {Object} stubs).
request: The path to the module you want to test (e.g., '../lib/foo').stubs: An object where keys are module paths (relative to the tested module) and values are the stubs. Stubs can be functions, objects, or key/value pairs of functions/properties representing the override.proxyquire('./foo', { 'path': pathStub });Use the @global property to override every require of a module, even transitively. This is useful when a dependency is required deep within a dependency tree and you cannot reach it via standard stubbing.
Warning: This is highly intrusive. It bypasses the Node.js require cache, meaning module initialization code will be re-executed for each require. This can cause unexpected side effects if modules perform actions like opening files or setting up listeners during initialization.
To use it, add '@global': true to your stub object.
var bazStub = {
method: function() {
console.info('goodbye');
}
};
var stubs = {
'./baz': Object.assign(bazStub, {'@global': true})
};
var proxyquire = require('proxyquire');
var foo = proxyquire('./foo', stubs);By default, if a method is not found on a stub, proxyquire calls the original dependency (this is called callThru). You can disable this behavior to ensure stubs are used strictly or to handle classes/instances correctly.
If your stub is a class, you can set a static property:
class MockClass {
static '@noCallThru' = true;
}If your stub is a class instance, use a getter:
class MockClass {
get '@noCallThru'() {
return true;
}
}You can add the '@noCallThru': true key to the stub object for a specific module:
var foo = proxyquire('./foo', {
path: {
extname: function (file) { /* stub */ },
'@noCallThru': true
}
});var foo = proxyquire('./foo', {
path: {
extname: function (file) { ... }
, '@noCallThru': true
}
});