2

我正在用 JavaScript 做一些非常邪恶的事情,我遇到了一个奇怪的问题。

我正在创建填充静态大小的缓冲区的二进制数据。如果内容没有填满缓冲区,则剩余部分用空字符填充。

下一步是转换为base64。

大小(字节)并不总是 3 的倍数,所以我可能需要在末尾添加填充。缓冲区中的最后一个字节总是空的(实际上,它大约是一 kb 的空值)。

当我在 Firefox 和 Chrome 上将其转换为 base64 时,ERR_INVALID_URL当我有一个尾随的“=”时会得到一个,但当我没有时它下载得很好。

例如:

var url = "data:application/octet-stream;base64,";

window.open(url + "AAAA"); // works
window.open(url + "AAAA="); // doesn't work
window.open(url + "icw="); // works

我的文件有效,但不符合规范。

这是无效的base64有什么原因吗?更重要的是,这是一个错误还是规范的一部分?

编辑:

我发布了一个答案,给出了 Firefox 和 Chrome 之间的一些奇怪之处。有谁知道标准规定了什么?或者它是那些导致碎片化的松散规范之一?如果可能的话,我想要一些确定的东西。

4

3 回答 3

5

填充字符=用于填充最多四个代码字符的倍数。由于每三个字节的输入映射到四个字节的输出,所以不是三的倍数的输入字节数需要填充(一个字节==的余数需要,两个字节的余数需要=)。

在您的情况下,AAAA已经是一个有效的代码字并且不需要填充。

于 2011-06-04T17:20:38.717 回答
2

为什么你会想象在字符串末尾添加一个“=”字符会起作用?这不是 base64 中的有效字符。

字符集为大小写字母;数字;和“+”和“/”。因此,其他任何内容在 base64 字符串中均无效。

编辑- 对于 URL,似乎使用“-”和“_”而不是“+”和“/”(对于字符集中的位置 62 和 63)。

再编辑一些——这是一个非常令人困惑的话题,因为存在不同的、表面上权威但相互矛盾的信息来源。例如,数据 URL 方案的 Mozilla 描述没有提到使用“文件名友好”替代编码。IETF 数据 url RFC 也是如此。但是,其他 IETF 文档清楚地讨论并指定了用“-”和“_”替换有问题的(对于文件名)“+”和“/”的变体。

因此,我宣布自己无知:-) Gumbo 可能是对的,您收到的抱怨是关于不正确的填充(即,实际上不需要填充时的填充)。

于 2011-06-04T17:12:43.857 回答
2

关于不同浏览器的注意事项:

  • 铬合金
    • datalength % 4 === 1- 一个等于是必要的
    • datalength % 4 === 2- 两个相等是必要的
  • Firefox - 等号是可选的,但遵循与 Chrome 相同的约定

这是我用来测试它的行(我每次都用不同的字符串替换 AAAAAA==):

var url = "data:application/octet-stream;base64,AAAAAA=="; window.open(url);

此外,Firefox 和 Chrome 都使用+& /,而不是-and _

来源:

我在 Ubuntu 11.04 上使用 Chrome 11 和 Firefox 4 进行的测试。

编辑:

我需要的代码是Javascript 的 tar 实用程序。我的代码按原样工作,但我希望尽可能符合标准,而且我认为缺少一个字节。没什么大不了的,因为 Linux 中的 tar 可以识别它。

于 2011-06-04T17:50:00.117 回答