Install any skill in seconds. Free to start, no credit card required.
Get Started Free →When the user wants to perform load testing or performance testing using Artillery with YAML-based scenario definitions. Also use when the user mentions "artillery," "YAML load test," "WebSocket testing," "Socket.io load test," "scenario-based load testing," or "artillery run." For JavaScript-based load testing, see k6.
.claude/skills/terminalskills-artillery/SKILL.md| Test case | Without → With | Effect | Δ tokens | Δ turns |
|---|---|---|---|---|
| case-05 | ✗→✓ | ▲ Improved | 59% | 0% |
| case-07 | ✗→✓ | ▲ Improved | 83% | 0% |
| case-11 | ✗→✓ | ▲ Improved | 94% | 0% |
| case-16 | ✗→✓ | ▲ Improved | 138% | 0% |
| case-19 | ✗→✓ | ▲ Improved | 49% | 0% |
You are an expert in Artillery, the modern load testing toolkit. You help users define test scenarios in YAML, configure phases for ramping traffic, test HTTP APIs and WebSocket/Socket.io services, write custom JavaScript functions for complex flows, and generate HTML reports. You understand Artillery's plugin ecosystem and CI integration.
Before creating a test scenario:
yaml# load-test.yml — Artillery scenario testing an HTTP API. # Ramps from 5 to 50 requests per second over 3 phases. config: target: "https://api.example.com" phases: - duration: 60 arrivalRate: 5 name: "Warm up" - duration: 120 arrivalRate: 25 name: "Ramp up" - duration: 60 arrivalRate: 50 name: "Peak load" defaults: headers: Content-Type: "application/json" scenarios: - name: "Browse and purchase" flow: - get: url: "/products" capture: - json: "$.products[0].id" as: "productId" - think: 2 - get: url: "/products/{{ productId }}" - think: 1 - post: url: "/cart" json: productId: "{{ productId }}" quantity: 1
yaml# websocket-test.yml — Artillery scenario testing a WebSocket server. # Connects, sends messages, and validates responses. config: target: "wss://ws.example.com" phases: - duration: 60 arrivalRate: 10 engines: ws: {} scenarios: - engine: "ws" flow: - send: payload: '{"type": "subscribe", "channel": "updates"}' - think: 1 - send: payload: '{"type": "message", "text": "hello"}' - think: 5
yaml# socketio-test.yml — Artillery scenario for Socket.io real-time apps. # Simulates users joining rooms and exchanging messages. config: target: "http://localhost:3000" phases: - duration: 60 arrivalRate: 20 engines: socketio: transports: ["websocket"] scenarios: - engine: "socketio" flow: - emit: channel: "join" data: room: "general" username: "user_{{ $randomNumber(1, 1000) }}" - think: 2 - emit: channel: "message" data: text: "Hello from Artillery" - think: 3
yaml# custom-flow.yml — Artillery scenario with custom JS processing. # Uses beforeRequest and afterResponse hooks for dynamic data. config: target: "https://api.example.com" phases: - duration: 120 arrivalRate: 10 processor: "./helpers.js" scenarios: - flow: - function: "generateUser" - post: url: "/users" json: name: "{{ name }}" email: "{{ email }}" beforeRequest: "addAuthToken" afterResponse: "logResponse"
javascript// helpers.js — Custom Artillery processor functions. // Generates dynamic data and handles auth tokens. module.exports = { generateUser(context, events, done) { context.vars.name = `user_${Date.now()}`; context.vars.email = `user_${Date.now()}@test.com`; return done(); }, addAuthToken(req, context, events, done) { req.headers = req.headers || {}; req.headers['Authorization'] = `Bearer ${context.vars.token || 'test-token'}`; return done(); }, logResponse(req, res, context, events, done) { if (res.statusCode !== 200) { console.log(`Error: ${res.statusCode} on ${req.url}`); } return done(); }, };
bash# run-artillery.sh — Common Artillery commands. # Install, run tests, and generate reports. # Install npm install -g artillery # Run a test artillery run load-test.yml # Generate HTML report artillery run --output results.json load-test.yml artillery report results.json --output report.html # Quick test (no YAML needed) artillery quick --count 100 --num 10 https://api.example.com/health
yaml# .github/workflows/artillery.yml — Run Artillery in GitHub Actions. # Posts HTML report as an artifact. name: Load Test on: push: branches: [main] jobs: artillery: runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - uses: actions/setup-node@v4 with: node-version: 20 - run: npm install -g artillery - run: artillery run --output results.json tests/load-test.yml - run: artillery report results.json --output report.html - uses: actions/upload-artifact@v4 if: always() with: name: artillery-report path: report.html
| Case | Status | Duration (ms) | Turns | Tokens | Tool calls | ||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
| Without | With | Δ | Without | With | Δ | Without | With | Δ | Without | With | Δ | ||
case-01 | fail→fail | 15,513 | 14,598 | -6% | 1 | 1 | 0% | 2,522 | 3,984 | +58% | 0 | 0 | — |
case-02 | fail→fail | 10,371 | 9,357 | -10% | 1 | 1 | 0% | 2,021 | 3,354 | +66% | 0 | 0 | — |
case-03 | pass→pass | 8,826 | 5,547 | -37% | 1 | 1 | 0% | 1,529 | 2,484 | +62% | 0 | 0 | — |
case-08 | pass→pass | 9,452 | 5,143 | -46% | 1 | 1 | 0% | 1,496 | 2,120 | +42% | 0 | 0 | — |
case-18 | pass→pass | 5,444 | 3,947 | -27% | 1 | 1 | 0% | 1,048 | 1,903 | +82% | 0 | 0 | — |
case-04 | pass→pass | 10,865 | 9,817 | -10% | 1 | 1 | 0% | 1,842 | 3,191 | +73% | 0 | 0 | — |
case-05 | fail→pass | 9,752 | 6,128 | -37% | 1 | 1 | 0% | 1,618 | 2,580 | +59% | 0 | 0 | — |
case-06 | fail→fail | 10,109 | 7,874 | -22% | 1 | 1 | 0% | 1,704 | 2,587 | +52% | 0 | 0 | — |
case-07 | fail→pass | 7,414 | 5,687 | -23% | 1 | 1 | 0% | 1,357 | 2,490 | +83% | 0 | 0 | — |
case-09 | pass→pass | 8,846 | 5,448 | -38% | 1 | 1 | 0% | 1,603 | 2,271 | +42% | 0 | 0 | — |
case-10 | pass→pass | 4,835 | 2,884 | -40% | 1 | 1 | 0% | 781 | 1,958 | +151% | 0 | 0 | — |
case-11 | fail→pass | 6,516 | 5,173 | -21% | 1 | 1 | 0% | 1,240 | 2,403 | +94% | 0 | 0 | — |
case-12 | pass→pass | 7,637 | 4,678 | -39% | 1 | 1 | 0% | 1,548 | 2,288 | +48% | 0 | 0 | — |
case-13 | pass→pass | 7,840 | 5,483 | -30% | 1 | 1 | 0% | 1,490 | 2,510 | +68% | 0 | 0 | — |
case-14 | fail→fail | 10,102 | 5,194 | -49% | 1 | 1 | 0% | 1,644 | 2,386 | +45% | 0 | 0 | — |
case-15 | pass→pass | 5,873 | 3,472 | -41% | 1 | 1 | 0% | 1,021 | 2,065 | +102% | 0 | 0 | — |
case-16 | fail→pass | 3,846 | 3,049 | -21% | 1 | 1 | 0% | 790 | 1,879 | +138% | 0 | 0 | — |
case-17 | pass→pass | 7,243 | 7,122 | -2% | 1 | 1 | 0% | 1,503 | 2,925 | +95% | 0 | 0 | — |
case-19 | fail→pass | 7,963 | 5,342 | -33% | 1 | 1 | 0% | 1,632 | 2,427 | +49% | 0 | 0 | — |
case-20 | pass→pass | 8,036 | 7,272 | -10% | 1 | 1 | 0% | 1,454 | 2,545 | +75% | 0 | 0 | — |
case-21 | pass→pass | 7,067 | 6,942 | -2% | 1 | 1 | 0% | 1,304 | 2,678 | +105% | 0 | 0 | — |
case-22 | pass→fail | 7,619 | 7,163 | -6% | 1 | 1 | 0% | 1,605 | 2,938 | +83% | 0 | 0 | — |
case-23 | pass→fail | 13,042 | 8,958 | -31% | 1 | 1 | 0% | 3,402 | 3,588 | +5% | 0 | 0 | — |
case-24 | pass→fail | 10,868 | 8,942 | -18% | 1 | 1 | 0% | 2,252 | 3,384 | +50% | 0 | 0 | — |
DecimalAI ran this skill against gemini-3.6-flash twice over the same eval suite — once with the skill loaded and once without — and compared the two runs case by case. 24 cases were attempted. The headline lift of +8 percentage points is the difference between those two pass rates over the 24 comparable cases. 3 cases got worse with the skill loaded, and they are included in that figure.
Without the skill loaded, the model failed this case. With it loaded, the same prompt on the same model passed. This is one improved case from the latest verified run; every case, including any that regressed, is in the table above.
Other measured skills in the registry, with their headline benchmark lift.