Command Line cho Developer · Part 6 - Debug API with curl & jq
Debug HTTP API bằng terminal: curl GET/POST, headers, auth, status code, redirects, timeout, verbose mode, lưu response và jq để đọc/lọc JSON.
Đây là Phần 6. Khi app frontend báo lỗi API, đừng đoán ngay. Dùng curl để gọi endpoint trực tiếp và jq để đọc JSON.
Bạn cần trả lời nhanh:
- API có reachable không?
- Status code là gì?
- Header có đúng không?
- Body gửi lên có đúng shape không?
- Response JSON có field mình cần không?
GET đơn giản
curl https://api.example.com/health
In cả header response:
curl -i https://api.example.com/health
Chỉ lấy header:
curl -I https://api.example.com/health
Follow redirect:
curl -L https://example.com
Thêm timeout:
curl --max-time 10 https://api.example.com/health
Nếu request treo mãi, timeout giúp bạn phân biệt server chậm với command đang chờ vô hạn.
Status code và fail mode
In status code cuối:
curl -s -o /tmp/response.json -w "%{http_code}\n" https://api.example.com/users
Giải thích:
| Flag | Nghĩa |
|---|---|
-s | silent, bớt progress noise |
-o file | ghi body vào file |
-w | in thông tin sau request |
Fail khi HTTP là 4xx/5xx:
curl --fail-with-body https://api.example.com/users
--fail-with-body hữu ích trong script: command trả non-zero khi HTTP lỗi nhưng vẫn giữ body lỗi để đọc.
Header và auth
Thêm header:
curl -H "Accept: application/json" https://api.example.com/users
Bearer token:
curl -H "Authorization: Bearer $TOKEN" https://api.example.com/me
Gửi nhiều header:
curl \
-H "Accept: application/json" \
-H "Authorization: Bearer $TOKEN" \
https://api.example.com/me
Không paste token thật vào shell history nếu đó là secret nhạy cảm. Ưu tiên biến môi trường tạm trong phiên shell, hoặc dùng secret manager của team.
POST JSON
curl -X POST https://api.example.com/users \
-H "Content-Type: application/json" \
-d '{"name":"Alice","role":"admin"}'
Với payload dài, để vào file:
cat > /tmp/user.json <<'JSON'
{
"name": "Alice",
"role": "admin"
}
JSON
curl -X POST https://api.example.com/users \
-H "Content-Type: application/json" \
--data @/tmp/user.json
--data @file giúp payload review được, tái chạy được, và tránh quote JSON rối trên một dòng.
Verbose mode để debug network
curl -v https://api.example.com/health
-v cho thấy:
- DNS/connect/TLS handshake;
- request headers;
- response headers;
- redirect hoặc lỗi chứng chỉ.
Khi chỉ cần trace rất chi tiết:
curl --trace-ascii /tmp/curl.trace https://api.example.com/health
Đừng share trace nếu nó chứa token/cookie.
Pretty print JSON với jq
curl -s https://api.example.com/users | jq .
Lấy field:
curl -s https://api.example.com/me | jq '.email'
curl -s https://api.example.com/me | jq -r '.email'
-r in raw string, không có dấu quote.
Lọc array:
curl -s https://api.example.com/users |
jq '.users[] | {id, email, role}'
Chọn item:
curl -s https://api.example.com/users |
jq '.users[] | select(.role == "admin") | .email'
Đếm:
curl -s https://api.example.com/users | jq '.users | length'
Lưu response để phân tích
curl -s https://api.example.com/users -o /tmp/users.json
jq '.users | length' /tmp/users.json
jq '.users[] | select(.active == false)' /tmp/users.json
Khi response lớn, lưu file trước giúp bạn thử nhiều query jq mà không gọi API lặp lại.
So sánh response giữa staging và production:
curl -s https://staging.example.com/config | jq -S . > /tmp/staging.json
curl -s https://example.com/config | jq -S . > /tmp/prod.json
diff -u /tmp/staging.json /tmp/prod.json
jq -S sort key để diff ổn định hơn.
Recipe developer hay dùng
Health check local:
curl -i http://localhost:3000/health
Kiểm tra CORS preflight:
curl -i -X OPTIONS http://localhost:3000/api/users \
-H "Origin: http://localhost:5173" \
-H "Access-Control-Request-Method: POST" \
-H "Access-Control-Request-Headers: content-type,authorization"
Đo thời gian request:
curl -s -o /dev/null -w "status=%{http_code} time=%{time_total}s\n" \
http://localhost:3000/api/users
Gửi form:
curl -X POST http://localhost:3000/login \
-d "email=a@example.com" \
-d "password=secret"
Upload file:
curl -X POST http://localhost:3000/upload \
-F "file=@./avatar.png"
Bài tập
- Gọi một endpoint local hoặc public bằng
curl -i. - Lưu response JSON vào
/tmp/response.json. - Dùng
jqlấy một field hoặc đếm số item trong array. - Dùng
curl -win status code và total time.
Lời giải tham khảo
curl -i https://api.github.com/repos/withastro/astro
curl -s https://api.github.com/repos/withastro/astro -o /tmp/astro.json
jq -r '.full_name' /tmp/astro.json
curl -s -o /dev/null -w "status=%{http_code} time=%{time_total}s\n" \
https://api.github.com/repos/withastro/astroĐiều cốt lõi
curl giúp bạn tách vấn đề API khỏi UI. jq giúp JSON đọc và lọc được. Khi bug HTTP xuất hiện, hãy gọi endpoint trực tiếp, xem status/header/body, rồi mới quay lại app.