This article is about fixing MaxListenersExceededWarning Possible EventEmitter memory leak detected. 11 error listeners added to [Keyv]. Use emitter.setMaxListeners() to increase limit in sindresorhus Got
  • 06-Feb-2023
Lightrun Team
Author Lightrun Team
Share
This article is about fixing MaxListenersExceededWarning Possible EventEmitter memory leak detected. 11 error listeners added to [Keyv]. Use emitter.setMaxListeners() to increase limit in sindresorhus Got

MaxListenersExceededWarning: Possible EventEmitter memory leak detected. 11 error listeners added to [Keyv]. Use emitter.setMaxListeners() to increase limit in sindresorhus Got

Lightrun Team
Lightrun Team
06-Feb-2023

Explanation of the problem

The use of simple cache adapters in the got library has been causing the emission of the MaxListenersExceededWarning warning. The issue has previously been addressed in the library’s issues #792 and #1128 but it seems that it has either been a regression or was not properly accounted for in highly asynchronous environments with hundreds of parallel requests.

Paragraph 2: The problem occurs in the environment described as: a macOS 10.15.7 operating system, a CPU of (12) x64 Intel(R) Core(TM) i7-9750H CPU @ 2.60GHz, Node version 12.19.0, Yarn version 1.22.10, npm version 6.14.8, Chrome version 86.0.4240.198 and Safari version 14.0. The actual behavior is described as MaxListenersExceededWarning: Possible EventEmitter memory leak detected. 11 error listeners added to [Keyv]. Use emitter.setMaxListeners() to increase limit.

Paragraph 3: The following code block reproduces the issue:

const got = require('got');

const client = got.extend({
    cache: {
        get: (key) => {
            return undefined;
        },
        set: (key, value) => {

        }
    }
});

(async () => {
    const promises = [];

    for (let i = 0; i < 20; i++) {
        promises.push(client('https://www.google.com', { method: 'HEAD' }));
    };

    await Promise.all(promises);

    console.log('Done');
})();

This code demonstrates the emission of the MaxListenersExceededWarning warning in the got library when using simple cache adapters.

Troubleshooting with the Lightrun Developer Observability Platform

Getting a sense of what’s actually happening inside a live application is a frustrating experience, one that relies mostly on querying and observing whatever logs were written during development.
Lightrun is a Developer Observability Platform, allowing developers to add telemetry to live applications in real-time, on-demand, and right from the IDE.

  • Instantly add logs to, set metrics in, and take snapshots of live applications
  • Insights delivered straight to your IDE or CLI
  • Works where you do: dev, QA, staging, CI/CD, and production

Start for free today

Problem solution for MaxListenersExceededWarning: Possible EventEmitter memory leak detected. 11 error listeners added to [Keyv]. Use emitter.setMaxListeners() to increase limit in sindresorhus Got

To resolve the “MaxListenersExceededWarning: Possible EventEmitter memory leak detected” in “sindresorhus Got”, you can use the setMaxListeners() method to increase the number of listeners for the event emitter. The default value for max listeners is 10, but you can change it to a higher value to prevent the warning from appearing. For example:

const got = require('got');
got.emitter.setMaxListeners(20);

This sets the maximum number of listeners for the got event emitter to 20. You can adjust the number as needed for your specific use case. Note that increasing the number of listeners can potentially lead to increased memory usage, so it’s important to set a reasonable value to avoid memory leaks.

Other popular problems with sindresorhus Got

Problem: Timeout errors

Another common problem with sindresorhus Got is that requests can time out if they take too long to complete. This can lead to an error message being thrown by the library.

Solution:

To resolve this issue, you can set a timeout value for your requests using the timeout option. The following code shows how to set a timeout value of 10 seconds for a request:

const got = require('got');

(async () => {
  try {
    const response = await got('https://google.com', {
      timeout: 10000
    });
    console.log(response.body);
  } catch (error) {
    console.log(error);
  }
})();

Problem: Certificate issues

Another common issue with sindresorhus Got is that it can run into certificate problems when making requests to secure websites. This can occur if the website’s SSL certificate is not recognized by the library.

Solution:

To resolve this issue, you can set the rejectUnauthorized option to false when making your requests. The following code shows how to make a request with rejectUnauthorized set to false:

const got = require('got');

(async () => {
  try {
    const response = await got('https://google.com', {
      rejectUnauthorized: false
    });
    console.log(response.body);
  } catch (error) {
    console.log(error);
  }
})();

Note that setting rejectUnauthorized to false is not recommended for production environments as it may compromise security by accepting SSL certificates from untrusted sources.

Problem: Handling JSON responses

One common problem when using sindresorhus Got is handling JSON responses from API calls. By default, sindresorhus Got returns the response body as a string, which means that you need to parse the JSON data yourself. This can lead to additional code and error-prone data parsing.

Solution:

To simplify handling JSON responses, sindresorhus Got provides a json option that can be set to true. When set, sindresorhus Got will automatically parse the response body as JSON and return the result as a JavaScript object. The following code shows how to make a request and handle a JSON response:

const got = require('got');

(async () => {
  try {
    const response = await got('https://api.example.com', {
      json: true
    });
    console.log(response.body);
  } catch (error) {
    console.log(error);
  }
})();

By using the json option, you can simplify your code and avoid the need to manually parse JSON data, making it easier to handle API responses. Note that if the response from the API is not valid JSON, an error will be thrown by sindresorhus Got.

A brief introduction to sindresorhus Got

sindresorhus Got is a popular HTTP client library for Node.js, designed to make it easy to send HTTP and HTTPS requests. It provides a simple and intuitive API for sending requests and handling responses. The library supports a wide range of HTTP methods, including GET, POST, PUT, DELETE, and others, as well as a variety of request options and features, such as automatic decompression of response data, query string building, and support for HTTP redirects.

In addition to its simple and intuitive API, sindresorhus Got is highly performant and efficient, making it a great choice for both simple and complex use cases. The library supports streaming request and response data, allowing for large files to be uploaded or downloaded with minimal memory overhead. Additionally, sindresorhus Got has built-in support for retrying failed requests, making it ideal for applications that need to send requests to unreliable or flaky servers. Overall, sindresorhus Got is a reliable and flexible HTTP client that provides a powerful set of features for sending HTTP requests from Node.js applications.

Most popular use cases for sindresorhus Got

  1. Making HTTP Requests:

One of the primary use cases for sindresorhus Got is making HTTP requests from Node.js applications. The library provides a simple and intuitive API for sending HTTP requests, allowing you to easily send GET, POST, PUT, DELETE, and other types of requests to remote servers. The following code block demonstrates how to use sindresorhus Got to make a GET request:

const got = require('got');

(async () => {
  try {
    const response = await got('https://api.example.com');
    console.log(response.body);
  } catch (error) {
    console.log(error);
  }
})();
  1. Handling API Responses:

sindresorhus Got is well suited for handling API responses, as it provides features such as automatic decompression of response data, query string building, and support for HTTP redirects. Additionally, the library supports streaming request and response data, allowing you to efficiently handle large files in your API calls.

  1. Error handling:

Another key use case for sindresorhus Got is error handling. The library provides built-in error handling, so you can catch and respond to errors that occur during an API call. For example, if the API server returns a non-200 status code, sindresorhus Got will throw an error, which can be caught and handled in your code. The following code block demonstrates how to handle errors when using sindresorhus Got:

const got = require('got');

(async () => {
  try {
    const response = await got('https://api.example.com');
    console.log(response.body);
  } catch (error) {
    console.log(error.response.statusCode);
  }
})();

By handling errors properly, you can ensure that your application continues to run smoothly, even in the face of errors returned by the API.

Share

It’s Really not that Complicated.

You can actually understand what’s going on inside your live applications.

Try Lightrun’s Playground

Lets Talk!

Looking for more information about Lightrun and debugging?
We’d love to hear from you!
Drop us a line and we’ll get back to you shortly.

By submitting this form, I agree to Lightrun’s Privacy Policy and Terms of Use.