[英]How to mock NODE_ENV in unit test using Jest
我想在其中一个单元测试中设置 NODE_ENV 但它总是设置为测试所以我的测试失败了。
日志服务.ts
...
const getTransport = () => {
if (process.env.NODE_ENV !== "production") {
let console = new transports.Console({
format: format.combine(format.timestamp(), format.simple()),
});
return console;
}
const file = new transports.File({
filename: "logFile.log",
format: format.combine(format.timestamp(), format.json()),
});
return file;
};
logger.add(getTransport());
const log = (level: string, message: string) => {
logger.log(level, message);
};
export default log;
loggingService.spec.ts
...
describe("production", () => {
beforeEach(() => {
process.env = {
...originalEnv,
NODE_ENV: "production",
};
console.log("test", process.env.NODE_ENV);
log(loglevel.INFO, "This is a test");
});
afterEach(() => {
process.env = originalEnv;
});
it("should call log method", () => {
expect(winston.createLogger().log).toHaveBeenCalled();
});
it("should not log to the console in production", () => {
expect(winston.transports.Console).not.toBeCalled();
});
it("should add file transport in production", () => {
expect(winston.transports.File).toBeCalledTimes(1);
});
});
...
如何在我的测试中将 process.env.NODE_ENV 设置为生产环境,最好在 beforeEach 中设置,以便我的服务中的 if 块为 false 并返回文件传输。 为简洁起见,我省略了一些代码。
您面临的核心问题是,一旦您尝试将您尝试测试的文件导入到您的测试套件中 - 其中的代码将立即被评估并且隐式调用的函数将被执行,这意味着logger.add(getTransport());
将在任何像beforeEach
这样的函数有机会设置环境变量之前被调用。
解决此问题的唯一方法是使用以下方法:
您首先需要将process.env.NODE_ENV
环境变量分配给另一个文件中的 const 变量。 我们称它为environmentVariables.ts
,其内容如下:
export const ENVIRONMENT = process.env.NODE_ENV;
然后,我们将不得不重构getTransport
以使用此变量,如下所示:
const getTransport = () => {
if (ENVIRONMENT !== "production") {
在您的测试套件中,您将不得不模拟 const 文件,这将允许您更改ENVIRONMENT
变量的设置。 注意../src/environmentVariables
是一个示例目录,您必须实际定义该文件的相关目录是什么。 此外,请确保这在describe
子句之外,为了便于阅读,最好在上面:
jest.mock('../src/environmentVariables', () => ({
ENVIRONMENT: 'production',
}));
然后,您的单元测试将在ENVIRONMENT
为production
的情况下执行。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.