Every lesson in this course has built toward this point. You have the tools — Thread Groups, extractors, timers, assertions, JSR223, CLI mode, InfluxDB, CI/CD pipelines. The capstone project assembles all of them into a professional-grade performance test suite for a realistic enterprise application.
The application: SecureBank
SecureBank is an online retail banking platform. Users can log in with multi-factor authentication, check account balances, review transaction history, transfer funds between accounts, and pay bills. It is a representative enterprise web application — session-based, database-heavy for some queries (transaction history), cached for others (balance check), and involving external systems for payment processing.
SecureBank is a fictional system. You will build the performance test suite design in full, and where an actual running endpoint is needed for practice tasks, the guided walkthrough provides alternatives. The architecture and SLA decisions are realistic — they reflect the kind of requirements you encounter in banking, insurance, and financial services performance engineering roles.
Performance SLAs
The product team and SRE have defined the following non-negotiable performance requirements:
| Endpoint | Metric | Threshold |
|---|---|---|
| POST /auth/login (with MFA) | p95 response time | < 800ms |
| GET /accounts/{id}/balance | p95 response time | < 300ms |
| GET /accounts/{id}/transactions | p95 response time | < 1500ms |
| POST /transfers | p95 response time | < 2000ms |
| POST /payments/bills | p95 response time | < 2000ms |
| All endpoints | Error rate | < 0.5% |
| All endpoints | Throughput | > 200 RPS at peak |
The login SLA (800ms) is higher than a typical unauthenticated endpoint because MFA adds a step — an OTP generation service is called, which adds ~200ms to the authentication path. The balance check SLA (300ms) is tight because it is cached at the application layer and should be near-instant.
Deliverables
The capstone requires a complete, version-controlled JMeter project. Here is what you are building:
- – test-plans/ — separate JMX per test type
- – environments/ — dev/staging/prod properties
- – data/ — users.csv, accounts.csv
- – scripts/ — quality gate, data gen
- – smoke.jmx — 1 user, verify all flows
- – load.jmx — 100 users, 30 min mixed load
- – stress.jmx — Stepping TG, find breaking point
- – spike.jmx — Ultimate TG, sudden surge
- – 10,000 users in CSV (email, password, mfa_key)
- – 50,000 accounts (accountId, userId, type)
- – Login → extract JWT + CSRF token
- – Transfer → extract transactionId
- Backend Listener → InfluxDB –
- Grafana dashboard (5496 + custom panels) –
- HTML report from .jtl post-test –
- CI/CD: smoke on PR, load nightly –
Workload model
The load test simulates real SecureBank user behaviour — not uniform hammering of every endpoint equally. Based on production analytics, here is the realistic request distribution:
| Flow | % of users | Operations |
|---|---|---|
| Balance check only | 60% | Login → check balance (2 accounts) → logout |
| Transaction review | 20% | Login → balance → transaction history (last 30 days) → logout |
| Fund transfer | 15% | Login → balance → transfer → confirm transfer → logout |
| Bill payment | 5% | Login → balance → bill lookup → pay bill → confirm → logout |
Implementing this distribution with Throughput Controllers means your 100-user test generates realistic mixed load rather than hammering every endpoint equally. The 60% balance-check users naturally drive the most GET /balance traffic; the 5% bill payment users generate payment system traffic proportional to real usage.
Think time
SecureBank users are real people taking deliberate actions, not automated bots. Think time per action reflects the nature of each step:
- Between login and first account view: 2–5 seconds (reading the login confirmation)
- Between account views: 3–8 seconds (user reviewing balance, deciding what to do)
- Before a transfer: 5–15 seconds (user entering amounts, verifying account numbers)
- Before bill payment: 8–20 seconds (looking up bill amount, confirming payee)
Use Gaussian Random Timers with means matching these ranges. Without think time, the test simulates automated bots, not human users — the concurrency model is wrong and the results do not reflect real capacity.
Correlation requirements
Banking applications are among the most correlation-intensive systems to load test. Every session involves multiple dynamic values:
Authentication flow:
- Login response returns a JWT access token (used as
Authorization: Bearer ${jwt}on all subsequent requests) - Login response may include a CSRF token (required on all state-changing requests)
- MFA verification may return a session upgrade token
Account operations:
- Account IDs are user-specific — must be extracted from the login response or an account list endpoint, not hardcoded
Transfer flow:
- Transfer submission returns a transaction ID (
transactionId) required for the confirmation step - Confirmation requires the same
transactionIdand a confirmation token returned by the submit step
Bill payment:
- Bill lookup returns a
billReferencerequired for the payment submission - Payment returns a
paymentIdfor the confirmation
Every dynamic value must be extracted from the correct response and threaded through to the request that needs it. Missing one breaks that entire flow for every virtual user.
Quality gates
CI/CD quality gates enforce the SLAs automatically:
thresholds = {
"POST /auth/login": {"p95": 800},
"GET /accounts/{id}/balance": {"p95": 300},
"GET /accounts/{id}/transactions":{"p95": 1500},
"POST /transfers": {"p95": 2000},
"POST /payments/bills": {"p95": 2000},
"ALL": {"error_rate": 0.5}
}The quality gate script reads the .jtl file, computes per-sampler p95, computes overall error rate, and exits non-zero if any threshold is exceeded. The CI/CD pipeline fails the build and notifies the team.
What professional performance testing actually looks like
This capstone mirrors what senior performance engineers deliver on real projects. The test suite you are building has:
- Multiple test types for different purposes (smoke, load, stress, spike)
- Realistic user behaviour (mixed scenarios, weighted distribution, think time)
- Full correlation (no hardcoded dynamic values)
- Parameterisation (one codebase, multiple environments)
- Observable execution (real-time Grafana dashboards)
- Automated quality gates (build fails on SLA breach)
- Version-controlled artefacts (
.jmxfiles, CSV data, pipeline definitions in git)
This is the standard that enterprise performance engineering teams operate at. A QA engineer who delivers a test suite at this level — with the artefacts, the pipelines, and the SLA enforcement — demonstrates senior-level competence regardless of job title.
Before you start
Review your work from Chapters 1–7 and confirm you can:
- Build a test plan from scratch in the JMeter GUI
- Configure CSV Data Set Config with correct sharing mode
- Add and verify JSON Extractors for correlation chains
- Configure Throughput Controllers for weighted scenario mixing
- Add Duration Assertions for per-sampler SLA enforcement
- Run the test in CLI mode and generate an HTML dashboard
- Configure a Backend Listener for InfluxDB
- Write a properties file and pass environment overrides via
-p
If any of those feel uncertain, revisit the relevant chapter before beginning the guided walkthrough in the next lesson.