
npm i -D jest.
├── node_modules
├── src
│ ├── controllers
│ ├── models
│ │ └── data-source.js (Connect to DB using TypeORM)
│ ├── routes
│ ├── services
│ └── utils
├── tests
│ └── **user.test.js**
├── .env
├── **.env.test**
├── .gitignore
├── **app.js**
├── package-lock.json
├── package.json
└── **server.js**
router, middleware code of applicationcreateApp function that returns appconst express = require("express");
const cors = require("cors");
const morgan = require("morgan");
const dotenv = require("dotenv");
dotenv.config();
const routes = require("./src/routes");
const { errorHandler } = require("./src/utils/errorHandling.js");
const createApp = () => {
const app = express();
app.use(express.json());
app.use(cors());
app.use(morgan("combined"));
app.use(routes);
app.use(errorHandler);
return app;
};
module.exports = { createApp };
createApp function to use app that created in app.jsstartServer function that includes AppDataSource.initialize() and app.listen().server.js when start server, and use app (= return value ofcreateApp) in test code.require("dotenv").config();
const { createApp } = require("./app");
const { AppDataSource } = require("./src/models/data-source");
const startServer = async () => {
const app = createApp();
// Connect to DB & initialize
await AppDataSource.initialize();
const PORT = process.env.PORT;
app.listen(PORT, () => {
console.log(`Listening on Port ${PORT}`);
});
};
startServer();
describe but also test are consists of (description, callback)description : Category or description about the logicdescribe and test can be declaired in callbackcallback and we can compare the values with expect to see if they were performed well.describe can helps adding caption about testjest instruction.test.js, .spec.js// npm i --save-dev supertest
// Send a test request to the app using the request of the *supertest*.
const request = require("supertest");
// Call CreateApp function to use app in request of supertest.
const { createApp } = require("../app");
// Call DataSource object for connecting to DB
const { AppDataSource } = require("../src/models/data-source");
// Category
describe("Sign Up", () => {
let app;
// Before start the test, create app object
beforeAll(async () => {
app = createApp();
// We can initialize DB here, but I moved the code to server.js to avoid some log :
// Jest has detected the following 1 open handle potentially keeping Jest from exiting:
//● TCPWRAP
// ...
// await AppDataSource.initialize();
});
afterAll(async () => {
// Remove all unnecessary data in test DB
// If TRUNCATE instruction doesn`t work because of foreign key,
// temporarily release the foreign key and restore.
await AppDataSource.query(`SET foreign_key_checks = 0;`);
await AppDataSource.query(`TRUNCATE users`);
await AppDataSource.query(`SET foreign_key_checks = 1;`);
// After all tests are finished, disconnect DB
await AppDataSource.destroy();
});
// Test all different cases.
// It helps to check if the code is well develpted for your intentions from the test stage!
// 1. Check the emaill address rule
test("FAILED: invalid email", async () => {
// Send test request to app using supertest의 request
await request(app)
.post("/users/signup") // HTTP Method, Endpoint address
// body
.send({
email: "wrongEmail",
password: "password001@",
username: "testName",
mobile: "testMobile",
})
.expect(400) // Test appropriate statusCode and response using expect()
.expect({ message: "invalid email!" });
});
// 2. Check creating user
test("SUCCESS: created user", async () => {
await request(app)
.post("/users/signup")
.send({
email: "wecode002@gmail.com",
password: "password001@",
username: "testName",
mobile: "testMobile",
})
.expect(201);
});
// 3. Check duplicated email
test("FAILED: duplicated email", async () => {
await request(app)
.post("/users/signup")
.send({
email: "wecode002@gmail.com",
password: "password001@",
username: "testName",
mobile: "testMobile",
})
.expect(409)
.expect({ message: "ALREADY_SIGNED_UP" });
});
});
TYPEORM_DATABASE = testDB"test": "DOTENV_CONFIG_PATH=.env.test jest --setupFiles=dotenv/config --runInBand --detectOpenHandles --forceExit"

Q. How can we test and release program with less time and effort? 🤔
A. Continuous Integration / Continuous Deployment


