为什么 JavaScript 中的非 http(s) URL 不能更改 URL 对象的协议?

Sam*_*eau 1 javascript url

在 JavaScript 中,使用对象时更改给定 URL 的协议似乎存在一些限制URL。但是,我找不到记录此行为的位置(URLURL.prototype.protocol)或为什么要让它这样工作。

\n

有人能解释一下吗?

\n

编辑: JS 运行时的行为似乎不一致。Firefox、Node 和 Deno 都“拒绝”更改协议,但 Chrome、Safari 和 Bun 都“遵守”更改\xe2\x80\xa6

\n

\r\n
\r\n
const url1 = new URL(\'http://example.com\')\nconsole.log(url1.protocol) // http:\nurl1.protocol = \'https:\'\nconsole.log(url1.protocol) // https:\n\nconst url2 = new URL(\'webcal://example.com\')\nconsole.log(url2.protocol) // webcal:\nurl2.protocol = \'https:\'\nconsole.log(url2.protocol) // webcal:, but should be https:
Run Code Online (Sandbox Code Playgroud)\r\n
\r\n
\r\n

\n

Ber*_*rgi 7

Node.js 对此进行了记录:

\n
\n

WHATWG URL 标准认为少数 URL 协议方案在解析和序列化方式方面\n是特殊的。当使用这些特殊协议之一解析 URL 时,属性url.protocol可以更改为其他特殊协议,但不能更改为非特殊协议,反之亦然。

\n

例如,从 更改为http有效https: [\xe2\x80\xa6]

\n

但是,从http假设fish协议更改为\n则不会,因为新协议并不特殊。[\xe2\x80\xa6]

\n

同样,也不允许从非特殊协议更改为特殊协议:[\xe2\x80\xa6]

\n

根据 WHATWG URL 标准,特殊协议方案有\n ftpfilehttphttpswswss

\n
\n

(强调和省略是我的)

\n

您的webcal协议不在该列表中,因此您无法将其更改为https.

\n

区分特殊和非特殊 URL的目的似乎是应该以不同的方式解析它们的主机名,例如需要有效的域名。如果现有 URL 的主机名不满足新协议的要求,那么切换协议就会变得危险。

\n

对于 Node.js,这是由 C++ Ada URL 库实现的。Deno 使用 Rust urlpattern crate。Firefox 已经更改了其实现以符合该规范,Chrome最近也紧随其后,并将随 M118 一起发布。Webkit(Safari、Bun)错误报告仍然开放。

\n

尽管如此,这还是很疯狂,并且2021 年开放了一个规范问题来允许这样做。此限制还可能存在网络兼容性问题,因此他们可能必须调整规范。然而,目前的计划似乎是遵循它,而是添加一个构造函数来URL从零件创建新的。

\n