06 · Using curl, httpie & Postman¶
You'll spend a large fraction of your API-development life issuing manual
requests to explore, test, and debug. This module covers the three most
common tools: curl (universal, scriptable), httpie (friendlier syntax),
and Postman (GUI, great for saved collections and teams).
curl¶
curl ships on essentially every Linux/macOS system and is the lowest
common denominator — if you can only learn one tool, learn this one.
Basic GET¶
Prints only the response body by default.
See status code and headers with -i / -v¶
HTTP/1.1 200 OK
Content-Type: application/json
Content-Length: 63
{"id": 17, "title": "Dune", "author": "Frank Herbert"}
-i (include) prepends the response headers. -v (verbose) goes further,
also showing the request curl sent (see module 4).
POST with a JSON body¶
curl -i -X POST https://api.example.com/books \
-H "Content-Type: application/json" \
-d '{"title": "Foundation", "author": "Isaac Asimov"}'
-X POST sets the method (curl infers POST automatically once you use
-d, but being explicit is clearer). -H adds a header; -d sets the body.
PATCH / PUT / DELETE¶
curl -X PATCH https://api.example.com/books/17 \
-H "Content-Type: application/json" \
-d '{"year": 1966}'
curl -X PUT https://api.example.com/books/17 \
-H "Content-Type: application/json" \
-d '{"title": "Dune", "author": "Frank Herbert", "year": 1966}'
curl -X DELETE https://api.example.com/books/17
Sending an auth header¶
curl https://api.example.com/me \
-H "Authorization: Bearer eyJhbGciOiJIUzI1NiJ9.eyJzdWIiOiI0MiJ9.xyz"
Query strings safely¶
curl -G https://api.example.com/books \
--data-urlencode "author=Ursula K. Le Guin" \
--data-urlencode "sort=-year"
Saving a response to a file, and only printing the status code¶
-w "%{http_code}\n" is invaluable in shell scripts that need to check
success/failure without parsing the body.
httpie¶
httpie (the http command) reads more like plain English and pretty-prints
JSON with syntax highlighting by default — many people prefer it for
interactive exploration, though curl remains more universal for scripting
and CI since it's preinstalled almost everywhere.
Basic GET¶
(the scheme defaults to http://; add https:// explicitly for HTTPS, or
use https api.example.com/... as shorthand)
POST with JSON — no manual escaping needed¶
httpie infers Content-Type: application/json automatically and builds the
JSON body from key=value arguments — no need to hand-write a JSON string.
Use key:=value for non-string JSON values:
http POST api.example.com/books \
title="Foundation" \
year:=1951 \
in_stock:=true \
tags:='["sci-fi", "classic"]'
Custom headers and auth¶
http GET api.example.com/me "Authorization:Bearer eyJhbGciOiJIUzI1NiJ9..."
# Or with the built-in auth helper for Basic auth:
http -a username:password GET api.example.com/me
Query parameters¶
Note == for query parameters vs. =/:= for body fields — this is
httpie's key syntax distinction.
curl vs httpie — when to use which¶
| curl | httpie | |
|---|---|---|
| Preinstalled everywhere | Yes | No (needs pip install httpie or a package manager) |
| Scripting / CI | Best choice | Works, less common in scripts |
| Interactive exploration | Verbose syntax | Faster to type, colorized output |
| JSON body construction | Manual (hand-write JSON string) | Automatic from key=value args |
Postman¶
Postman is a GUI application built around collections — saved, organized groups of requests you can share with a team, run in sequence, and attach tests to.
Core workflow¶
- Create a new request: pick the method (
GET/POST/...), enter the URL. - Add headers in the Headers tab (e.g.
Authorization,Content-Type). - For a body, go to the Body tab, select raw + JSON, and type the JSON payload.
- Click Send — Postman shows status code, response time, response size, headers, and a pretty-printed body.
- Save the request into a Collection so it's reusable and shareable.
Environments and variables¶
Postman lets you define variables like {{base_url}} or {{auth_token}}
per environment (e.g. "local," "staging," "production"), so the same
collection of requests can target different servers just by switching a
dropdown:
Why teams like it over curl for shared work¶
- A whole collection of requests (covering an entire API) can be exported as JSON and version-controlled, or shared via a Postman workspace.
- Postman can auto-generate equivalent
curlcommands from any request (Code button) — handy for turning exploratory GUI work into a script. - Built-in test scripts (JavaScript) can assert on status codes and response shape, turning a manual collection into a lightweight automated smoke test suite.
Choosing a tool¶
- Quick one-off check, or a CI script:
curl. - Fast interactive exploration, especially with JSON bodies:
httpie. - Organizing dozens of endpoints across a team, with saved environments: Postman (or its open-source-friendly alternatives like Insomnia).
All three send exactly the same HTTP over the wire — pick based on your workflow, not on any difference in what's possible.
How It Actually Works¶
curl, HTTPie, and Postman are just three different HTTP clients — each
one performs the same low-level socket work, but you can see this most
clearly with curl's verbose flag:
* Connected to api.example.com (203.0.113.10) port 443
* TLS handshake, Client hello (1)
* TLS handshake, Server hello (2)
* SSL connection using TLSv1.3
> GET /books/17 HTTP/1.1
> Host: api.example.com
> Accept: */*
>
< HTTP/1.1 200 OK
< Content-Type: application/json
< Content-Length: 84
<
{"id":17,"title":"..."}
* Connection #0 to host api.example.com left intact
Every line curl prints with > is a header it generated and sent; every
< line is a header the server sent back. This is the actual raw exchange
that Postman's GUI and HTTPie's colorized output are also performing
underneath — they just parse the same bytes into a nicer view. "Connection
... left intact" is curl telling you it kept the TCP+TLS session open for
potential reuse (HTTP keep-alive), rather than tearing down and
renegotiating on your next request.
Postman's "Collections" and environment variables don't change any of this — they're client-side templating that gets resolved into the exact same plain-text request line and headers before anything touches the socket. If you can't explain a Postman failure, drop to curl -v against the same URL — you're removing a rendering layer, not changing the protocol.
Exercise¶
- Using
curl, write the command toPOSTa new resource tohttps://api.example.com/commentswith a JSON body{"post_id": 17, "text": "Great article!"}, including the correctContent-Typeheader, and printing the response headers. - Rewrite that same request using
httpiesyntax. - Using
curl, write aGETrequest to/searchwith query parametersq=rest api(note the space) andlimit=5, letting curl handle the URL-encoding. - In one sentence, explain what advantage a Postman collection gives a team of 5 backend engineers that a folder of curl one-liners in a text file doesn't.