Blog
Mert Özen's blog posts on software development, backend, frontend, and DevOps.
A Map of API Testing Tools: Choosing Between curl, .http Files, Postman, Bruno and OpenAPI UIs
The real question when choosing a tool is where the request definitions live: .http files and Bruno collections in the repo change in the same pull request as the API code, while a cloud collection falls behind. We add login and JWT to Bookstore.Api, run the shared scenario with curl, put the Bearer scheme into the OpenAPI document, and compare Scalar's role, Postman's single-user free plan since March 2026 and Bruno's editions.
Testing APIs with curl: Methods, Headers, --json, Authentication, Uploads, Error Codes and Using It in Scripts
The rule for using curl safely in scripts is not to trust its exit code, which is 0 for 401 and 500 too: --fail-with-body exits with 22 and still prints the ProblemDetails. Against Bookstore.Api, with real output: -v and --trace-ascii, -d versus --json (415), keeping the token out of history with --variable and -H @file, cover uploads with -F and the antiforgery error, the limits of --retry, a smoke script, curl.exe quoting on Windows, Invoke-RestMethod and xh.
API Testing in the Repo with .http Files: Variables, Environments and Request Chaining in Visual Studio, Rider and VS Code
.http files live in the repo, but the same extension has three dialects: Visual Studio's {{login.response.body.$.accessToken}}, $dotenv and $shared go out unresolved in the JetBrains HTTP Client (ijhttp 2026.2), and 401s are not failures unless you write a test. Two files for Bookstore, http-client.env.json and secret providers, VS Code settings, a JUnit report with client.test, the http-client.private.env.json .gitignore misses, and a token caught by gitleaks.
Postman in Depth: Collections, Environments, Variable Scopes, Scripts, Tests, Mock Servers and the CLI
Keeping the Postman collection in the repo and running it in CI with Newman or the Postman CLI is the most robust answer to the single-user free plan since March 2026. A hand-written v2.1 collection for Bookstore: OpenAPI import, variable scope precedence, shared versus local values, a pre-request script that gets the token once, pm.test, an iteration failing on a data file, a JUnit report, and why the Postman CLI's local mock returns useless data.
A Git-friendly API Client: Keeping Collections in the Repo with Bruno, OpenCollection YAML and Running Them in CI with the CLI
Keeping a Bruno collection in the repo as OpenCollection YAML files and running it in GitHub Actions with the Bruno CLI turns request changes into readable diffs in code review. A collection with inherited auth for Bookstore, OpenAPI and Postman import (pm.variables.get mistranslated to bru.getVar), secrets via .env, assertions and test scripts, JUnit/HTML reports, the CLI exiting with 2 without a report folder, and a run that silently skips a .bru file in a YAML collection.