Base64 解码在编码以 + 开头时会出现错误。

3
每次我使用Base64编码字符串时,如果添加了一个+号,解码将因为字符串长度无效而失败。如果编码没有前导+,那么解码就可以正常进行。请问有人能解释这是为什么吗?是什么原因导致某些情况下会生成+符号?以下是一个示例,这个字符串被编码了但无法解码。
+ueJ0q91t5XOnFYP8Xac3A== 

我正在传递的参数示例在编码之前的格式为123_true或123_false。下划线是否会导致"+"出现随机问题?

2个回答

4
+是常用的base64字符之一,当被编码的6个位的值为62时使用。
我猜你是在URL的查询参数中使用它,其中+是空格的转义值。对于这种情况,您应该使用URL安全的Base64编码
引用如下: 使用标准Base64在URL中需要将“+”、“/”和“=”字符编码为特殊的百分比编码十六进制序列(例如,“+”变为“%2B”,“/”变为“%2F”,“=”变为“%3D”),从而使字符串变得不必要地更长。 出于这个原因,修改过的Base64的URL变体存在,其中标准Base64的“+”和“/”字符分别被替换为“-”和“_”,以便在关系数据库、Web表单和通用对象标识符中使用URL编码器/解码器不再是必需的,并且对编码值的长度没有影响,使得相同的编码形式可以保持不变。某些变体允许或要求省略填充“=”符号,以避免将其与字段分隔符混淆,或要求对任何此类填充进行百分比编码。某些库(例如org.bouncycastle.util.encoders.UrlBase64Encoder)将“=”编码为“.”。
在这里选择的确切路径取决于您是否控制双方-如果是,则使用修改的decodabet可能是最好的计划。否则,您需要仅转义查询参数。
引用如下: 以下示例已编码,但无法解码。 +ueJ0q91t5XOnFYP8Xac3A==
本身并不是真的。
byte[] bytes = Convert.FromBase64String("+ueJ0q91t5XOnFYP8Xac3A==");

运行正常......这暗示了字符串的传播出现了问题,这与我之前说的一致。


编码会生成一个byte[],因此你的加号是在合并一个数组。Base 64期望数组的长度可被8整除,因为Base 64是由8个字节组成的行。 - jdweng
@jdweng:这并不清楚是针对我还是原帖作者,但我认为“+”应该是字符串值的一部分... - Jon Skeet
2
@user1732364:你可以使用WebUtility.UrlEncode或类似的方法。如果你控制编码和解码两端,你可以通过在结果上使用string.Replace来使用替代的解码表。但是,由于你的问题缺少大量上下文,这并没有什么帮助。 - Jon Skeet
@jdweng:这似乎是一个巨大的假设。考虑到我们所知道的,我觉得更有可能加号被用作URL的一部分,并且在接收端被有效地解码为一个空格。除了SQL注入攻击外,让值的一部分突然成为代码的一部分是很奇怪的。 - Jon Skeet
现在正在尝试WebUtility方法..测试结束后会回复。 - user1732364
显示剩余9条评论

2
与PHP解决此问题的方案类似,您可以将+/=替换为安全字符-_,
string safeBase64= base64.Replace('+', '-').Replace('/', '_').Replace('=', ',')

在解码之前,您可以将原始字符替换回来:

string base64 = safeBase64.Replace('-','+').Replace('_','/').Replace(',','=')

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