Integration tests that use your app the way your users do.
Recorded from real traffic. Run on every pull request.
2,189 unit tests. One flow. Eight bugs.
The unit tests caught 5. The flow caught 6. Each caught a bug the other missed, and one got past both.
One named experiment on a small shop app, not a product benchmark. Read the method and every row.
4Both
- Body parser moved below the routes
- Route renamed
- Login and auth read different secrets
- New required column
2Only the flow
- Login token renamed, unit tests updated with it
- Create answers 200 instead of 201
1Only the unit tests
- A product update with no tags wipes the tags
1Neither
- A field renamed to camelCase in the product list
Keep your unit tests.
Unit tests
They check the logic inside one function and point at the line that broke. They can't see how the parts connect.
An API flow
It calls your running app like a client: routes, login, database. It catches the bugs between the parts, and only fails on what it checks.
Three commands to a check on every PR.
1Record
Use your app on localhost. Each journey becomes a YAML flow in api-tests/.
$ npx stresseur record
$ npx stresseur generate
2Add to CI
Writes the GitHub Actions workflow that runs your flows on every pull request.
$ npx stresseur init-ci
3Check every PR
One check and one comment per pull request, updated on each push.
Stresseurcheck
What a flow checks.
- Real routes
- Every request goes through your router and middleware, in the order your app sets them.
- Real auth
- The flow logs in like a client and sends the token it got back.
- The database
- Creates, reads and updates hit your real schema, columns and constraints.
- Values between steps
- A token or an ID from one response feeds the next request, mapped from the recording.
- request: name: Login method: POST url: '{{ #env:APP_URL }}/api/auth/login'- request: name: ListCategories depends_on: Login method: GET url: '{{ #env:APP_URL }}/api/categories' headers: { Authorization: 'Bearer {{ Login.response.body.token }}' } assertions: - response.status == 200If login stops returning token, the next step gets a 401 and the check fails.
Add the test your unit suite can't write.
The free plan covers 1 private repo.