如何将 Base64URL 转换为 Base64
- 把 Base64URL 粘贴到 输入 · Base64URL。填充可有可无,输入中出现标准的
+和/也没问题。 - 标准 Base64 显示在 输出 · Base64 中,
-和_已换成+和/,填充也已补全。 - 输出下方的 填充(=) 默认开启;换行 可以把结果按 64 个字符(PEM)或 76 个字符(MIME)断行。
- 点击 复制输出。切换为 Base64 → Base64URL,或使用 Base64 转 Base64URL,即可反向转换。
需要补多少填充
Base64 以 4 个字符为一组。Base64URL 通常会省略用来填满最后一组的 =,所以根据长度就能知道要补回几个:
| 长度 mod 4 | 需要补的填充 | 示例 |
|---|---|---|
| 0 | 无 | eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9(36 个字符) |
| 2 | == | PDw_Pz8-Pg(10)变为 PDw/Pz8+Pg== |
| 3 | = | eyJyb2xlIjoiYWRtaW4-In0(23)变为 eyJyb2xlIjoiYWRtaW4+In0= |
| 1 | 无效 | 剩下的单个字符装不下一个完整字节 |
常见的示例载荷 eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ 有 70 个字符,余数为 2,所以结果就是在同一字符串末尾加上 ==。完整的推导见 填充指南。
为什么可能需要标准 Base64
很多解码器只接受标准字母表,遇到 Base64URL 时的失败方式各不相同:
- GNU coreutils 的
base64 -d会输出第一个-或_之前已解码的内容,然后报base64: invalid input。 - Java 的
Base64.getDecoder()会抛出IllegalArgumentException;处理 URL 安全输入要用Base64.getUrlDecoder()。 - .NET 的
Convert.FromBase64String遇到-、_或缺少=时会抛出FormatException。 - Python 的
base64.b64decode最危险:默认情况下,它会丢弃标准字母表以外的字符而不报错。b64decode("PDw_Pz8-Pg==")返回的是b'<<\x0f\xcf\xc3\xe0',而不是b'<<???>>'。
最后这种情况值得在所有处理令牌的代码中专门测试。字节错了却没有异常,问题往往要很久以后才会暴露,表现为签名校验失败或数据损坏。
在代码中将 Base64URL 转为 Base64
import base64
def b64url_to_bytes(s: str) -> bytes:
return base64.urlsafe_b64decode(s + "=" * (-len(s) % 4))
b64url_to_bytes("PDw_Pz8-Pg") # b'<<???>>'
base64.b64encode(b64url_to_bytes("PDw_Pz8-Pg")).decode() # 'PDw/Pz8+Pg=='
-len(s) % 4 就是缺少的 = 个数:对有效输入来说是 0、1 或 2。urlsafe_b64decode 需要填充,所以要在调用之前补上。
function b64urlToB64(s) {
const b = s.replace(/-/g, "+").replace(/_/g, "/");
return b + "=".repeat((4 - (b.length % 4)) % 4);
}
b64urlToB64("PDw_Pz8-Pg"); // 'PDw/Pz8+Pg=='
在 Node.js 中,Buffer.from(s, "base64url").toString("base64") 一次调用就能完成同样的转换。各语言标准库中的 URL 安全解码器,请参阅 Python、Java 和 C# 页面。
常见问题
- “最后一组字符不完整”。 长度除以 4 余 1。字符串的一部分丢失了,常见于换行处,或者 URL 被截断。
- 输入中有
.。 JWT 用点号连接三个 Base64URL 片段。请一次转换一个片段;JWT 解码器 则可以直接读取整个令牌。 - 字符串中有
%3D。 该值在 Base64URL 之外还做了百分号编码。请先用 URL 解码 处理。
常见问题
怎么给 Base64URL 补回填充?
在末尾用 = 补足到 4 的倍数个字符:余 2 补两个,余 3 补一个。有效数据不可能余 1。这个转换器会自动帮你完成。
为什么 base64 -d 解不了 JWT?
GNU 的 base64 -d 只认识标准字母表,遇到第一个 - 或 _ 就会以 invalid input 停止。请先在这里转换该片段,或者使用能读取 URL 安全字母表的 basenc --base64url -d。
字符串多了一个字符怎么办?
长度除以 4 余 1 的 Base64URL 字符串要么被截断了,要么多了一个字符。转换器会报告最后一组不完整;请检查这个值是怎么复制的。
读取 JWT 需要先转成标准 Base64 吗?
在本站不需要:JWT 解码器 和 Base64URL 解码器 可以直接读取 Base64URL。只有当其他工具或库只接受标准形式时,才需要转换。