基于SM4的文件加密解密功能实现(ECB模式)
先上一下效果
前置准备:有一个演示.txt文件,我提前下载到了手机上,里面的内容是“测试内容,今天天气很好”。
进入“文件加密”页面,选择文件后,显示文件内容,输入密钥后,点击加密,显示加密后内容,并可以保存到文件里
进入“文件解密”页面,选择文件后,显示加密后的文件内容,输入密钥,点击解密,显示解密后内容,并可以保存到文件里
两个页面的截图如下:
相关技术实现思路如下:
一、SM4加密解密
大部分的代码官网都有,我这里先介绍一下我的开发中踩坑的记录
如果看官方文档里的代码,你会发现,他对于加密解密的演示,是直接把加密后的结果,扔给解密的代码的。
如果直接拿来用的话,问题是……encryptText,他不是一个string,而是cryptoFramework.DataBlob
如果要把这个解密后的内容,显示给用户看的话,看文档的意思就是encryptText.data.toString(),所以我就通过encryptText.data.toString()获取了加密后的文字内容,并保存到了文件里。
但是解密的时候,我按照文档里的代码,输入这个解密后的文字内容,但是提示错误,是doFinal()这一步的报错,但是我在文档里都看不到具体这个报错对应的错误原因是什么……
后来在开发群里,有幸得到了大佬的指点
大佬的原话如下: “你输出的是hex 那么 在入参的时候也需要将hex转换成unit8Array 类型要匹配”
“不能输出的是hex 解密的时候又传入了base64但是还用hex格式解”
然后再回头自己的代码
我是把加密后的数据,直接转成了string输出并保存,然后再把这个string进行解密。但是对于这个string,我并没有去指定具体是什么格式的,是utf-8,还是啥,都没有指定。
在大佬的指点下,我把代码进行了修改
整体的逻辑是:
输入要加密的文字内容 + 密钥(密钥的处理直接用示例代码里的即可)
把输出的加密内容,转成hex格式,但是hex格式用户看不了(是乱码),所以hex再转成base64输出,并保存到文件里
解密的时候,先把base64解码后以string格式输出,然后再把这个string转成hex格式以后进行解密
这样一来,加密的时候,实际输出的是hex(只不过为了方便用户看进行了base64编码),输入到解密里的时候,也是hex(从base64转到hex),输入和输出的格式一致,解密成功
加密解密的代码如下:
// 加密消息。
export async function encryptMessagePromise(symKey: string, message: string) {
let Key = await genSymKeyByData(new Uint8Array(buffer.from(symKey, 'utf-8').buffer));
let plainText: cryptoFramework.DataBlob = { data: new Uint8Array(buffer.from(message, 'utf-8').buffer) };
let cipher = cryptoFramework.createCipher('SM4_128|ECB|PKCS7');
await cipher.init(cryptoFramework.CryptoMode.ENCRYPT_MODE, Key, null);
let encryptData = await cipher.doFinal(plainText);
let a1 = buffer.from(encryptData.data).toString('hex');
let a2 = buffer.from(a1).toString("base64");
return a2;
}
// 解密消息。
export async function decryptMessagePromise(symKey: string, message: string) {
let Key = await genSymKeyByData(new Uint8Array(buffer.from(symKey, 'utf-8').buffer));
let base64 = new util.Base64Helper();
let textDecoder: util.TextDecoder = util.TextDecoder.create();
let result: string = textDecoder.decodeToString(base64.decodeSync(message),{stream:true});
let cipherText: cryptoFramework.DataBlob = { data: new Uint8Array(buffer.from(result, 'hex').buffer) };
let decoder = cryptoFramework.createCipher('SM4_128|ECB|PKCS7');
await decoder.init(cryptoFramework.CryptoMode.DECRYPT_MODE, Key, null);
let decryptData = await decoder.doFinal(cipherText);
let a1 = buffer.from(decryptData.data).toString('utf-8');
return a1;
}
- 0回答
- 0粉丝
- 0关注
- 开发者工具箱-鸿蒙AES加密解密开发笔记
- 基于文本方式读取文件
- 第五四课:基于HarmonyOS Next的智能办公应用开发:功能实现与案例解析
- OpenHarmony 设计模式-单例模式
- 鸿蒙版Flutter实现发送短信的功能
- 实现文件内容数据同步
- (四五)HarmonyOS Design 的设计模式应用
- OpenHarmony: 如何实现跨模块的页面跳转功能
- 如何实现跨文件组件复用
- (十三)ArkTS 开发中的设计模式应用
- Flutter加密货币应用
- 应用中的“复制功能”如何实现##HarmonyOS应用开发##
- 浅谈 发布-订阅模式
- 96.HarmonyOS NEXT工具类设计模式教程:最佳实践与实现
- 如何实现防截屏功能