如何通过cURL调用发送HTTP请求头?

1965

我希望通过cURL调用向我的Linux Apache服务器发送标头。如何实现这一点?


101
学习如何使用curl进行HTTP请求有一个好方法,即通过示例。下载最新版本的Postman,在用户界面级别上进行任何HTTP请求配置(例如,使用标头和JSON正文进行POST、PUT、GET等),然后单击“生成代码”并选择“curl”选项。它会给出相应的命令行。 - Vinicius Lima
3
这是一个2分钟的视频链接,用于上面提到的方法。链接地址为https://youtu.be/L3m6cpQPsV0。 - VedantK
11个回答

2294

curl命令手册:

   -H/--header <header>
          (HTTP)  Extra header to use when getting a web page. You may specify
          any number of extra headers. Note that if you should  add  a  custom
          header that has the same name as one of the internal ones curl would
          use, your externally set header will be used instead of the internal
          one.  This  allows  you  to make even trickier stuff than curl would
          normally do. You should not replace internally set  headers  without
          knowing  perfectly well what you're doing. Remove an internal header
          by giving a replacement without content on the  right  side  of  the
          colon, as in: -H "Host:".

          curl  will  make sure that each header you add/replace get sent with
          the proper end of line marker, you should thus not  add  that  as  a
          part  of the header content: do not add newlines or carriage returns
          they will only mess things up for you.

          See also the -A/--user-agent and -e/--referer options.

          This option can be used multiple times to add/replace/remove  multi-
          ple headers.

示例 1:单个标题

curl --header "X-MyHeader: 123" www.google.com

示例 2:多个标题

curl --header "Accept: text/javascript" --header "X-Test: hello" -v www.google.com
可以通过添加-v选项来查看curl发送的请求。

115
如果想要发送多个头部信息,可以使用多个--header参数,curl会将每个参数视为不同的头部信息进行解析。无法在同一个--header参数中分隔不同的头部信息。例如:curl --header "Accept: javascript" --header "test: hello" -v www.google.com - Hatoru Hansou
5
如果人们需要示例,我会在这里提供一个链接:http://bropages.org/。 - Rachel K. Westmacott
1
手册页(至少在OSX上)现在包括一个示例: 示例: #curl -H“X-First-Name:Joe”http://192.168.0.1/ - JESii
9
@MartinKonicek 和其他人:我强烈推荐 tldr 工具(使用 brew 等安装 tldr)。它只提供示例。例如:“- 使用自定义 HTTP 方法发送带有额外头部的请求: curl -H 'X-My-Header: 123' -X PUT http://example.com”。 - user3853034
这篇帖子应该成为被采纳的答案。然而,目前被采纳的答案虽然正确,但只是隐含地回答了提问者的问题。 - Robert
显示剩余2条评论

901

获取(GET):

使用JSON格式:

curl -i -H "Accept: application/json" -H "Content-Type: application/json" http://hostname/resource

使用XML:

curl -H "Accept: application/xml" -H "Content-Type: application/xml" -X GET http://hostname/resource

POST:

用于发布数据:

curl --data "param1=value1&param2=value2" http://hostname/resource

文件上传:

curl --form "fileupload=@filename.txt" http://hostname/resource

RESTful HTTP Post:

curl -X POST -d @filename http://hostname/resource

用于登录网站(认证):

curl -d "username=admin&password=admin&submit=Login" --dump-header headers http://localhost/Login
curl -L -b headers http://localhost/

@filename在RESTful post中是什么意思?你是要将文件POST到REST服务器吗?这对我来说似乎很奇怪。 - JesseBoyd
13
对于之后到达并可能有相同疑问的人……@符号是一种从文件中读取数据以发送到服务器的方法,而不是将其内联到curl请求中。你并不是直接POST一个文件,而是将文件内容作为POST请求体进行POST。 - f1dave
更详细的答案在这里:https://dev59.com/XmUp5IYBdhLWcg3w5Kg6#14978657 :) - Amith Koujalgi
如果我正确理解了头部的使用:Accept 头部是为了 客户端(发出请求)想要的内容,但 Content-Type 头部只是服务器的 回答,没有更多意义,它不是客户端的意愿:“我想要这种类型的内容”。对吗?所以对于 GET 请求 curl -i -H "Accept: application/json" http://hostname/resource 应该就可以了。我错了吗?请参见 https://developer.mozilla.org/zh-CN/docs/Web/HTTP/Headers/Content-Type 《在响应中,Content-Type 首部告诉客户端实际返回的内容类型。》 - andreas.naturwiki
1
@andreas.naturwiki,再次提醒不要混淆。来自MDN的“在响应中...”意味着响应中的Content-Type,而不是请求。Content-Type始终指的是两个参与方之间传输的数据类型。如果它在请求头中,这意味着客户端告诉服务器“是的,我正在向您发送数据类型为application/json”。如果它在响应中,则表示服务器告诉客户端“现在我正在向您发送数据类型为text/plain”。 - fa wildchild
@andreas.naturwiki Content-Type 是你在请求主体中发送的内容类型,而 Accept 是你想要在响应主体中接收的内容类型。服务器会响应 Content-Type,这可能与你的 Accept 不同。 - Sebastian Sipos

294

PHP 中:

curl_setopt($ch, CURLOPT_HTTPHEADER, array('HeaderName:HeaderValue'));

或者你可以设置多个:

curl_setopt($ch, CURLOPT_HTTPHEADER, array('HeaderName:HeaderValue', 'HeaderName2:HeaderValue2'));

1
@James 在某些情况下它可以正常工作,但在其他情况下CURL会发送一个额外的头部"Expect: 100-continue" - 你有什么办法可以去掉它吗? - coding_idiot
1
@coding_idiot:你可以在头部值的数组中传递"Expect:"来禁用它。例如:curl_setopt($ch,CURLOPT_HTTPHEADER,array('HeaderName: HeaderValue', 'Expect:')); - ether
19
OP并没有提到PHP。 - hanshenrik
标题名称使用下划线大写,并以HTTP_为前缀。例如,“protection-token”变成“HTTP_PROTECTION_TOKEN”。 - Bimal Poudel
1
@hanshenrik 没错,但 OP 也没有提到关于命令行的任何内容。实际上,该问题应该因为不清楚而被暂停。今天,新手是不可能逃过如此马虎的提问。 - user12635841

63

10
-H选项可在命令提示符中使用,例如:curl -H "pwd:123" http://localhost/test.php。它用于向HTTP请求添加自定义标头,这里的示例是将“pwd”标头与值“123”一起发送到http://localhost/test.php上。 - shasi kanth
谢谢。简短、简洁并附有文档链接。然而,该链接已经过时,新链接为https://curl.haxx.se/docs/manpage.html#-H。 - Oleksii Kyslytsyn

50

获取(多个参数):

curl -X  GET "http://localhost:3000/action?result1=gh&result2=ghk"
或者。
curl --request  GET "http://localhost:3000/action?result1=gh&result2=ghk"
或者
curl  "http://localhost:3000/action?result1=gh&result2=ghk"
或者
curl -i -H "Application/json" -H "Content-type: application/json"  "http://localhost:3000/action?result1=gh&result2=ghk"

1
谢谢。我没有意识到这种URL需要使用必须的引号。 - remat_br

28

我使用Postman。

执行您想要进行的任何调用。然后,postman提供了一个方便的工具来显示curl代码。

在终端中运行它。 输入图像描述

输入图像描述


1
这是一个加速事情的好方法,但如果您在Windows上使用shell脚本,则要小心转义单引号或双引号,因为shell脚本有自己的格式要求。 - Thierrydev
1
尽管Postman是一个好工具,但当你没有像在Kubernetes pods这样的图形环境时,它就没有用了。学会使用Curl,你就可以随时测试REST。 - Namphibian

28

你也可以像这样在单个Curl调用中发送多个标头、数据(例如JSON),并指定调用方法(POST、GET):

curl -X POST(Get or whatever) \
  http://your_url.com/api/endpoint \
  -H 'Content-Type: application/json' \
  -H 'header-element1: header-data1' \
  -H 'header-element2: header-data2' \

......更多标题................

  -d '{
  "JsonExArray": [
    {
      "json_prop": "1",
    },
    {
      "json_prop": "2",
    }
  ]
}'

1
我认为它在bash中使用,而不是在cmd中。我是正确的吗?请告诉我,先生。 - Gray Programmerz
是的,那就是Bash。 - Gray Programmerz

10

我已经从curl转为 Httpie ;其语法如下:

http http://myurl HeaderName:value

7

如果您想发送自定义头部,可以按照以下方式进行:

curl -v -H @{'custom_header'='custom_header_value'} http://localhost:3000/action?result1=gh&result2=ghk

这不是试图从名为{'custom_header'='custom_header_value'}的文件中读取头信息吗? - Robin A. Meade

6
在 Windows 系统中的 Anaconda 环境下,应使用以下命令: GET,例如:
curl.exe http://127.0.0.1:5000/books 

发布或更新数据,例如:

curl.exe http://127.0.0.1:5000/books/8 -X PATCH -H "Content-Type: application/json" -d '{\"rating\":\"2\"}' 

提示: 为json数据添加反斜杠来避免此类型错误 => Failed to decode JSON object: Expecting value: line 1 column 1 (char 0)

并且仅使用curl.exe而不是curl来避免此问题:

Invoke-WebRequest : Cannot bind parameter 'Headers'. Cannot convert the "Content-Type: application/json" value of type
"System.String" to type "System.Collections.IDictionary".
At line:1 char:48
+ ... 0.1:5000/books/8 -X PATCH -H "Content-Type: application/json" -d '{\" ...
+                                  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
    + CategoryInfo          : InvalidArgument: (:) [Invoke-WebRequest], ParameterBindingException
    + FullyQualifiedErrorId : CannotConvertArgumentNoMessage,Microsoft.PowerShell.Commands.InvokeWebRequestCommand

这几乎与最初发布的问题无关。 - MarkHu
@MarkHu 它回应的是问题标题,而不是问题正文 :). 有许多类似于问题标题的问题,所以他们会利用我的答案,我也是其中之一,所以一旦我找到答案就分享了它。 - DINA TAKLIT
这是PowerShell的Curl函数,而不是curl.exe。 - Garric

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接