完成AI问答模块
This commit is contained in:
176
src/utils/websocket.ts
Normal file
176
src/utils/websocket.ts
Normal file
@@ -0,0 +1,176 @@
|
||||
/**
|
||||
* WebSocket连接管理类
|
||||
*/
|
||||
export class WebSocketManager {
|
||||
private ws: WebSocket | null = null;
|
||||
private url: string;
|
||||
private reconnectAttempts = 0;
|
||||
private maxReconnectAttempts = 5;
|
||||
private reconnectInterval = 3000;
|
||||
private heartbeatInterval: NodeJS.Timeout | null = null;
|
||||
private heartbeatTimer = 30000; // 30秒心跳
|
||||
|
||||
// 事件回调
|
||||
private onMessageCallback?: (data: any) => void;
|
||||
private onOpenCallback?: () => void;
|
||||
private onCloseCallback?: () => void;
|
||||
private onErrorCallback?: (error: Event) => void;
|
||||
|
||||
constructor(url: string) {
|
||||
this.url = url;
|
||||
}
|
||||
|
||||
/**
|
||||
* 连接WebSocket
|
||||
*/
|
||||
connect(): Promise<void> {
|
||||
return new Promise((resolve, reject) => {
|
||||
try {
|
||||
this.ws = new WebSocket(this.url);
|
||||
|
||||
this.ws.onopen = () => {
|
||||
console.log('WebSocket连接成功');
|
||||
this.reconnectAttempts = 0;
|
||||
this.startHeartbeat();
|
||||
this.onOpenCallback?.();
|
||||
resolve();
|
||||
};
|
||||
|
||||
this.ws.onmessage = (event) => {
|
||||
console.log(event,'event>>>')
|
||||
try {
|
||||
const data = JSON.parse(event.data);
|
||||
this.onMessageCallback?.(data);
|
||||
} catch (error) {
|
||||
console.error('解析WebSocket消息失败:', error);
|
||||
}
|
||||
};
|
||||
|
||||
this.ws.onclose = () => {
|
||||
console.log('WebSocket连接关闭');
|
||||
this.stopHeartbeat();
|
||||
this.onCloseCallback?.();
|
||||
this.handleReconnect();
|
||||
};
|
||||
|
||||
this.ws.onerror = (error) => {
|
||||
console.error('WebSocket连接错误:', error);
|
||||
this.onErrorCallback?.(error);
|
||||
reject(error);
|
||||
};
|
||||
} catch (error) {
|
||||
reject(error);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* 发送消息
|
||||
*/
|
||||
send(message: any): void {
|
||||
if (this.ws && this.ws.readyState === WebSocket.OPEN) {
|
||||
this.ws.send(typeof message === 'string' ? message : JSON.stringify(message));
|
||||
} else {
|
||||
console.warn('WebSocket未连接,无法发送消息');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 关闭连接
|
||||
*/
|
||||
close(): void {
|
||||
this.stopHeartbeat();
|
||||
if (this.ws) {
|
||||
this.ws.close();
|
||||
this.ws = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 重连处理
|
||||
*/
|
||||
private handleReconnect(): void {
|
||||
if (this.reconnectAttempts < this.maxReconnectAttempts) {
|
||||
this.reconnectAttempts++;
|
||||
console.log(`尝试重连WebSocket (${this.reconnectAttempts}/${this.maxReconnectAttempts})`);
|
||||
|
||||
setTimeout(() => {
|
||||
this.connect().catch(error => {
|
||||
console.error('重连失败:', error);
|
||||
});
|
||||
}, this.reconnectInterval);
|
||||
} else {
|
||||
console.error('WebSocket重连次数已达上限');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 开始心跳
|
||||
*/
|
||||
private startHeartbeat(): void {
|
||||
this.heartbeatInterval = setInterval(() => {
|
||||
if (this.ws && this.ws.readyState === WebSocket.OPEN) {
|
||||
this.ws.send(JSON.stringify({ type: 'ping' }));
|
||||
}
|
||||
}, this.heartbeatTimer);
|
||||
}
|
||||
|
||||
/**
|
||||
* 停止心跳
|
||||
*/
|
||||
private stopHeartbeat(): void {
|
||||
if (this.heartbeatInterval) {
|
||||
clearInterval(this.heartbeatInterval);
|
||||
this.heartbeatInterval = null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置消息回调
|
||||
*/
|
||||
onMessage(callback: (data: any) => void): void {
|
||||
this.onMessageCallback = callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置连接成功回调
|
||||
*/
|
||||
onOpen(callback: () => void): void {
|
||||
this.onOpenCallback = callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置连接关闭回调
|
||||
*/
|
||||
onClose(callback: () => void): void {
|
||||
this.onCloseCallback = callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置错误回调
|
||||
*/
|
||||
onError(callback: (error: Event) => void): void {
|
||||
this.onErrorCallback = callback;
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取连接状态
|
||||
*/
|
||||
getReadyState(): number {
|
||||
return this.ws?.readyState ?? WebSocket.CLOSED;
|
||||
}
|
||||
|
||||
/**
|
||||
* 是否已连接
|
||||
*/
|
||||
isConnected(): boolean {
|
||||
return this.ws?.readyState === WebSocket.OPEN;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 创建WebSocket连接
|
||||
*/
|
||||
export function createWebSocket(url: string): WebSocketManager {
|
||||
return new WebSocketManager(url);
|
||||
}
|
||||
Reference in New Issue
Block a user