WebSocket
使用@vueuse/core
中的 useWebSocket
使用说明
- 使用
ts
import { useWebSocket } from '@vueuse/core'
const { status, data, send, open, close } = useWebSocket('ws://websocketurl')
自动连接:(默认情况下启用),也可以使用
open()
手动启动自动关闭连接: 根据页面的生命周期,自动关闭连接,也可以使用
close()
手动关闭自动进行异常重试:
- autoReconnect: true,
- autoReconnect: 如下:自动重试3次,每次延迟1秒,失败后执行onFailed()
{ retries: 3, delay: 1000, onFailed() { alert('Failed to connect WebSocket after 3 retires') }, },
心跳测试连接
- heartbeat: true,
- heartbeat: 如下,心跳时发送消息
{ message: 'ping', interval: 1000, }
子协议:
protocols: ['soap'], // ['soap', 'wamp']
示例
- 正常发送消息
- 断开连接后尝试重试3次
示例代码
示例位置:src/views/demo/pages/comp/websocket/index.vue
vue
<template>
<div class="flex">
<div class="w-1/3 bg-white p-4">
<div class="flex items-center">
<span class="text-lg font-medium mr-4"> 连接状态: </span>
<el-tag :type="getTagColor">{{ status }}</el-tag>
</div>
<hr class="my-4" />
<div class="flex">
<el-input v-model:value="state.server" disabled>
<template #addonBefore> 服务地址 </template>
</el-input>
<el-button :type="getIsOpen ? 'danger' : 'primary'" @click="toggle">
{{ getIsOpen ? '关闭连接' : '开启连接' }}
</el-button>
</div>
<p class="text-lg font-medium mt-4">设置</p>
<hr class="my-4" />
<el-input
v-model="state.sendValue"
:rows="2"
:disabled="!getIsOpen"
placeholder="需要发送到服务器的内容"
type="textarea"
/>
<el-button
type="primary"
block
class="mt-4"
:disabled="!getIsOpen"
@click="handlerSend"
>
发送
</el-button>
</div>
<div class="w-2/3 bg-white ml-4 p-4">
<span class="text-lg font-medium mr-4"> 消息记录: </span>
<hr class="my-4" />
<div class="max-h-80 overflow-auto">
<ul>
<li v-for="item in getList" class="mt-2" :key="item.time">
<div class="flex items-center">
<span class="mr-2 text-primary font-medium">收到消息:</span>
<span>{{ formatToDateTime(item.time) }}</span>
</div>
<div>
{{ item.result }}
</div>
</li>
</ul>
</div>
</div>
</div>
</template>
<script setup lang="ts">
import { useWebSocket } from '@vueuse/core';
import { computed, reactive, watchEffect } from 'vue';
import { formatToDateTime } from '/@/utils/dateUtil';
const state = reactive({
server: 'ws://localhost:8000',
sendValue: '',
recordList: [] as { id: number; time: number; res: string }[],
});
const { status, data, send, close, open } = useWebSocket(state.server, {
autoReconnect: {
retries: 3,
delay: 1000,
onFailed() {
alert('Failed to connect WebSocket after 3 retires');
},
},
// heartbeat: {
// message: 'ping',
// interval: 1000,
// },
});
watchEffect(() => {
console.log(state);
if (data.value) {
try {
const res = JSON.parse(data.value);
state.recordList.push(res);
} catch (error) {
state.recordList.push({
res: data.value,
id: Math.ceil(Math.random() * 1000),
time: new Date().getTime(),
});
}
}
});
const getIsOpen = computed(() => status.value === 'OPEN');
const getTagColor = computed(() => (getIsOpen.value ? 'success' : 'danger'));
const getList = computed(() => {
return [...state.recordList].reverse();
});
function handlerSend() {
send(state.sendValue);
state.sendValue = '';
}
function toggle() {
if (getIsOpen.value) {
close();
} else {
open();
}
}
</script>
<style scoped></style>