url - URI 查询中什么是有效的,什么是无效的?

标签 url query-string uri specifications

背景(下面的问题)

我一直在谷歌上来回搜索,阅读 RFC 和 SO 问题,试图解决这个问题,但我仍然没有找到 jack 。

所以我想我们只是投票选出“最佳”答案,仅此而已,或者?

基本上可以归结为这一点。

3.4. Query Component

The query component is a string of information to be interpreted by the resource.

query = *uric

Within a query component, the characters ";", "/", "?", ":", "@", "&", "=", "+", ",", and "$" are reserved.

让我困惑的第一件事是 *uric 是这样定义的

uric = reserved | unreserved | escaped

reserved = ";" | "/" | "?" | ":" | "@" | "&" | "=" | "+" | "$" | ","

然而,诸如此类的段落在一定程度上澄清了这一点

The "reserved" syntax class above refers to those characters that are allowed within a URI, but which may not be allowed within a particular component of the generic URI syntax; they are used as delimiters of the components described in Section 3.

Characters in the "reserved" set are not reserved in all contexts. The set of characters actually reserved within any given URI component is defined by that component. In general, a character is reserved if the semantics of the URI changes if the character is replaced with its escaped US-ASCII encoding.

最后的摘录感觉有些倒退,但它清楚地表明保留字符集取决于上下文。然而 3.4 规定所有保留字符都保留在查询组件中,但是,这里唯一会改变语义的是转义问号 (?),因为 URI 不定义查询字符串的概念。

此时我已经完全放弃了 RFC,但发现 RFC 1738 特别有趣。

An HTTP URL takes the form:

http://<host>:<port>/<path>?<searchpart>

Within the <path> and <searchpart> components, "/", ";", "?" are reserved. The "/" character may be used within HTTP to designate a hierarchical structure.

我至少在 RFC 1738 取代 RFC 2396 的 HTTP URL 方面对此进行解释。因为 URI 查询没有查询字符串的概念,所以保留的解释实际上不允许我定义查询字符串,因为我'我现在已经习惯了。

问题

这一切都是从我想要将数字列表与另一个资源的请求一起传递时开始的。我没有多想,只是将其作为逗号分隔值传递。令我惊讶的是,逗号被转义了。查询page.html?q=1,2,3编码后变成 page.html?q=1%2C2%2C3它有效,但它很丑,没想到它。从那时起我开始查看 RFC。

我的第一个问题很简单,编码逗号真的有必要吗?

我的回答,根据 RFC 2396:是,根据 RFC 1738:否

后来我发现了有关在请求之间传递列表的相关帖子。 csv 方法本来就很糟糕。相反,它出现了(以前没有见过)。

page.html?q=1;q=2;q=3

我的第二个问题,这是一个有效的网址吗?

我的回答,根据 RFC 2396:否,根据 RFC 1738:否(; 被保留)

只要它是数字,我在传递 csv 时不会遇到任何问题,但是,如果其他东西突然需要逗号,您确实会遇到必须来回编码和解码值的风险。无论如何,我尝试了 ASP.NET 的分号查询字符串,但结果不是我所期望的。

Default.aspx?a=1;a=2&b=1&a=3

Request.QueryString["a"] = "1;a=2,3"
Request.QueryString["b"] = "1"

我看不出这与 csv 方法有何显着不同,因为当我要求“a”时,我得到一个带有逗号的字符串。 ASP.NET 当然不是一个引用实现,但它还没有让我失望。

但最重要的是——我的第三个问题——这方面的规范在哪里?您会做什么或不会做什么?

最佳答案

在通用 URL 组件中保留字符并不意味着当它出现在组件中或组件中的数据中时必须对其进行转义。该字符还必须定义为通用或特定于方案的语法中的分隔符,并且字符的出现必须在数据内。

通用 URI 的当前标准是 RFC 3986 ,其中有这样一句话:

2.2. Reserved Characters

URIs include components and subcomponents that are delimited by characters in the "reserved" set. These characters are called "reserved" because they may (or may not) be defined as delimiters by the generic syntax, by each scheme-specific syntax, or by the implementation-specific syntax of a URI's dereferencing algorithm. If data for a URI component would conflict with a reserved character's purpose as a delimiter [emphasis added], then the conflicting data must be percent-encoded before the URI is formed.

   reserved    = gen-delims / sub-delims

gen-delims = ":" / "/" / "?" / "#" / "[" / "]" / "@"

sub-delims = "!" / "$" / "&" / "'" / "(" / ")" / "*" / "+" / "," / ";" / "="

3.3. Path Component

[...]
pchar         = unreserved / pct-encoded / sub-delims / ":" / "@"
[...]

3.4 Query Component

[...]
      query       = *( pchar / "/" / "?" )

因此,查询字符串中明确允许使用逗号,并且仅当特定方案将其定义为分隔符时才需要在数据中转义。 HTTP 方案不使用逗号或分号作为查询字符串中的分隔符,因此不需要对它们进行转义。浏览器是否遵循这个标准是另一回事。

使用 CSV 应该可以很好地处理字符串数据,您只需遵循标准 CSV 约定并引用数据或使用反斜杠转义逗号即可。

对于 RFC 2396,它还允许在 HTTP 查询字符串中使用未转义的逗号:

2.2. Reserved Characters

Many URI include components consisting of or delimited by, certain special characters. These characters are called "reserved", since their usage within the URI component is limited to their reserved purpose. If the data for a URI component would conflict with the reserved purpose, then the conflicting data must be escaped before forming the URI.

由于逗号在 HTTP 方案下没有保留用途,因此不必在数据中对它们进行转义。第 2.3 节中关于保留字符的注释是那些在百分比编码时改变语义的字符,仅适用于一般情况;字符可以进行百分比编码,而不改变特定方案的语义,但仍然保留。

关于url - URI 查询中什么是有效的,什么是无效的?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2366260/

相关文章:

javascript - 获取浏览器中打开的所有URL

ruby - 使用 Ruby 转义和下载 URL

javascript - 如何使用history.pushState将查询字符串变量附加到现有URL?

php - 如何在查询字符串中传递数组?

java - "IllegalArgumentException: !utf8"大多数请求出现 Jetty 错误

java - 在java中获取AppData路径时URI语法错误

javascript - 提取api-如何将数组附加为搜索参数

java - java中获取图像的名称

javascript - 如果 URL 更改,则重定向页面返回

rest - 如果我使用 HTTP 方法 POST 来获取数据是否有效?