JS的base64编码解码
2024-10-16 23:04:28
Unicode问题解法
有个小坑是它只支持ASCII. 如果你调用btoa("中文")
会报错:
Uncaught DOMException: Failed to execute 'btoa' on 'Window': The string to be encoded contains characters outside of the Latin1 range.
浏览器中DOMString是UTF-16编码. 如果输入字符串中包含超过8位(0x00~0xFF)的字符, 就会报这个错误.
思路一
对整个字符串进行转义(如使用encodeURIComponent
进行UTF-8转义)然后再btoa
编码.
let Base64 = {
encode(str) {
// first we use encodeURIComponent to get percent-encoded UTF-8,
// then we convert the percent encodings into raw bytes which
// can be fed into btoa.
return btoa(encodeURIComponent(str).replace(/%([-9A-F]{})/g,
function toSolidBytes(match, p1) {
return String.fromCharCode('0x' + p1);
}));
},
decode(str) {
// Going backwards: from bytestream, to percent-encoding, to original string.
return decodeURIComponent(atob(str).split('').map(function (c) {
return '%' + ('' + c.charCodeAt().toString()).slice(-);
}).join(''));
}
}; let encoded = Base64.encode("哈ha"); // "5ZOIaGE="
let decoded = Base64.decode(encoded); // "哈ha"
思路二
将UTF-16的DOMString
转化成UTF-8的字节数组然后编码.
MDN上此思路的解法用了很多库, 就不推荐了.
网上找到了下面这段代码, 思路是一样的, 但是是直接裸写的转换代码.
/**
*
* Base64 encode / decode
* http://www.webtoolkit.info
*
**/
var Base64 = { // private property
_keyStr: "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=" // public method for encoding
, encode: function (input)
{
var output = "";
var chr1, chr2, chr3, enc1, enc2, enc3, enc4;
var i = ; input = Base64._utf8_encode(input); while (i < input.length)
{
chr1 = input.charCodeAt(i++);
chr2 = input.charCodeAt(i++);
chr3 = input.charCodeAt(i++); enc1 = chr1 >> ;
enc2 = ((chr1 & ) << ) | (chr2 >> );
enc3 = ((chr2 & ) << ) | (chr3 >> );
enc4 = chr3 & ; if (isNaN(chr2))
{
enc3 = enc4 = ;
}
else if (isNaN(chr3))
{
enc4 = ;
} output = output +
this._keyStr.charAt(enc1) + this._keyStr.charAt(enc2) +
this._keyStr.charAt(enc3) + this._keyStr.charAt(enc4);
} // Whend return output;
} // End Function encode // public method for decoding
,decode: function (input)
{
var output = "";
var chr1, chr2, chr3;
var enc1, enc2, enc3, enc4;
var i = ; input = input.replace(/[^A-Za-z0-\+\/\=]/g, "");
while (i < input.length)
{
enc1 = this._keyStr.indexOf(input.charAt(i++));
enc2 = this._keyStr.indexOf(input.charAt(i++));
enc3 = this._keyStr.indexOf(input.charAt(i++));
enc4 = this._keyStr.indexOf(input.charAt(i++)); chr1 = (enc1 << ) | (enc2 >> );
chr2 = ((enc2 & ) << ) | (enc3 >> );
chr3 = ((enc3 & ) << ) | enc4; output = output + String.fromCharCode(chr1); if (enc3 != )
{
output = output + String.fromCharCode(chr2);
} if (enc4 != )
{
output = output + String.fromCharCode(chr3);
} } // Whend output = Base64._utf8_decode(output); return output;
} // End Function decode // private method for UTF-8 encoding
,_utf8_encode: function (string)
{
var utftext = "";
string = string.replace(/\r\n/g, "\n"); for (var n = ; n < string.length; n++)
{
var c = string.charCodeAt(n); if (c < )
{
utftext += String.fromCharCode(c);
}
else if ((c > ) && (c < ))
{
utftext += String.fromCharCode((c >> ) | );
utftext += String.fromCharCode((c & ) | );
}
else
{
utftext += String.fromCharCode((c >> ) | );
utftext += String.fromCharCode(((c >> ) & ) | );
utftext += String.fromCharCode((c & ) | );
} } // Next n return utftext;
} // End Function _utf8_encode // private method for UTF-8 decoding
,_utf8_decode: function (utftext)
{
var string = "";
var i = ;
var c, c1, c2, c3;
c = c1 = c2 = ; while (i < utftext.length)
{
c = utftext.charCodeAt(i); if (c < )
{
string += String.fromCharCode(c);
i++;
}
else if ((c > ) && (c < ))
{
c2 = utftext.charCodeAt(i + );
string += String.fromCharCode(((c & ) << ) | (c2 & ));
i += ;
}
else
{
c2 = utftext.charCodeAt(i + );
c3 = utftext.charCodeAt(i + );
string += String.fromCharCode(((c & ) << ) | ((c2 & ) << ) | (c3 & ));
i += ;
} } // Whend return string;
} // End Function _utf8_decode }
最新文章
- 完整成功配置wamp server小记
- iOS 中的第三方库管理工具
- 转】从源代码剖析Mahout推荐引擎
- Lotus 迁移到Exchange POC 之安装Exchange 2010!
- iframe父子窗口取值
- MM32Flash读写操作(兼容STM32)
- Emacs颜色设置
- HNCU1330:算法3-1:八进制数
- sql 检查执行时间
- Oracle角色,权限,表空间基础语句
- EOS account 中的 Threshold 和 weight 使用
- Linux交叉工具链安装
- 关于U3D图片的压缩格式
- oracle启动过程
- 转!!git如何撤销上一次commit(或已push)
- (转载)Ubuntu 16.04+1080Ti机器学习基本环境配置
- Shiro实战教程(一)
- Python字符与ASCII码转换
- javascript总结28 :匿名函数
- Memcached set 命令
热门文章
- freebsd缓存包与仓库版本不一致
- prometheus学习系列十一: Prometheus pushgateway的使用
- springboot 集成百度的唯一ID生成器
- (05节)快速搭建SSM项目
- win7 创建vhd提示“找不到指定文件的虚拟磁盘支持提供程序”解决方法
- 关于__int 128 的读入与输出
- spring Boot + MyBatis + Maven 项目,日志开启打印 sql
- 运行 npm run lint -- --fix,提示:error Use the global form of &#39;use strict&#39;
- Weltanschauung--世界观是人类知觉的基础架构
- k-mean