1 Star 0 Fork 0

陈迅/node-study

加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
文件
该仓库未声明开源许可证文件(LICENSE),使用请关注具体项目描述及其代码上游依赖。
克隆/下载
myTransform.js 2.30 KB
一键复制 编辑 原始数据 按行查看 历史
// 数据的封包与拆包来解决数据的粘包问题
// 长度编码的传输方式:定长的消息头(header): 序列号和消息长度, 不定长的消息体(body)
// 客户端传入的是数字或字符串,封装成二进制数据包传递。另一端按规则拆解数据,获取指定长度取出相应的数据,转为字符串
// Buffer数据读写 writeInt16BE: 将value从指定位置写入
// 另外还有32BE的 readInt16BE: 从指定位置开始读取数据
class MyTransformCode {
constructor() {
this.packageHeaderLen = 4 // header总长度
this.serialNum = 0 // 序列号
this.serialLen = 2 // 序列号长度
}
// 编码
encode(data, serialNum) { // 数据,编号
const body = Buffer.from(data) // 把data变为二进制的数据
// 01 先按照指定的长度来申请一片内存空间做为 header 来使用
const headerBuf = Buffer.alloc(this.packageHeaderLen)
// 02
headerBuf.writeInt16BE(serialNum || this.serialNum) // 写入序列号,👇写入消息长度
headerBuf.writeInt16BE(body.length, this.serialLen) // 跳过之前写入继续写入,将数据长度做为消息长度
if (serialNum === undefined) {
this.serialNum++
}
return Buffer.concat([headerBuf, body])
}
// 解码
decode(buffer) {
const headerBuf = buffer.slice(0, this.packageHeaderLen)
const bodyBuf = buffer.slice(this.packageHeaderLen)
return {
serialNum: headerBuf.readInt16BE(),
bodyLength: headerBuf.readInt16BE(this.serialLen), // 跳过序列号长度读取
body: bodyBuf.toString()
}
}
// 获取包长度的方法
getPackageLen(buffer) {
if (buffer.length < this.packageHeaderLen) {
return 0
} else {
// 包里面还有数据可取
return this.packageHeaderLen + buffer.readInt16BE(this.serialLen) // header总长度 + 消息长度
}
}
}
module.exports = MyTransformCode
const ts = new MyTransformCode()
let str = '测试数据' // 12
let encodeBuf = ts.encode(str,1) // <Buffer 00 01 00 0c e6 b5 8b e8 af 95 e6 95 b0 e6 8d ae>
let a = ts.decode(encodeBuf) // { serialNum: 1, bodyLength: 12, body: '测试数据' }
let len = ts.getPackageLen(encodeBuf) // 16
马建仓 AI 助手
尝试更多
代码解读
代码找茬
代码优化
1
https://gitee.com/chenxun98/node-study.git
git@gitee.com:chenxun98/node-study.git
chenxun98
node-study
node-study
master

搜索帮助