当我用JSON主体向我的REST服务发出POST请求时,我包括Content-type: application/ JSON;消息头中的Charset =utf-8。如果没有这个报头,我将从服务中得到一个错误。我也可以成功地使用Content-type: application/json而不使用;charset=utf-8部分。

charset=utf-8到底做什么?我知道它指定了字符编码,但没有它服务也能正常工作。这种编码是否限制了可以出现在消息体中的字符?


当前回答

标头仅仅表示内容的编码内容。从内容本身推断内容的类型不一定是可能的,也就是说,你不一定只看内容就知道该怎么做。这就是HTTP报头的作用,它们告诉接收者他们(应该)在处理什么样的内容。

内容类型:application / json;charset=utf-8指定内容为JSON格式,以utf-8字符编码编码。指定编码对于JSON来说有些多余,因为JSON的默认编码(只有?)是UTF-8。因此,在这种情况下,接收服务器显然很高兴知道它正在处理JSON,并假设编码默认为UTF-8,这就是为什么它可以使用或不使用报头。

这种编码是否限制了可以出现在消息体中的字符?

不。你可以在标题和正文中发送任何你想要的东西。但是,如果两者不匹配,你可能会得到错误的结果。如果在报头中指定内容是UTF-8编码的,但实际上发送的是Latin1编码的内容,接收方可能会产生垃圾数据,试图将Latin1编码的数据解释为UTF-8。当然,如果您指定您正在发送Latin1编码的数据,并且您实际上正在这样做,那么是的,您只能在Latin1中编码256个字符。

其他回答

Dart http的实现处理字节多亏了“charset=utf-8”,所以我相信有几个实现支持这一点,以避免从响应中读取字节时的“latin-1”回切字符集。 在我的例子中,我完全丢失了响应体字符串的格式,所以我必须手动对utf8进行字节编码,或者在服务器的API响应上添加头“内部”参数。

我完全同意@欺骗,但我想发展这个“我从服务中得到一个错误”的问题部分,

我们得到这种错误作为http 415

Http 415不支持的媒体类型错误

HTTP 415不支持的媒体类型客户端错误响应代码表示服务器拒绝接受请求,因为负载格式是不支持的格式。

格式问题可能是由于请求指定的Content-Type或Content-Encoding,或者是直接检查数据的结果。

换句话说,这个例子就是这样。

我们必须设置正确的内容类型,我们必须接受正确的内容类型 添加内容类型:application/json和接受:application/json。否则,它将假设默认值

请注意,IETF RFC4627已被IETF RFC7158所取代。在第[8.1]节中,它撤回了@Drew之前引用的文本,说:

实现绝对不能在JSON文本的开头添加字节顺序标记。

为了证实@dece的声明,默认的JSON编码是UTF-8…

来自IETF RFC4627:

JSON文本应以Unicode编码。默认编码为 utf - 8。 因为JSON文本的前两个字符总是ASCII 字符[RFC0020],可以确定一个八字节 流是UTF-8, UTF-16 (BE或LE),或UTF-32 (BE或LE) 前四个八位的空音。 00 00 00 xx UTF-32BE 00 xx 00 xx UTF-16BE xx 00 00 00 UTF-32LE xx 00 xx 00 UTF-16LE xx xx xx xx UTF-8

标头仅仅表示内容的编码内容。从内容本身推断内容的类型不一定是可能的,也就是说,你不一定只看内容就知道该怎么做。这就是HTTP报头的作用,它们告诉接收者他们(应该)在处理什么样的内容。

内容类型:application / json;charset=utf-8指定内容为JSON格式,以utf-8字符编码编码。指定编码对于JSON来说有些多余,因为JSON的默认编码(只有?)是UTF-8。因此,在这种情况下,接收服务器显然很高兴知道它正在处理JSON,并假设编码默认为UTF-8,这就是为什么它可以使用或不使用报头。

这种编码是否限制了可以出现在消息体中的字符?

不。你可以在标题和正文中发送任何你想要的东西。但是,如果两者不匹配,你可能会得到错误的结果。如果在报头中指定内容是UTF-8编码的,但实际上发送的是Latin1编码的内容,接收方可能会产生垃圾数据,试图将Latin1编码的数据解释为UTF-8。当然,如果您指定您正在发送Latin1编码的数据,并且您实际上正在这样做,那么是的,您只能在Latin1中编码256个字符。