优化 WebSocket 实现单例连接用于打印【待测试 】

class PrinterWebSocket {

constructor(url) {

if (PrinterWebSocket.instance) {

return PrinterWebSocket.instance;

}

this.url = url;

this.socket = null;

this.queue = []; // 打印任务队列

this.isConnecting = false;

this.retryCount = 0;

this.maxRetry = 3;

PrinterWebSocket.instance = this;

this.connect();

}

connect() {

if (this.isConnecting || this.socket) return;

this.isConnecting = true;

this.socket = new WebSocket(this.url);

this.socket.onopen = () => {

console.log('WebSocket连接已建立');

this.isConnecting = false;

this.retryCount = 0;

this.processQueue();

};

this.socket.onmessage = (event) => {

console.log('收到打印响应:', event.data);

// 处理打印响应

};

this.socket.onclose = () => {

console.log('WebSocket连接关闭');

this.socket = null;

if (this.retryCount < this.maxRetry) {

this.retryCount++;

setTimeout(() => this.connect(), 1000 * this.retryCount);

}

};

this.socket.onerror = (error) => {

console.error('WebSocket错误:', error);

this.socket = null;

this.isConnecting = false;

};

}

print(data) {

if (!this.socket || this.socket.readyState !== WebSocket.OPEN) {

console.log('连接未就绪,加入打印队列');

this.queue.push(data);

if (!this.isConnecting) {

this.connect();

}

return;

}

try {

this.socket.send(JSON.stringify(data));

console.log('打印指令已发送');

} catch (error) {

console.error('发送打印指令失败:', error);

this.queue.push(data);

this.socket = null;

this.connect();

}

}

processQueue() {

while (this.queue.length > 0 && this.socket?.readyState === WebSocket.OPEN) {

const data = this.queue.shift();

this.socket.send(JSON.stringify(data));

}

}

static getInstance(url) {

if (!PrinterWebSocket.instance) {

PrinterWebSocket.instance = new PrinterWebSocket(url);

}

return PrinterWebSocket.instance;

}

}

使用方法:

// 初始化单例(通常在应用启动时)

const printer = PrinterWebSocket.getInstance('ws://your-print-server/ws');

// 打印时直接使用

function handlePrint() {

const printData = {

type: 'print',

content: '要打印的内容',

copies: 1

};

printer.print(printData);

}

// 页面按钮点击事件

document.getElementById('print-btn').addEventListener('click', handlePrint);

优化建议

  1. 心跳机制:添加心跳保持连接活跃
复制代码
// 在构造函数中添加
this.heartbeatInterval = setInterval(() => {
  if (this.socket?.readyState === WebSocket.OPEN) {
    this.socket.send(JSON.stringify({ type: 'heartbeat' }));
  }
}, 30000);
  1. 连接状态通知:提供连接状态变更回调
复制代码
// 添加状态监听
this.onStatusChange = null;

// 状态变更时
const notifyStatus = (status) => {
  if (this.onStatusChange) {
    this.onStatusChange(status);
  }
};

// 在onopen/onclose/onerror中调用notifyStatus
  1. 打印结果回调:支持打印结果返回
复制代码
print(data, callback) {
  const task = { data, callback };
  this.queue.push(task);
  // ...其余逻辑
}

// 在onmessage中处理响应时调用callback

这种实现方式避免了每次打印都创建新连接,提高了效率并减少了服务器压力,同时保证了打印任务的可靠性。

相关推荐
二狗mao2 小时前
Uniapp使用websocket进行ai回答的流式输出
websocket·网络协议·uni-app
7***u2163 小时前
显卡(Graphics Processing Unit,GPU)架构详细解读
大数据·网络·架构
河北瑾航科技5 小时前
广西水资源遥测终端 广西水利遥测终端 广西用水监测遥测终端 河北瑾航科技遥测终端机HBJH-B01说明书
网络·科技·水文遥测终端机·遥测终端机·广西水资源遥测终端机·广西水利遥测终端·广西用水终端
羑悻的小杀马特6 小时前
轻量跨云·掌控无界:Portainer CE + cpolar 让远程容器运维像点外卖一样简单——免复杂配置,安全直达对应集群
运维·网络·安全·docker·cpolar
愚戏师7 小时前
Python3 Socket 网络编程复习笔记
网络·笔记
降临-max7 小时前
JavaSE---网络编程
java·开发语言·网络·笔记·学习
156082072197 小时前
基于7VX690T FPGA实现万兆TCP/IP资源和性能测试
网络协议·tcp/ip·fpga开发
赖small强8 小时前
【Linux 网络基础】libwebsockets HTTPS 服务端实现机制详解
linux·网络·https·tls·libwebsockets
大白的编程日记.8 小时前
【计算网络学习笔记】MySql的多版本控制MVCC和Read View
网络·笔记·学习·mysql
踏浪无痕10 小时前
线上偶发 502 排查:用 Netty 成功复现 KeepAlive 时间窗口案例实战(附完整源码)
运维·网络协议