On this page 28 sections
- What cURL is useful for
- Basic GET requests
- Download a file
- Inspect the full HTTP exchange
- Response headers vs response body
- HEAD requests
- Ignore certificate validation in a lab
- Set a custom User-Agent
- Send custom headers
- HTTP Basic Authentication
- GET parameters
- POST form data
- Send JSON data
- Cookies and sessions
- Save cookies for later requests
- HTTP methods
- Read API data
- Format JSON with jq
- Create an API resource
- Update an API resource
- Delete an API resource
- Follow redirects
- Show only the HTTP status code
- Understand common HTTP status codes
- Browser DevTools and cURL
- Network tab workflow
- A practical request workflow
- Key takeaway
What cURL is useful for
cURL is a command-line tool for sending requests to web servers and APIs. It is useful for testing endpoints, inspecting headers, sending authentication data, reproducing browser requests and interacting with APIs without opening a browser.
curl -hBasic GET requests
When no HTTP method is specified, cURL sends a GET request by default. This is the simplest way to retrieve the content returned by a web endpoint.
curl https://sam0x.mecurl https://sam0x.me/index.htmlDownload a file
The -O option saves the response using the remote filename. The -s option enables silent mode and removes progress output.
curl -s -O https://sam0x.me/index.htmlInspect the full HTTP exchange
Verbose mode is one of the most useful cURL options when troubleshooting. The -v flag displays connection information, outgoing request headers and incoming response headers.
curl -v https://sam0x.meResponse headers vs response body
The -I option sends a HEAD request and returns only response headers. The -i option keeps the normal response body but includes the response headers above it.
curl -I https://sam0x.mecurl -i https://sam0x.meHEAD requests
A HEAD request is similar to GET but normally returns only metadata such as status code, content type, server information, cookies and caching headers. It is useful when you want to inspect an endpoint without downloading the full body.
curl -I https://sam0x.meIgnore certificate validation in a lab
The -k option disables TLS certificate verification. This is useful in controlled environments using self-signed certificates, but it should not be treated as a normal production configuration.
curl -k https://target1.sam0x.meSet a custom User-Agent
The User-Agent header identifies the client making the request. Some applications change behaviour depending on this header, so cURL allows it to be modified with -A.
curl https://sam0x.me -A 'Mozilla/5.0'Send custom headers
The -H option adds or overrides HTTP headers. This is frequently used for authorization tokens, content types, API keys and custom application headers.
curl -H 'X-Lab: sam0x' https://api.sam0x.mecurl -H 'Authorization: Basic YWRtaW46YWRtaW4=' https://target1.sam0x.meHTTP Basic Authentication
HTTP Basic Authentication sends a username and password as an Authorization header. cURL can generate this header automatically with -u.
curl -u admin:admin https://target1.sam0x.mecurl https://admin:admin@target1.sam0x.meGET parameters
GET parameters are appended to the URL after a question mark. Multiple parameters are separated with an ampersand. Quoting the full URL avoids shell interpretation issues.
curl 'https://sam0x.me/search.php?search=linux'curl 'https://sam0x.me/search.php?q=nmap&page=2'POST form data
The -d option sends request data. When used with standard key=value form data, cURL automatically uses POST unless another method is explicitly selected.
curl -X POST -d 'username=admin&password=admin' https://target1.sam0x.me/logincurl -d 'username=admin&password=admin' https://target1.sam0x.me/loginSend JSON data
APIs frequently expect JSON instead of traditional form data. The body is passed with -d and the Content-Type header tells the server that the payload is JSON.
curl -X POST https://api.sam0x.me/search -H 'Content-Type: application/json' -d '{"search":"linux"}'Cookies and sessions
Web applications often use cookies to maintain sessions. The -b option sends cookies with the request, making it possible to reproduce an authenticated browser session from the command line.
curl -b 'PHPSESSID=sam0xsession123' https://target1.sam0x.me/dashboardSave cookies for later requests
A useful extension to the basic cookie workflow is to save cookies returned by the server and reuse them later. -c writes cookies to a file, while -b can read them back.
curl -c cookies.txt -d 'username=admin&password=admin' https://target1.sam0x.me/logincurl -b cookies.txt https://target1.sam0x.me/dashboardHTTP methods
The -X option explicitly selects the HTTP method. GET reads data, POST commonly creates or submits data, PUT updates a resource, and DELETE removes a resource when the API supports those operations.
curl -X GET https://api.sam0x.me/userscurl -X POST https://api.sam0x.me/userscurl -X PUT https://api.sam0x.me/users/1curl -X DELETE https://api.sam0x.me/users/1Read API data
REST-style APIs usually expose resources through predictable URLs. A GET request can retrieve one entry or an entire collection.
curl https://api.sam0x.me/city/londoncurl -s https://api.sam0x.me/city/Format JSON with jq
API responses are often returned as JSON. Piping the output to jq makes nested JSON easier to read and inspect.
curl -s https://api.sam0x.me/city/ | jqCreate an API resource
A POST request is commonly used to create a new resource. The exact JSON fields depend on the API contract.
curl -X POST https://api.sam0x.me/city/ -H 'Content-Type: application/json' -d '{"city_name":"Sam0x_City","country_name":"Lab"}'Update an API resource
PUT is commonly used to replace or update an existing resource. Some APIs use PATCH for partial modifications instead, so always check the API behaviour.
curl -X PUT https://api.sam0x.me/city/london -H 'Content-Type: application/json' -d '{"city_name":"New_Sam0x_City","country_name":"Lab"}'Delete an API resource
DELETE requests are normally used to remove a resource identified by its URL.
curl -X DELETE https://api.sam0x.me/city/New_Sam0x_CityFollow redirects
Some endpoints respond with HTTP redirects instead of returning the final page directly. The -L option tells cURL to follow Location headers automatically.
curl -L https://sam0x.me/loginShow only the HTTP status code
When scripting or quickly validating endpoints, it can be useful to ignore the response body and print only the status code.
curl -s -o /dev/null -w '%{http_code}\n' https://sam0x.meUnderstand common HTTP status codes
cURL exposes the raw HTTP response, so understanding status codes is important. 200 generally means success, 301 and 302 indicate redirects, 401 indicates missing or invalid authentication, 403 means the server understood but refused the request, 404 indicates the resource was not found, and 500 indicates a server-side error.
Browser DevTools and cURL
Browser developer tools are useful for understanding the requests generated by a web application. The Network tab shows request methods, URLs, headers, cookies, parameters, request bodies and server responses. Once a request is understood, it can often be reproduced with cURL.
F12CTRL+SHIFT+INetwork tab workflow
When analysing a request in DevTools, start with the method and URL, then inspect request headers, cookies, query parameters or request payload, and finally review the response status, headers and body. These elements map directly to cURL options.
A practical request workflow
A good cURL workflow is to begin with the simplest request possible and add options only when needed. First retrieve the endpoint, then enable verbose output, inspect headers, reproduce authentication or cookies, and finally recreate the exact request body.
curl https://target1.sam0x.mecurl -v https://target1.sam0x.mecurl -i https://target1.sam0x.mecurl -X POST -H 'Content-Type: application/json' -d '{"search":"nmap"}' https://target1.sam0x.me/api/searchKey takeaway
cURL is most useful when you think in terms of HTTP rather than memorising flags. Identify the method, URL, headers, authentication, cookies and body of a request, then translate each part into the corresponding cURL option.