/commands/http/get-http-status-code-curl
curl get only the HTTP status code: curl -s -o /dev/null -w '%{http_code}'
- tool
- HTTP
- versions
- curl 7.x / 8.x
- os
- linux, macos, windows
curl -s -o /dev/null -w '%{http_code}\n' URL prints only the three-digit HTTP status code of the response, for example 200 or 404. -o /dev/null discards the body, -s hides the progress meter, and -w (write-out) prints a variable after the transfer finishes. It is the usual way to check an endpoint from a shell script, a health check or a CI job.
Example against a local server
cat > server.js <<'EOF'
const http = require("http");
http.createServer((req, res) => {
if (req.url === "/missing") { res.writeHead(404); return res.end("not found\n"); }
if (req.url === "/old") { res.writeHead(301, { Location: "/" }); return res.end(); }
res.end("ok\n");
}).listen(5205, "127.0.0.1");
setTimeout(() => process.exit(0), 10000);
EOF
node server.js &
sleep 1
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:5205/
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:5205/missing
curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:5205/old
curl -sL -o /dev/null -w '%{http_code} after %{num_redirects} redirect(s)\n' http://127.0.0.1:5205/old
waitOutput
200 404 301 200 after 1 redirect(s)
Without -L, curl reports the redirect itself (301); with -L it follows the Location header and reports the status of the last response.
Use it in a script
code=$(curl -s -o /dev/null -w '%{http_code}' --max-time 10 https://api.example.com/health)
if [ "$code" != "200" ]; then
echo "health check failed: HTTP $code" >&2
exit 1
fi--max-time 10 stops a hanging server from blocking the script. Quote the format string: in some shells % and {} have special meaning, and in Windows cmd.exe the % must be doubled (%%{http_code}).
Variants
| Command | What it gives you |
|---|---|
| curl -s -o /dev/null -w '%{http_code}' URL | Status code of the response, body discarded |
| curl -sL -o /dev/null -w '%{http_code}' URL | Status code of the final response after redirects |
| curl -s -o /dev/null -w '%{http_code} %{redirect_url}' URL | Status code and the URL a redirect points to |
| curl -sf URL | Exit code 22 for any status of 400 or higher, nothing printed |
| curl -s --fail-with-body URL | Exit code 22 on errors but still prints the error body (curl 7.76+) |
| curl -sI URL | HEAD request: status line and headers only |
%{response_code} is an alias of %{http_code}. On Windows PowerShell, /dev/null does not exist: use -o NUL with curl.exe, and call curl.exe explicitly because curl in Windows PowerShell 5.1 is an alias of Invoke-WebRequest.
Pitfalls
- A status of
000is not an HTTP status: no response came back. curl's own exit code tells you why, for example 7 when the connection is refused (see connect ECONNREFUSED). -falone hides the error body, which often explains a 4xx. Use--fail-with-bodywhen you need both.- Status codes are listed with their meaning in the HTTP status codes table; any value from 100 to 599 can appear.
FAQ
Why does curl print 000 as the status code?
curl never received an HTTP response: the connection was refused, the host name did not resolve, TLS failed or the request timed out. Check the exit code of curl (7 means it could not connect, 6 that the host did not resolve, 28 a timeout) and drop -s to see the error message.
Should I use -I to get the status code?
Only if the server handles HEAD correctly. -I sends a HEAD request, and some servers answer HEAD with a different status (405 or 404) than GET. -o /dev/null -w '%{http_code}' sends the real GET and throws the body away.
How do I get the status code and the body at the same time?
Write the body to a file and print the code with -w, for example curl -s -o body.json -w '%{http_code}' URL. The variable is printed after the transfer, so the code arrives on stdout and the body in the file.