Skip to main content

Api Load Testing With Grafana K6 Using Js

· 7 min read
Sivabharathy

Performance testing is a crucial step in ensuring that your application can handle real-world traffic, perform well under heavy load, and recover from unexpected spikes or prolonged usage. Grafana K6 is a modern, open-source load testing tool that can be used to simulate and measure the performance of web applications, APIs, and services under various conditions.

In this article, we’ll walk through the implementation of load testing, stress testing, spike testing, and soak testing using Grafana K6 in a Node.js environment. We will also integrate Grafana to visualize the metrics and performance results.

1. What is Grafana K6?

Grafana K6 is an open-source, developer-centric load testing tool designed for testing the performance of APIs, microservices, and web applications. It is scriptable in JavaScript, which makes it easy to write complex test scenarios and integrate with other tools. K6 supports metrics collection, distributed testing, and integrates seamlessly with Grafana for real-time monitoring and visualization.

Key Features of K6:

  • Easy to use: It uses JavaScript for scripting test scenarios.
  • Scalable: Supports running tests with large numbers of virtual users.
  • Real-time metrics: Integration with Grafana for monitoring.
  • Extensibility: Supports custom metrics, thresholds, and complex workflows.
  • Performance: Efficient resource usage and fast execution.

2. Setting Up the Environment

Before we begin, let’s set up the environment.

Step 1: Install Grafana and K6

To start, we need to install Grafana, K6, and Node.js on your machine.

  • Install Node.js (if not already installed): Node.js download

  • Install K6: You can install K6 via Homebrew (on macOS), or use the download links for your system:

    # For macOS (using Homebrew)
    brew install k6

    # For Linux
    sudo apt install k6
  • Install Grafana: Grafana download

Step 2: Install Required NPM Packages

We will use the k6 command-line tool to run the tests, but we will also use Node.js to handle test automation and setup.

In your Node.js project, run the following command to install required dependencies:

npm install axios grafana-dashboard

Axios is used to simulate HTTP requests within our Node.js application, while grafana-dashboard helps us integrate K6 with Grafana.


3. Creating K6 Test Scripts

Now that the environment is set up, let’s dive into creating K6 test scripts for the four types of testing: Load Testing, Stress Testing, Spike Testing, and Soak Testing.

3.1 Load Testing with K6

Load testing simulates the normal and peak traffic that the system expects to handle. The goal is to ensure that the system can handle the specified number of virtual users (VUs) and that it doesn’t degrade in performance.

Script for Load Testing:

import http from "k6/http";
import { check, sleep } from "k6";

export let options = {
stages: [
{ duration: "5m", target: 1000 }, // Ramp-up to 1000 users over 5 minutes
{ duration: "10m", target: 1000 }, // Maintain 1000 users for 10 minutes
{ duration: "5m", target: 0 }, // Ramp-down to 0 users
],
};

export default function () {
const res = http.get("http://yourapi.com/api/endpoint");
check(res, {
"status is 200": (r) => r.status === 200,
"response time is less than 500ms": (r) => r.timings.duration < 500,
});
sleep(1); // Simulate user think time
}

Explanation:

  • The stages configuration defines the load profile. In this case, the test ramps up to 1,000 users, holds for 10 minutes, and then ramps down.
  • The http.get() function sends a GET request to the API, and check() verifies the response status and timing.

3.2 Stress Testing with K6

Stress testing is designed to push the system beyond its expected capacity to determine where the system breaks.

Script for Stress Testing:

import http from "k6/http";
import { check } from "k6";

export let options = {
vus: 5000, // Simulate 5000 virtual users
duration: "10m", // Run for 10 minutes
};

export default function () {
const res = http.get("http://yourapi.com/api/endpoint");
check(res, {
"status is 200": (r) => r.status === 200,
"response time is less than 1000ms": (r) => r.timings.duration < 1000,
});
}

Explanation:

  • In this case, we are simulating 5,000 users (which is much higher than the normal expected load). The goal is to find out how the system performs under extreme conditions and where it starts to fail.

3.3 Spike Testing with K6

Spike testing simulates a sudden, unexpected increase in traffic to see how the system handles abrupt spikes.

Script for Spike Testing:

import http from "k6/http";
import { check } from "k6";

export let options = {
stages: [
{ duration: "2m", target: 500 }, // Gradually increase to 500 users
{ duration: "2m", target: 5000 }, // Spike up to 5000 users
{ duration: "2m", target: 500 }, // Gradually reduce to 500 users
{ duration: "2m", target: 0 }, // Ramp down to 0 users
],
};

export default function () {
const res = http.get("http://yourapi.com/api/endpoint");
check(res, {
"status is 200": (r) => r.status === 200,
"response time is less than 500ms": (r) => r.timings.duration < 500,
});
}

Explanation:

  • We simulate a traffic spike from 500 users to 5,000 users within a short timeframe. This test helps us assess how the system reacts to sudden, unpredictable traffic increases.

3.4 Soak Testing with K6

Soak testing involves running the system under a sustained load for an extended period to detect issues like memory leaks or performance degradation over time.

Script for Soak Testing:

import http from "k6/http";
import { check } from "k6";

export let options = {
vus: 500, // Simulate 500 virtual users
duration: "24h", // Run for 24 hours
};

export default function () {
const res = http.get("http://yourapi.com/api/endpoint");
check(res, {
"status is 200": (r) => r.status === 200,
"response time is less than 200ms": (r) => r.timings.duration < 200,
});
}

Explanation:

  • This test runs continuously for 24 hours with 500 users, monitoring for resource leaks or performance degradation over a long period.

4. Running the K6 Tests

To run your K6 tests, use the following command:

k6 run load-test-script.js

You can replace load-test-script.js with the name of your script (e.g., stress-test.js, soak-test.js, etc.).

Running Tests with Multiple Virtual Users

To simulate more complex scenarios, you can scale the number of virtual users (vus) and the test duration (duration) to simulate high traffic.


5. Integrating Grafana for Monitoring

You can integrate K6 with Grafana for real-time monitoring and visualization of performance metrics.

Step 1: Start a Prometheus Server

K6 can send metrics to a Prometheus server, which can then be visualized in Grafana.

  1. Download and run Prometheus:

    docker run -d -p 9090:9090 prom/prometheus
  2. Configure Prometheus to collect metrics from K6.

Step 2: Start Grafana and Add Prometheus Data Source

  1. Start Grafana (if not already running):

    docker run -d -p 3000:3000 grafana/grafana
  2. Open Grafana in your browser at http://localhost:3000 and log in (default credentials: admin/admin).

  3. Add Prometheus as a data source:

    • Go to Configuration -> Data Sources -> Add Data Source -> Select Prometheus.
    • Set the URL to http://localhost:9090.

Step 3: Create Dashboards in Grafana

Once Prometheus is set up to collect data from K6, you can create dashboards in Grafana to visualize metrics like:

  • Request count
  • Response times
  • Error rates
  • Virtual users (VUs) over time

Grafana offers prebuilt K6 dashboards that you can import directly from Grafana’s dashboard library.


6. Conclusion

Using Grafana K6 for performance testing in Node.js allows you to simulate real-world traffic conditions and gain insights into how your application performs under various scenarios. By implementing Load Testing, Stress Testing, Spike Testing, and Soak Testing, you can ensure that your system is robust, resilient, and able to handle both normal and extreme traffic conditions.

Integrating Prometheus and Grafana provides real-time metrics and visualizations, enabling you to track performance, detect bottlenecks, and optimize your application for better performance.