Skip to main content
This article explains how to run load tests on APIs without extensive experience, using the open-source tools k6 and JMeter.
  • API: An interface that enables communication between applications.
  • Load testing: Tests that evaluate how an application performs under a given load; they measure resilience, speed, and overall performance.
  • k6: An open-source load-testing tool; JavaScript-based scripts, console-driven. It simulates realistic API traffic and measures how your system responds under load.
  • JMeter: An open-source, Java-based load-testing tool; scenarios are defined via GUI or XML. It simulates realistic user behavior.
We will run the same kinds of tests with both k6 and JMeter and compare them.

Grafana k6 and Apache JMeter Comparison

FeatureJMeterk6
Language and styleJavaJavaScript
Setup and startupJRE, GUI-basedNode.js, console-based
Performance and scalabilityHeavy load tests, higher resource usageLightweight, scalable
Scenario definitionXML, GUI or manualCode in JavaScript
Distributed testingBroad supportk6 Cloud or custom setups
ReportingGUI, graphs, Grafana/InfluxDBConsole, k6 Cloud, integrations
CommunityLarge user baseRapidly growing
JMeter’s UI offers graphical reports, Backend listener, and Grafana/InfluxDB. k6 is console-based but can be used with many visualization options and Grafana integration.

k6 Basic Test Scenarios

Below are examples for load, endurance, stress, and performance-optimization scenarios targeting API endpoints.

Load test

Simulates many users connecting at the same time.
import http from 'k6/http';
import { sleep } from 'k6';
export default function () {
  const numberOfUsers = 100;
  Array.from({ length: numberOfUsers }, (_, index) => {
    http.get(`https://example.com/page${index}`);
    sleep(1);
  });
}

Endurance test

Simulates the application running stably under a constant load for a period.
import http from 'k6/http';
import { sleep } from 'k6';
export default function () {
  while (1) {
    http.get('https://example.com');
    sleep(1);
  }
}

Stress test

Simulates sudden traffic spikes or fast changes in user count.
import http from 'k6/http';
import { sleep } from 'k6';
export default function () {
  const numberOfUsers = __VU * 10;
  Array.from({ length: numberOfUsers }, (_, index) => {
    http.get(`https://example.com/page${index}`);
    sleep(0.1);
  });
}

Example k6 scenario (staged load)

import http from 'k6/http';
import { check, sleep } from 'k6';
export let options = {
  stages: [
    { duration: '30s', target: 500 },
    { duration: '1m', target: 50 },
    { duration: '30s', target: 0 },
  ],
};
export default function () {
  let methods = ['GET', 'POST', 'PUT', 'DELETE'];
  let method = methods[Math.floor(Math.random() * methods.length)];
  let endpoints = [
    'https://example.com/k6_load_test/get',
    'https://example.com/k6_load_test/post',
    'https://example.com/k6_load_test/put',
    'https://example.com/k6_load_test/delete',
  ];
  let endpoint = endpoints[Math.floor(Math.random() * endpoints.length)];
  let res = http.request(method, endpoint);
  check(res, { 'is status 200': (r) => r.status === 200 });
}
Run with: k6 run k6_load_test.js k6 result metrics (summary): http_reqs (total requests), http_req_duration (response time), http_req_failed, iterations, vus/vus_max, checks, data_received/data_sent, p(90)/p(95) (percentiles). These help you assess your API’s behavior under load and find bottlenecks. k6 results can be visualized together with system metrics via Prometheus and Grafana. Installation: k6 installation guide (Windows, Mac, Linux).

JMeter Basic Test Scenarios

In JMeter you configure Threads (number of simulated users), Loop count, and Ramp-up Period (time to start all threads). API performance test: Threads = number of concurrent requests to the API (e.g. 500); Loop = how many times each user repeats; Ramp-up = time to start all users. Additional scenarios: (1) Increase request count to simulate load, (2) Maximum load test, (3) Long-duration load test, (4) Different request types (GET, POST, PUT, DELETE), (5) Average response time test, (6) Error-handling test, (7) Scheduled tests with a timer. JMeter can be run from the GUI (Run) or from the command line; results can be written to CSV:
jmeter -n -t /path/to/TEST_NAME.jmx -l /path/to/RECORD_NAME.csv
JMeter result metrics (summary): summary (total requests), total time, average requests/second, average/min/max response time, error count and percentage, active/started/finished request counts. Installation: JMeter installation guide (Windows, Mac, Linux).

Comparing JMeter and k6 Performance Test Results

FeatureJMeterk6
Test environmentStandalone testLocal environment
Test duratione.g. 2 min 41 sece.g. 3 min
Target userse.g. max 500 concurrentRamp up to 500
Total requestse.g. 25,000e.g. 180,077
Average response timee.g. 11.44 se.g. 242 ms
Max response timee.g. 21.15 se.g. 33.68 s
Throughpute.g. 169.6 req/se.g. 857.45 req/s
Note: Values depend on the example test environment.

Conclusion

JMeter supports high concurrent user counts even at lower request throughput and is well suited for large-scale applications. k6 offers higher request throughput and is good for minimizing failed-request rates and for scenarios that require fast responses. Which tool to use depends on your test requirements, target metrics, and application design. Both tools can be used in different scenarios and provide valuable data for performance testing. You can run your own load tests with these tools to evaluate your applications’ performance.