skip to content

Generator Capacity

What limits the traffic one JMeter machine can really produce: the launcher's JVM settings, the cost the plan itself imposes, and the signs the injector has run out of room.

on this pageshow

explore

questions

15

In Apache JMeter's bin/jmeter launcher, which environment variable sets the JVM heap, and what is its default?

level: juniorimportance: must knowfreq 68%

answer

  1. A launcher variable, not a property
  2. Read before the JVM even starts
  3. Initial and maximum ship equal
  4. bin/setenv.sh is the sanctioned place

basics

~10 s

HEAP. Apache JMeter's bin/jmeter launcher defaults it to -Xms1g -Xmx1g -XX:MaxMetaspaceSize=256m, so an injector starts with a fixed one-gigabyte heap unless HEAP is exported first, normally from bin/setenv.sh.

solid answer

~40 s

`HEAP` is the environment variable Apache JMeter 6.0.0's `bin/jmeter` script reads to build the memory part of the injector's `java` command line. The script applies it as a shell default, `: "${HEAP:="-Xms1g -Xmx1g -XX:MaxMetaspaceSize=256m"}"`, so an already-exported value wins and an unset one falls back to a fixed 1 GB heap plus a 256 MB metaspace cap. It is not a JMeter property — no entry in `jmeter.properties` can change it, because the heap is fixed before the JVM starts. Because `bin/jmeter` sources `bin/setenv.sh` (a file you create; Apache does not ship it) before computing that default, exporting `HEAP` there is the supported way to raise an injector past the shipped gigabyte, and it survives an upgrade because the launcher itself is untouched.

code

bash · 6 lines
bash
# bin/setenv.sh - you create this file; Apache does not ship it.
# bin/jmeter sources it before it computes any default.
export HEAP="-Xms4g -Xmx4g -XX:MaxMetaspaceSize=256m"

# One-off equivalent, scoped to a single run:
# HEAP="-Xms4g -Xmx4g -XX:MaxMetaspaceSize=256m" jmeter -n -t plan.jmx -l results.jtl

go deeper

for a junior

Recall the name and the number: the variable is HEAP and the shipped default is a fixed one-gigabyte heap. Knowing that a stock JMeter starts at 1 GB is the point of the question.

for a middle

Explain the mechanics: bin/jmeter sources bin/setenv.sh first, then applies HEAP as a shell default, then expands it into the java command line. Name the metaspace flag that rides along in the same string.

for a senior

Show that you verify rather than assume. Point at the Max memory line jmeter.log records at startup, and know that jmeter-server inherits the same default so a fleet needs the setting everywhere.

for a principal

Own the policy: one documented HEAP per machine class in setenv.sh, no edits to the shipped launcher, and a rule that says the number is a machine decision rather than something each run improvises.

## The variable, not a property Apache JMeter 6.0.0 sizes the injector JVM from a shell environment variable named `HEAP`, read by `bin/jmeter` on Un*x and by `bin/jmeter.bat` on Windows. It is **not** a JMeter property: nothing you put in `bin/jmeter.properties`, `bin/user.properties` or `bin/system.properties` can change the heap, because the heap has to be fixed on the `java` command line before the JVM that would read those files exists at all. `bin/jmeter` assigns it with a shell default: ```sh : "${HEAP:="-Xms1g -Xmx1g -XX:MaxMetaspaceSize=256m"}" ``` The `:=` form keeps an already-set, non-empty `HEAP` and falls back to the shipped string otherwise. `HEAP` is then expanded into the `ARGS` list the script hands to `java`. ## What the shipped default contains - `-Xms1g` — the initial heap. - `-Xmx1g` — the maximum heap; initial and maximum ship **equal**. - `-XX:MaxMetaspaceSize=256m` — a metaspace cap, which is a separate region from the heap and is *not* raised when you raise `-Xmx`. That gigabyte is a JMeter 4.0 change; older releases shipped `-Xms512m -Xmx512m`. The Getting Started manual's own load-run checklist lists "Increase the Java Heap size" as a step, noting the default "might not be enough for your test". Two neighbouring assignments in the same script matter as soon as you raise it: - `GC_ALGO` defaults to `-XX:+UseG1GC -XX:MaxGCPauseMillis=100 -XX:G1ReservePercent=20`. (The user manual's variable table still prints `250` for the pause target; the shipped scripts say `100`, and the scripts are what runs.) - `DUMP` is set unconditionally to `-XX:+HeapDumpOnOutOfMemoryError`, with the comment "Always dump on OOM (does not cost anything unless triggered)". No `-XX:HeapDumpPath` is set anywhere in the distribution. ## Where to set it 1. **`bin/setenv.sh`** (`setenv.bat` on Windows). Apache does not ship this file — you create it. `bin/jmeter` sources it near the top, long before the `HEAP` default is computed, so an `export HEAP=...` there wins. This is the documented route, and because the launcher itself is never edited, a JMeter upgrade cannot silently discard it. 2. **An exported variable for a single run**, e.g. `HEAP="-Xms4g -Xmx4g -XX:MaxMetaspaceSize=256m" jmeter -n -t plan.jmx -l results.jtl`. Same effect, scoped to that invocation. 3. **`JVM_ARGS`**, which the launcher appends *after* `ARGS`, so a `-Xmx` there overrides the one `HEAP` already placed on the line instead of replacing the whole string. Editing `bin/jmeter` in place is the fourth option and the one the script's own header warns against: "Do not set the variables in this script. Instead put them into a script `setenv.sh` in `JMETER_HOME/bin` to keep your customizations separate." ## Confirming the value took effect `org.apache.jmeter.JMeter` logs a startup block at INFO into `jmeter.log` that includes `java.version=`, `java.vm.name=` and a `Max memory =` line carrying `Runtime.getRuntime().maxMemory()` **in bytes**. An injector you believe you raised to four gigabytes should show roughly `4294967296` there; a value near a gigabyte means your `HEAP` never reached the launcher. ## The launcher variables side by side | Variable | Shipped default | How it reaches `java` | |---|---|---| | `HEAP` | `-Xms1g -Xmx1g -XX:MaxMetaspaceSize=256m` | inside `ARGS` | | `GC_ALGO` | `-XX:+UseG1GC -XX:MaxGCPauseMillis=100 -XX:G1ReservePercent=20` | inside `ARGS` | | `VERBOSE_GC` | unset; two commented-out candidates | inside `ARGS` | | `JVM_ARGS` | empty | appended after `ARGS` | | `JMETER_COMPLETE_ARGS` | empty | when set, `ARGS` is emptied | ## One launcher, several entry points `bin/jmeter-server` is a thin wrapper that calls `bin/jmeter`, so a remote engine inherits the same one-gigabyte default as a local run. `bin/jmeter.sh` does the opposite: it sets `JMETER_COMPLETE_ARGS=true`, which makes `bin/jmeter` skip `HEAP` altogether. What in a plan consumes that heap, and what evidence shows the heap was the constraint, are separate subjects — this one ends at the launcher's command line.

  • Where would you confirm that the heap you set actually reached the JVM?
    In `jmeter.log`. `org.apache.jmeter.JMeter` logs a startup block at INFO with `java.version=`, `java.vm.name=` and `Max memory =`, the last carrying `Runtime.getRuntime().maxMemory()` in bytes. A four-gigabyte injector reports roughly 4294967296; a number near a gigabyte means the launcher used its own default.
  • Does raising -Xmx also raise the metaspace cap the default sets?
    No. `-XX:MaxMetaspaceSize=256m` is a separate flag inside the same `HEAP` string and covers a different region. If you override `HEAP` you replace the whole string, so carry the metaspace flag over deliberately; if you patch only `-Xmx` through `JVM_ARGS`, the shipped 256 MB cap stays exactly as it was.
  • Does a remote engine started with bin/jmeter-server get a different default?
    No. `bin/jmeter-server` is a thin wrapper whose last line calls `bin/jmeter` with `-s` and a server port, so it inherits the same `HEAP` default and the same `bin/setenv.sh`. Raising the heap on a generator fleet therefore means setting `HEAP` on each machine, not only on the machine you launch from.

saying these in an interview costs you the question

  • Says the heap is configured in jmeter.properties
  • Edits bin/jmeter directly instead of creating bin/setenv.sh
  • Thinks -Xmx1g is a per-thread allowance
  • Claims JMeter ships with no heap limit at all
  • Confuses HEAP with the plan's own memory use
open as a page

Which JMeter listeners keep a copy of every sample, and which one is built for a load run?

level: juniorimportance: must knowfreq 74%

basics

~20 s

Most JMeter listeners keep every sample they receive, View Results Tree and View Results in Table included. Simple Data Writer keeps none - it writes the row and lets the result go, so load runs use it.

open as a page

A JMeter plan runs 500 threads with a View Results Tree still attached. What does that cost?

level: middleimportance: must knowfreq 64%

basics

~20 s

Each of the 500 threads calls the listener inside its own loop and queues behind one shared buffer. In GUI mode that buffer holds up to 500 whole sample results, response bodies included, redrawn twice a second.

open as a page

In a JMeter non-GUI run, what do the summariser's + and = console lines each report?

level: middleimportance: must knowfreq 62%

basics

~20 s

The + line is a delta covering only the window since the last report; the = line is the running total for the whole run so far. Only the + line carries Active, Started and Finished thread counts.

open as a page

An Apache JMeter run is started with JVM_ARGS="-Xmx4g" and HEAP left unset. What heap does the JVM get?

level: middleimportance: should knowfreq 52%

basics

~10 s

Maximum 4 GB, initial still 1 GB. The launcher expands HEAP's default first and appends JVM_ARGS afterwards, so the later -Xmx4g wins while -Xms1g and -XX:MaxMetaspaceSize=256m stay on the line untouched.

open as a page

In JMeter, what does each extra Thread Group thread allocate before it sends a request?

level: middleimportance: should knowfreq 50%

basics

~10 s

One real platform thread, its own clone of everything under that Thread Group, and its own copy of the variables. Plan size therefore multiplies by thread count before the first request goes out.

open as a page

A JMeter injector started via bin/jmeter.sh ignores the HEAP you set. What does that script do differently?

level: seniorimportance: should knowfreq 31%

basics

~10 s

It exports JMETER_COMPLETE_ARGS=true before calling bin/jmeter, which makes that script set ARGS empty. Only JVM_ARGS and JMETER_OPTS then reach java, so HEAP, GC_ALGO and the OOM heap-dump flag are all dropped.

open as a page

Your JMeter plan ticks Retrieve All Embedded Resources on every page sampler. What does the injector pay?

level: seniorimportance: should knowfreq 46%

basics

~20 s

Every HTML response is parsed on the sampling thread, and each asset becomes another request whose result hangs off a container result JMeter builds for the page. That container can carry dozens of results, and every listener sees all of them.

open as a page

A JMeter run's summariser rate flattens while its Active count keeps climbing. Which JMeter output records that?

level: seniorimportance: should knowfreq 52%

basics

~20 s

Successive + delta lines hold the story: the /s figure, the Active count, the Avg time and the Err share, window by window. Beside them sit jmeter.log at ERROR and any gap where no line was printed at all.

open as a page

What happens to a JMeter non-GUI run when a sampler thread throws OutOfMemoryError?

level: seniorimportance: should knowfreq 48%

basics

~10 s

The thread dies and the run carries on. JMeter's default uncaught-exception handler logs an ERROR block in jmeter.log and prints one line to stderr, and bin/jmeter's always-on heap-dump flag leaves a .hprof file behind.

open as a page

Each JMeter injector in your team has bin/jmeter hand-edited to raise the heap. How would you get that under control?

level: principalimportance: should knowfreq 34%

basics

~10 s

Move the setting into bin/setenv.sh, which bin/jmeter sources before applying its own defaults and which an upgrade cannot overwrite. Set the whole HEAP string per machine class, and forbid edits to the shipped launcher.

open as a page

Across a team's JMeter plans, how would you decide what a load run may record and keep?

level: principalimportance: should knowfreq 38%

basics

~20 s

Set a default the injector can always afford - a lean writer, errors only, nothing retained - and make richer recording an explicit, time-boxed exception that someone owns rather than a habit plans drift into.

open as a page

Across a team's headless JMeter runs, which of JMeter's own output would you require every run to archive?

level: principalimportance: should knowfreq 38%

basics

~20 s

At minimum the captured stdout carrying the summariser lines, a per-run jmeter.log kept with -j, and the results file. JMeter tracks nothing about the injector host during a run, so decide separately where that comes from.

open as a page

In Apache JMeter's bin/jmeter, what is VERBOSE_GC and what must you do before it produces anything?

level: middleimportance: nice to knowfreq 24%

basics

~10 s

VERBOSE_GC is a slot the launcher expands into the JVM options between HEAP and GC_ALGO. Apache ships it unset, with two commented-out -Xlog:gc candidates, so you must uncomment one or export your own.

open as a page

Why can JMeter's non-GUI summariser print nothing for minutes while the test is still running?

level: middleimportance: nice to knowfreq 32%

basics

~20 s

Nothing schedules the line. JMeter checks whether a reporting boundary has passed only when a sample result arrives, so a window in which no sample completes produces no line at all rather than a zero-rate one.

open as a page