forwardemail / forwardemail/supertest

Why I was getting "Jest has detected the following 1 open handle potentially keeping Jest from exiting: Timeout"

Open
#823 1 comment 0 reactions 0 assignees View on GitHub
Dominant language
JavaScript
Stars
14.4k
Forks
782
PR merge metrics
No merged PRs in 30d

Description

Not a bug. Just wanted to document this here in case anyone else comes across the same issue. When running my tests I was getting the below output:
```
Jest has detected the following 1 open handle potentially keeping Jest from exiting:

● Timeout

41 | describe("responses", () => {
42 | it("should send a 200 response for a valid request", async () => {
> 43 | const response = await request(app).get(
| ^
44 | `/api/${apiVersion}${ROUTE_PATHS.PARTNUMBERS}`
45 | );
46 | // console.log(request(app).get("/").serverAddress(app, "/"));

at Test.serverAddress (node_modules/supertest/lib/test.js:48:35)
at new Test (node_modules/supertest/lib/test.js:34:14)
at Object.obj. [as get] (node_modules/supertest/index.js:43:18)
at __tests__/controllers/partnumbers.test.ts:43:40
at __tests__/controllers/partnumbers.test.ts:8:71
at Object..__awaiter (__tests__/controllers/partnumbers.test.ts:4:12)
at Object. (__tests__/controllers/partnumbers.test.ts:42:67)
```
I couldn't find anything online or in the github related to a 'Timeout' open handle.

I traced the issue to a rate limiting middleware I had made.

```
const rateLimiter = (req: Request, res: Response, next: NextFunction) => {
// Get the client's IP address
const clientIp = req.ip;

// Check if the client has exceeded the rate limit
if (requestCounter.has(clientIp)) {
const requestsMade = requestCounter.get(clientIp);
if (requestsMade >= REQUESTS_PER_MINUTE) {
return res.status(429).send("Too Many Requests");
}
}

// Increment the number of requests made by this client
requestCounter.set(clientIp, (requestCounter.get(clientIp) || 0) + 1);

// Clear the request count for this client after 1 minute
const requestTimer = setTimeout(() => {
requestCounter.delete(clientIp);
clearInterval(refillTimer); // clear the refill timer, which also prevents unopen handles in tests
}, 60 * 1000);

// Refill the bucket by 1 request every second
const refillTimer = setInterval(() => {
requestCounter.set(clientIp, Math.max(requestCounter.get(clientIp) - 1, 0));
}, 1000);

// Call the next middleware in the chain
next();

// Clean up the timers after the middleware has finished
clearTimeout(requestTimer);
clearInterval(refillTimer);
};
```

Without the `clearTimeout` and `clearInterval` calls the timers will start running indefinitely, even after the tests have completed, which was leading to the open handle error.

After adding the calls to clear these two timers I no longer experience the issue.

Contributor guide

Open the contributing guide

Assessment

This issue has not been assessed yet.

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.