如何正确对Swift中的字符串进行urlencode以使用PHP urldecode进行解码?

问题描述 投票:0回答:1

我想将一些 URL 编码数据从 Swift 应用程序发送到 PHP API,在其中数据再次被解码。

虽然这在大多数情况下工作得很好,但我现在意识到 PHP urldecode 处理 + 号的方式与 Swift movingPercentEncoding 不同,并将 + 解码为空格。

如何避免这种情况?

// Swift
let data = "some+test"
let encodedData = data.addingPercentEncoding(withAllowedCharacters: .urlHostAllowed)  // some+test
sendToMyServer(encodedData)

// PHP
$encodedData = $receivedData;             // some+text
$decodedData = urldecode($encodedData);   // some text

看来 Swift 不考虑其任何内置(倒置)字符集中的 + 号:

URLFragmentAllowedCharacterSet  "#%<>[\]^`{|}
URLHostAllowedCharacterSet      "#%/<>?@\^`{|}
URLPasswordAllowedCharacterSet  "#%/:<>?@[\]^`{|}
URLPathAllowedCharacterSet      "#%;<>?[\]^`{|}
URLQueryAllowedCharacterSet     "#%<>[\]^`{|}
URLUserAllowedCharacterSet      "#%/:<>?@[\]^`

PHP 以这种方式处理+号有什么原因吗?

解决这个问题的“正确”方法是什么?我假设我可以简单地定义一个包含+号的自定义字符集,但我不确定这是否会导致其他意外的副作用。这安全吗?PHP urldecode 是否还有其他需要考虑的差异?

php swift urlencode urldecode
1个回答
1
投票

原因:

CharacterSet.urlHostAllowed
的文档:

返回主机 URL 子组件中允许的字符集。

如果我们然后转到

URLComponents

的隐式链接文档

此结构根据 RFC 3986 解析和构造 URL。其行为与符合旧 RFC 的 URL 结构的行为略有不同。但是,您可以根据 URLComponents 值的内容轻松获取 URL 值,反之亦然。

PhP 的文档

urldecode
说:

加号 ('+') 被解码为空格字符。

urlencode
说:

这与 » RFC 3986 编码(请参阅 rawurlencode())不同,因为由于历史原因,空格被编码为加号 (+)。

所以 iOS 使用

RFC 3986
而 PhP 则没有。

解决方案:

通过在 iOS 或服务器上更改它来使用相同的编码/解码。

对于服务器更改:

要在服务器端使用与 iOS 相同的方式,请使用

rawurldecode
(或
rawurlencode
,如果需要),如下所示:

rawurldecode() 不会将加号 ('+') 解码为空格。 urldecode() 可以。

rawurlencode — 根据 RFC 3986 进行 URL 编码

对于 iOS 更改:

参见 Sajjad 的回答

最新问题
© www.soinside.com 2019 - 2025. All rights reserved.