超级测试在每次测试中更改 url
supertest changing url at every test
我是后端开发的新手,我遇到了一个我不明白的问题。
我设置了我的 API 的第一个路由叫 "health" 谁只是 return 一个简单的消息来知道我的服务器是否启动。
这条路线看起来像预期的那样工作。
然而,
当我尝试使用方法 "toMatchSnapshot" 测试这条路线时
开玩笑 API,由于 url 中的不断变化,测试未通过。
我的测试文件"index.test.ts":
const request = supertest.agent(app);
describe("app", () => {
it("should return a successful response for GET /health", async () => {
const res = await request.get("/health");
res.header = omit(res.header, ["date"]);
expect(res).toMatchSnapshot();
});
});
服务器索引"index.ts":
const app = express();
expressService(app);
if (require.main === module) {
app.listen(PORT, () => {
console.log("server started at http://localhost:" + PORT);
});
}
export default app;
我的函数"expressService":
const expressService = (app: Application) => {
app.use(cors());
app.use(express.urlencoded({ extended: true }));
app.use(express.json());
app.use(api);
};
export default expressService;
我的 PORT 变量:PORT = 3000;
- "url": "http://127.0.0.1:49694/health",
+ "url": "http://127.0.0.1:52568/health",
这是测试失败的地方。
感谢您的回答。
supertest
的文档说:
You may pass an http.Server, or a Function to request() - if the server is not already listening for connections then it is bound to an ephemeral port for you so there is no need to keep track of ports.
您需要传递一个Node.js http.Server
对象给supertest.agent()
,然后您可以使用特定的PORT
进行测试。
解决方法如下:
index.ts
:
import express from 'express';
import expressService from './expressService';
import http from 'http';
const app = express();
const PORT = process.env.PORT || 3000;
expressService(app);
function createHttpServer() {
const httpServer: http.Server = app.listen(PORT, () => {
console.log('server started at http://localhost:' + PORT);
});
return httpServer;
}
if (require.main === module) {
createHttpServer();
}
export default createHttpServer;
expressService.ts
:
import { Application } from 'express-serve-static-core';
import express, { Router } from 'express';
import cors from 'cors';
const expressService = (app: Application) => {
app.use(cors());
app.use(express.urlencoded({ extended: true }));
app.use(express.json());
const api = Router();
api.get('/health', (req, res) => {
res.sendStatus(200);
});
app.use(api);
};
export default expressService;
index.spec.ts
:
import createHttpServer from './';
import { agent } from 'supertest';
import { omit } from 'lodash';
const httpServer = createHttpServer();
const request = agent(httpServer);
afterAll(done => {
httpServer.close(done);
});
describe('app', () => {
it('should return a successful response for GET /health', async () => {
const res = await request.get('/health');
res.header = omit(res.header, ['date']);
expect(res).toMatchSnapshot();
});
});
单元测试结果:
PASS src/Whosebug/57409561/index.spec.ts (7.853s)
app
✓ should return a successful response for GET /health (61ms)
console.log src/Whosebug/57409561/index.ts:12
server started at http://localhost:3000
Test Suites: 1 passed, 1 total
Tests: 1 passed, 1 total
Snapshots: 1 passed, 1 total
Time: 8.66s
快照:
// Jest Snapshot v1
exports[`app should return a successful response for GET /health 1`] = `
Object {
"header": Object {
"access-control-allow-origin": "*",
"connection": "close",
"content-length": "2",
"content-type": "text/plain; charset=utf-8",
"etag": "W/\"2-nOO9QiTIwXgNtWtBJezz8kv3SLc\"",
"x-powered-by": "Express",
},
"req": Object {
"data": undefined,
"headers": Object {
"user-agent": "node-superagent/3.8.3",
},
"method": "GET",
"url": "http://127.0.0.1:3000/health",
},
"status": 200,
"text": "OK",
}
`;
这是完成的演示:https://github.com/mrdulin/jest-codelab/tree/master/src/Whosebug/57409561
足够简单的解决方案:
const request = require('supertest'); // npm i -ED supertest
const app = require('../app'); // your expressjs app
const { url } = request(app).get('/'); // next, just use url
console.debug(url); // prints: http://127.0.0.1:57516/
我是后端开发的新手,我遇到了一个我不明白的问题。
我设置了我的 API 的第一个路由叫 "health" 谁只是 return 一个简单的消息来知道我的服务器是否启动。
这条路线看起来像预期的那样工作。
然而,
当我尝试使用方法 "toMatchSnapshot" 测试这条路线时 开玩笑 API,由于 url 中的不断变化,测试未通过。
我的测试文件"index.test.ts":
const request = supertest.agent(app);
describe("app", () => {
it("should return a successful response for GET /health", async () => {
const res = await request.get("/health");
res.header = omit(res.header, ["date"]);
expect(res).toMatchSnapshot();
});
});
服务器索引"index.ts":
const app = express();
expressService(app);
if (require.main === module) {
app.listen(PORT, () => {
console.log("server started at http://localhost:" + PORT);
});
}
export default app;
我的函数"expressService":
const expressService = (app: Application) => {
app.use(cors());
app.use(express.urlencoded({ extended: true }));
app.use(express.json());
app.use(api);
};
export default expressService;
我的 PORT 变量:PORT = 3000;
- "url": "http://127.0.0.1:49694/health",
+ "url": "http://127.0.0.1:52568/health",
这是测试失败的地方。
感谢您的回答。
supertest
的文档说:
You may pass an http.Server, or a Function to request() - if the server is not already listening for connections then it is bound to an ephemeral port for you so there is no need to keep track of ports.
您需要传递一个Node.js http.Server
对象给supertest.agent()
,然后您可以使用特定的PORT
进行测试。
解决方法如下:
index.ts
:
import express from 'express';
import expressService from './expressService';
import http from 'http';
const app = express();
const PORT = process.env.PORT || 3000;
expressService(app);
function createHttpServer() {
const httpServer: http.Server = app.listen(PORT, () => {
console.log('server started at http://localhost:' + PORT);
});
return httpServer;
}
if (require.main === module) {
createHttpServer();
}
export default createHttpServer;
expressService.ts
:
import { Application } from 'express-serve-static-core';
import express, { Router } from 'express';
import cors from 'cors';
const expressService = (app: Application) => {
app.use(cors());
app.use(express.urlencoded({ extended: true }));
app.use(express.json());
const api = Router();
api.get('/health', (req, res) => {
res.sendStatus(200);
});
app.use(api);
};
export default expressService;
index.spec.ts
:
import createHttpServer from './';
import { agent } from 'supertest';
import { omit } from 'lodash';
const httpServer = createHttpServer();
const request = agent(httpServer);
afterAll(done => {
httpServer.close(done);
});
describe('app', () => {
it('should return a successful response for GET /health', async () => {
const res = await request.get('/health');
res.header = omit(res.header, ['date']);
expect(res).toMatchSnapshot();
});
});
单元测试结果:
PASS src/Whosebug/57409561/index.spec.ts (7.853s)
app
✓ should return a successful response for GET /health (61ms)
console.log src/Whosebug/57409561/index.ts:12
server started at http://localhost:3000
Test Suites: 1 passed, 1 total
Tests: 1 passed, 1 total
Snapshots: 1 passed, 1 total
Time: 8.66s
快照:
// Jest Snapshot v1
exports[`app should return a successful response for GET /health 1`] = `
Object {
"header": Object {
"access-control-allow-origin": "*",
"connection": "close",
"content-length": "2",
"content-type": "text/plain; charset=utf-8",
"etag": "W/\"2-nOO9QiTIwXgNtWtBJezz8kv3SLc\"",
"x-powered-by": "Express",
},
"req": Object {
"data": undefined,
"headers": Object {
"user-agent": "node-superagent/3.8.3",
},
"method": "GET",
"url": "http://127.0.0.1:3000/health",
},
"status": 200,
"text": "OK",
}
`;
这是完成的演示:https://github.com/mrdulin/jest-codelab/tree/master/src/Whosebug/57409561
足够简单的解决方案:
const request = require('supertest'); // npm i -ED supertest
const app = require('../app'); // your expressjs app
const { url } = request(app).get('/'); // next, just use url
console.debug(url); // prints: http://127.0.0.1:57516/