Linux/Mac curl 命令参数详解


Linux/Mac curl 命令参数深度解析:网络交互瑞士军刀

curl(Client for URLs)是一个在 Linux、macOS 以及 Windows 等多种操作系统上广泛使用的命令行工具和库,用于与服务器进行数据传输。它支持多种协议,包括 HTTP、HTTPS、FTP、FTPS、SCP、SFTP、LDAP、LDAPS、DICT、FILE、GOPHER、IMAP、IMAPS、POP3、POP3S、RTMP、RTSP、SMTP、SMTPS、TELNET 和 TFTP 等。由于其强大的功能和灵活性,curl 成为了开发人员、系统管理员和网络工程师进行 API 测试、文件下载、自动化脚本编写和网络诊断不可或缺的工具。

curl 的强大之处很大程度上体现在其丰富的命令行参数上。这些参数允许用户精细地控制请求的各个方面,从 HTTP 方法、请求头、请求体,到认证、代理、SSL/TLS 选项、连接管理等等。本文将对 curl 的常用及部分高级参数进行详细的分类解析,帮助你全面掌握这个强大的工具。

基本语法

curl 的基本命令格式如下:

bash
curl [options] [URL...]

  • options: 一系列用于修改 curl 行为的参数,通常以 --- 开头。
  • URL...: 一个或多个需要访问的 URL。

一、 基本用法与输出控制

这类参数主要控制 curl 的基本操作和输出内容的格式与位置。

  1. 无参数(默认 GET):

    • 用法: curl https://example.com
    • 说明: 最简单的用法。默认使用 GET 方法请求指定的 URL,并将服务器返回的响应体(通常是 HTML 源码、JSON 数据等)直接输出到标准输出(stdout)。
  2. -o, --output <file>: 将输出写入文件,而非标准输出。

    • 用法: curl -o page.html https://example.com
    • 说明: 将从 https://example.com 获取的内容保存到当前目录下的 page.html 文件中。如果文件已存在,会被覆盖。
  3. -O, --remote-name: 将输出写入文件,文件名使用 URL 中推断的文件名。

    • 用法: curl -O https://example.com/path/to/archive.zip
    • 说明: 下载 archive.zip 并将其保存在当前目录下,文件名也为 archive.zip。这对于下载文件名明确的文件非常方便。需要注意的是,它只使用 URL 的最后一部分作为文件名,不创建目录结构。
  4. -J, --remote-header-name: 结合 -O 使用,让 curl 尝试从服务器响应的 Content-Disposition 头中提取文件名。

    • 用法: curl -O -J https://example.com/download?file_id=123
    • 说明: 如果服务器在响应头中提供了 Content-Disposition: attachment; filename="report.pdf",那么即使 URL 本身不包含明确的文件名,curl 也会将文件保存为 report.pdf。这是处理动态生成文件名下载链接的推荐方式。
  5. -s, --silent: 静默模式。

    • 用法: curl -s https://example.com
    • 说明: 不显示进度条或错误信息。这在脚本中只想获取纯粹的输出数据时非常有用。错误仍然可以通过退出码($?)检查。
  6. -S, --show-error: 在静默模式(-s)下,如果发生错误,仍然显示错误信息。

    • 用法: curl -sS https://nonexistent.example.com
    • 说明: 结合 -s 使用,既隐藏了正常操作的进度条,又能在请求失败时(如 DNS 解析失败、连接超时等)看到具体的错误提示。
  7. -v, --verbose: 显示详细的操作信息。

    • 用法: curl -v https://example.com
    • 说明: 输出详细的连接过程、发送的请求头、接收的响应头以及其他诊断信息。对于调试网络请求非常有帮助。输出以 * 开头的行是 curl 的内部信息,以 > 开头的行是发送的请求数据(包括请求行和头),以 < 开头的行是接收到的响应数据(包括状态行和头)。
  8. --trace <file>: 将所有传入和传出的数据(包括二进制)记录到指定文件。

    • 用法: curl --trace trace.log https://example.com
    • 说明: 比 -v 更详细,记录了完整的请求和响应(包括主体),用于深度调试。
  9. --trace-ascii <file>: 类似 --trace,但以 ASCII 格式记录,隐藏了敏感信息(如密码)并使非文本数据更易读。

    • 用法: curl --trace-ascii debug.log https://example.com
    • 说明: 调试时常用,比原始 trace 更易于人类阅读。
  10. -L, --location: 跟随重定向。

    • 用法: curl -L http://example.com
    • 说明: 如果服务器返回 3xx 重定向状态码(如 301 Moved Permanently, 302 Found),curl 会自动请求 Location 头指向的新 URL。默认情况下 curl 不会跟随重定向。

二、 HTTP 请求方法

控制 curl 使用哪种 HTTP 方法发送请求。

  1. -X, --request <method>: 指定请求方法。

    • 用法:
      • curl -X POST https://api.example.com/users
      • curl -X PUT https://api.example.com/users/1
      • curl -X DELETE https://api.example.com/users/1
      • curl -X HEAD https://example.com (只获取响应头)
    • 说明: 可以指定 GET, POST, PUT, DELETE, PATCH, HEAD, OPTIONS 等任何标准的或自定义的 HTTP 方法。注意,某些方法(如 POST, PUT)通常需要配合 -d-F 参数发送数据。
  2. -G, --get: 强制将 -d--data 系列参数提供的数据附加到 URL 的查询字符串中,并使用 GET 方法。

    • 用法: curl -G --data "search=keyword&page=1" https://example.com/search
    • 说明: 这会将请求变成 https://example.com/search?search=keyword&page=1。即使你指定了 -X POST-G 也会强制使用 GET 方法。这是一种构造带参数的 GET 请求的便捷方式,尤其是当参数包含特殊字符需要 URL 编码时(--data-urlencode 配合 -G 效果更佳)。
  3. -I, --head: 只获取 HTTP 响应头。

    • 用法: curl -I https://example.com
    • 说明: 相当于执行 curl -X HEAD https://example.com。这对于检查服务器状态、Content-TypeLast-Modified 等元信息而不下载整个内容非常有用。

三、 请求头(Headers)

定制发送给服务器的 HTTP 请求头。

  1. -H, --header <header/@file>: 添加自定义请求头。

    • 用法:
      • curl -H "Content-Type: application/json" -H "Authorization: Bearer YOUR_TOKEN" https://api.example.com/data
      • curl -H "Accept-Language: en-US,en;q=0.9" https://example.com
      • curl -H @headers.txt https://example.com (从文件 headers.txt 读取,每行一个头)
    • 说明: 可以多次使用 -H 来添加多个头。如果提供的头与 curl 默认添加的头(如 Host, User-Agent)同名,自定义的头会覆盖默认值。要移除 curl 内部添加的某个头,可以设置为空值,例如 -H "Accept:"。要发送一个没有值的头(例如 DNT),使用分号结尾:-H "DNT;"
  2. -A, --user-agent <agent string>: 设置 User-Agent 请求头。

    • 用法: curl -A "MyCustomClient/1.0" https://example.com
    • 说明: 覆盖 curl 默认的 User-Agent 字符串(如 curl/7.68.0)。有些网站会根据 User-Agent 返回不同的内容或限制访问。
  3. -e, --referer <URL>: 设置 Referer 请求头。

    • 用法: curl -e "https://previous-page.com" https://example.com/current-page
    • 说明: 模拟用户是从 previous-page.com 点击链接来到 current-page 的。

四、 请求数据(Data)

向服务器发送请求体,常用于 POST、PUT、PATCH 等方法。

  1. -d, --data <data>: 发送 URL 编码的 POST 数据(application/x-www-form-urlencoded)。

    • 用法:
      • curl -d "name=John Doe&city=New York" https://api.example.com/submit
      • curl -d '{"key": "value", "num": 123}' -H "Content-Type: application/json" https://api.example.com/post_json (注意:-d 默认会 URL 编码,对于 JSON,通常需要配合 -H "Content-Type: application/json" 并确保 JSON 字符串本身是有效的)
      • curl -d @data.txt https://api.example.com/submit (从文件 data.txt 读取数据)
    • 说明: 这是发送表单数据最常用的方式。curl 会自动将数据进行 URL 编码,并设置 Content-Typeapplication/x-www-form-urlencoded。如果同时指定了 -X POST,则使用 POST;否则,默认使用 POST。
  2. --data-raw <data>: 类似 -d,但不解析 @ 符号。

    • 用法: curl --data-raw "param=@value" https://example.com
    • 说明: 如果你的数据本身就包含 @ 字符,并且不想让 curl 将其解释为文件路径,使用 --data-raw
  3. --data-urlencode <data>: 类似 -d,但会对数据进行 URL 编码。

    • 用法:
      • curl --data-urlencode "comment=This needs encoding & stuff!" https://api.example.com/comment
      • curl -G --data-urlencode "query=search term with spaces" https://example.com/search (配合 -G 用于 GET 请求)
    • 说明: 对于需要确保特殊字符(如 &, =, 空格)被正确编码的场景非常有用。可以多次使用。
  4. --data-binary <data>: 发送二进制数据,不做任何处理。

    • 用法: curl --data-binary @image.jpg -H "Content-Type: image/jpeg" https://api.example.com/upload
    • 说明: 当你需要发送原始的二进制数据(如上传图片、文件)且不希望 curl 进行任何编码或换行符转换时使用。通常需要配合 -H 设置正确的 Content-Type
  5. -F, --form <name=content>: 发送 multipart/form-data 数据,常用于文件上传。

    • 用法:
      • curl -F "name=John Doe" -F "avatar=@/path/to/photo.jpg;type=image/jpeg" https://api.example.com/profile
      • curl -F "config=</path/to/config.json;type=application/json" https://api.example.com/upload_config (使用 < 从文件读取内容作为字段值)
      • curl -F "data={\"key\":\"value\"};type=application/json" https://api.example.com/form_json (直接提供字符串内容)
    • 说明: 模拟 HTML 表单提交,特别是包含文件上传 (<input type="file">) 的情况。
      • name=content: 普通表单字段。
      • name=@filepath: 上传文件,curl 会自动读取文件内容,并附带文件名。
      • name=<filepath: 将文件内容作为字段值发送,但不包含文件名。
      • 可以附加 ;type=mimetype 来指定内容的 MIME 类型。
      • 可以附加 ;filename=customname 来指定在请求中使用的文件名。
  6. --json <json data/@file> (较新版本的 curl 支持): 发送 JSON 数据,自动设置 Content-Type: application/json

    • 用法:
      • curl --json '{"name": "Alice", "age": 30}' https://api.example.com/users
      • curl --json @user_data.json https://api.example.com/users
    • 说明: 这是发送 JSON 数据的推荐方式(如果你的 curl 版本支持)。它简化了操作,自动设置了正确的 Content-Type 头,并通常使用 POST 方法。相当于 curl -d '...' -H "Content-Type: application/json" 的快捷方式。

五、 认证(Authentication)

处理需要用户名密码或其他认证方式的请求。

  1. -u, --user <user:password>: 设置 HTTP 基本认证(Basic Authentication)。

    • 用法: curl -u username:password https://secure.example.com
    • 说明: curl 会自动将 username:password 进行 Base64 编码,并添加到 Authorization: Basic <base64-string> 请求头中。如果只提供用户名 (-u username),curl 会提示输入密码。
  2. --basic: 强制使用 HTTP 基本认证(即使 curl 默认可能尝试其他方式)。

  3. --digest: 使用 HTTP Digest 认证。curl 会自动处理 challenge-response 过程。需要配合 -u 提供用户名密码。

  4. --ntlm: 使用 HTTP NTLM 认证。需要配合 -u

  5. --negotiate: 使用 HTTP Negotiate (SPNEGO) 认证。通常用于 Kerberos 环境。需要配合 -u : (冒号表示无密码,由 GSS-API 处理)。

  6. --netrc, --netrc-optional, --netrc-file <file>: 从 .netrc 文件读取认证信息。

    • 说明: .netrc 文件(通常在用户主目录下)可以存储主机、用户名和密码,curl 可以自动查找并使用这些凭据。--netrc 表示必须找到匹配条目,--netrc-optional 表示如果找到就使用,找不到则继续(可能匿名或提示)。

六、 Cookie 管理

发送和接收 HTTP Cookie。

  1. -b, --cookie <data/@file>: 发送 Cookie。

    • 用法:
      • curl -b "sessionid=12345; user=logged_in" https://example.com (直接提供 Cookie 字符串)
      • curl -b cookies.txt https://example.com (从 Netscape cookie 文件格式的 cookies.txt 读取 Cookie)
    • 说明: 向服务器发送指定的 Cookie。
  2. -c, --cookie-jar <file>: 将服务器返回的 Set-Cookie 头保存到文件。

    • 用法: curl -c cookies.txt https://example.com/login -d "user=...&pass=..."
    • 说明: 在执行请求后,将服务器发送的 Cookie 写入指定的文件(Netscape cookie 文件格式)。这对于需要维持登录状态的后续请求非常有用。先登录并保存 Cookie,然后在后续请求中使用 -b cookies.txt 来发送这些 Cookie。

七、 SSL/TLS 相关

控制 HTTPS 请求的行为。

  1. -k, --insecure: 允许连接到 SSL 站点时不验证服务器证书。

    • 用法: curl -k https://self-signed.example.com
    • 说明: 极不推荐在生产环境或处理敏感数据时使用! 这会绕过证书验证,使连接容易受到中间人攻击。仅用于测试或连接使用自签名证书且你完全信任的内部服务。
  2. --cacert <file>: 指定用于验证服务器证书的 CA 证书包文件(PEM 格式)。

    • 用法: curl --cacert /path/to/ca-bundle.crt https://example.com
    • 说明: 使用指定的 CA 证书来验证服务器证书的有效性,而不是系统默认的 CA 库。
  3. --capath <dir>: 指定包含多个 CA 证书文件(PEM 格式)的目录。curl 会在此目录中查找合适的 CA 证书。

  4. --cert <certificate[:password]>: 指定客户端证书文件(PEM 格式),用于客户端身份验证。

    • 用法: curl --cert client.pem:password --key client.key https://secure.api.example.com
    • 说明: 用于需要双向 TLS (mTLS) 认证的场景。如果证书文件包含私钥,则 --key 可能不需要。如果私钥有密码保护,在此处提供。
  5. --key <key file>: 指定客户端私钥文件(PEM 格式)。

    • 用法: (见上例)
    • 说明: 与 --cert 配合使用,提供客户端证书对应的私钥。
  6. --cert-type <type>: 指定客户端证书类型(PEM, DER, ENG)。默认为 PEM。

  7. --key-type <type>: 指定私钥文件类型(PEM, DER, ENG)。默认为 PEM。

  8. --tls-max <VERSION>: 设置允许的最高 TLS 版本(如 1.2, 1.3)。

  9. --tlsv1.2, --tlsv1.3, etc.: 强制使用指定的 TLS 版本。


八、 网络与连接控制

管理网络连接、超时、重试和代理。

  1. --connect-timeout <seconds>: 设置建立 TCP 连接的最长等待时间(浮点数)。

    • 用法: curl --connect-timeout 5 https://example.com
    • 说明: 如果在指定秒数内无法与服务器建立连接,curl 将放弃并报错。
  2. -m, --max-time <seconds>: 设置整个操作(包括连接、数据传输等)允许的总时间(浮点数)。

    • 用法: curl -m 10 https://example.com/large-file
    • 说明: 如果整个 curl 操作超过指定秒数仍未完成,将被中断。
  3. --retry <num>: 在发生瞬时错误(如连接超时、5xx 服务器错误)时,重试请求的次数。

    • 用法: curl --retry 3 https://flaky.example.com
  4. --retry-delay <seconds>: 每次重试之间的等待时间(默认为 1 秒)。

  5. --retry-max-time <seconds>: 重试操作允许的总时间。

  6. -x, --proxy <[protocol://]host[:port]>: 指定使用的代理服务器。

    • 用法:
      • curl -x http://proxy.example.com:8080 https://target.com
      • curl -x socks5://localhost:1080 https://target.com
    • 说明: 支持 HTTP, HTTPS, SOCKS4, SOCKS4a, SOCKS5, SOCKS5h 代理。协议部分(如 http://)是可选的,默认为 HTTP。
  7. --proxy-user <user:password>: 设置代理服务器需要的认证信息。

  8. --noproxy <no-proxy-list>: 指定不通过代理访问的主机列表(逗号分隔,支持通配符 *)。

    • 用法: curl --proxy http://proxy.example.com:8080 --noproxy "*.internal.com,localhost" https://external.com
  9. --limit-rate <speed>: 限制传输速度(下载和上传)。

    • 用法: curl --limit-rate 100k -O https://example.com/large-file.zip (限制速度为 100 KB/s)
    • 说明: 支持后缀 k (KB), m (MB), g (GB)。
  10. -C, --continue-at <offset>: 断点续传。

    • 用法: curl -C - -O https://example.com/large-file.zip
    • 说明: -C - 告诉 curl 自动检测本地已下载文件的大小,并从那个偏移量开始继续下载。也可以指定具体的字节偏移量,如 -C 102400。需要服务器支持 Range 请求。
  11. --resolve <host:port:address[,address]...>: 提供自定义的 DNS 解析。

    • 用法: curl --resolve example.com:443:192.168.1.100 https://example.com
    • 说明: 强制将 example.com 的 443 端口解析到 IP 地址 192.168.1.100,绕过系统 DNS。这对于测试特定服务器或在 DNS 尚未生效时访问服务非常有用。

九、 其他有用参数

  1. -f, --fail: 在服务器返回 HTTP 错误码(4xx 或 5xx)时不输出任何内容(除非 -S 也被使用),并以错误码 22 退出。

    • 用法: curl -f -s https://httpbin.org/status/404
    • 说明: 在脚本中用于判断请求是否成功(HTTP 状态码为 2xx 或 3xx)。如果请求失败,不会有干扰性的 HTML 错误页面输出到 stdout。
  2. -w, --write-out <format>: 在请求完成后,根据指定的格式字符串输出额外信息。

    • 用法: curl -s -o /dev/null -w "Status: %{http_code}, Time: %{time_total}s\n" https://example.com
    • 说明: 非常适合在脚本中获取请求的元数据,如 HTTP 状态码 (%{http_code}), 总时间 (%{time_total}), 下载大小 (%{size_download}), 远程 IP (%{remote_ip}) 等。变量列表请查阅 man curl-o /dev/null 常用于丢弃响应体,只关注 -w 的输出。
  3. -T, --upload-file <file>: 上传本地文件。

    • 用法: curl -T localfile.txt ftp://ftp.example.com/remote/path/
    • 说明: 主要用于 FTP/SFTP 上传,也可以用于 HTTP PUT 请求。对于 HTTP PUT,URL 通常指向目标资源路径。
  4. -K, --config <config file>: 从文件中读取 curl 命令行参数。

    • 用法: curl -K myconfig.txt
    • 说明: 文件中每行可以包含一个或多个参数,就像在命令行上写一样。以 # 开头的行是注释。这对于保存复杂的常用 curl 命令非常有用。

总结

curl 是一个极其强大和灵活的命令行工具,其丰富的参数集赋予了用户对网络请求近乎完全的控制能力。从简单的网页抓取、文件下载,到复杂的 API 交互、认证处理、性能测试和网络调试,curl 都能胜任。

掌握 curl 的关键在于理解其参数的分类和作用:

  • 输出控制 (-o, -O, -s, -v): 决定内容去向和显示细节。
  • HTTP 方法 (-X, -G, -I): 定义请求类型。
  • 请求头 (-H, -A, -e): 定制发送给服务器的元信息。
  • 请求数据 (-d, -F, --json): 发送请求体内容。
  • 认证 (-u, --digest, --netrc): 处理访问权限。
  • Cookie (-b, -c): 管理会话状态。
  • SSL/TLS (-k, --cacert, --cert): 控制安全连接。
  • 网络连接 (--connect-timeout, -m, --proxy, -C): 管理连接行为和性能。

虽然本文覆盖了许多常用和重要的参数,但这并非 curl 的全部。当你遇到更具体或特殊的需求时,强烈建议查阅 curl 的官方手册页 (man curl) 或在线文档,那里有最全面、最权威的参数说明和示例。

熟练运用 curl 及其参数,无疑将极大提升你在命令行环境下处理网络任务的效率和能力。它不仅仅是一个工具,更是理解和探索网络世界的一把钥匙。

THE END