参考地址:https://www.npmjs.com/package/@aspnet/signalr
1、:安装
npm install @aspnet/signalr
2、在signalR.js中封装signalR方法
import bus from "./bus.js"
const signalR = require("@aspnet/signalr");
let connection = null;
export let connectServer = (url, createUserDto) => {
connection = new signalR.HubConnectionBuilder().withUrl(url).build();
//初始化
initSocket(createUserDto)
}
//初始化包括 连接,获取消息
let initSocket = (createUserDto) => {
//连接
connection.start().then(function () {
connection.invoke("Connected", createUserDto) //这里的invoke是指触发后端相应的“Connected”方法
.then(function (message) {
console.log('已连接start...')
})
.catch(function (err) {
return console.error(err.toString());
});
}).catch(function (err) {
return console.error(err.toString());
});
//获取消息 对应后端的方法,此处为“SendGroup”
connection.on("SendGroup", function (data) {
//所有用户需要改变的 写在下面
if (data != null && data != undefined) {
var str = "[" + data.time + "]";
switch (data.type) {
case 1: //组内信息
str += data.data.connectName + ":" + data.data.msg;
break;
case 2: //加入
str += data.data.connectName + "加入房间";
break;
case 3: //离开
str += data.data.connectName + "离开房间";
break;
case 4: //私人通知
str += data.data.msg;
break;
default:
break;
}
bus.$emit('handleRefreshChatData', data) //根据业务需要调用方法更新数据
bus.$notify.info({
title: '消息',
dangerouslyUseHTMLString: true,
message: str,
duration: 0,
position: 'bottom-right'
});
} else {
console.log("error,please restart ChatHub");
}
});
}
//触发方法 methodName是方法名 connectObject是传入的参数
let sendMsg = (methodName, connectObject) => {
connection.invoke(methodName, connectObject)
.then(function (message) {
//该用户改变 在下面调用
console.log('触发'+methodName+' '+message)
//业务需要 触发离开则断开连接
if(methodName === 'LeaveGroup'){
endConnect()
}
})
.catch(function (err) {
return console.error(err.toString());
});
}
let endConnect = ()=>{
connection.stop(()=>{
})
}
export default { sendMsg }
3、在main.js中注册发送消息的全局方法
import signalR from './utils/signalR'
Vue.prototype.sendMsg = signalR.sendMsg
4、父组件中
<chat :options="options"></chat>
<el-button @click="startConnect">{{options.connectFlag == '1' ? '断开' : '连接'}}</el-button>
...
methods: {
startConnect(){
if(this.options.connectFlag == 1){
this.options.connectFlag =2
}else{
this.options.connectFlag =1
}
},
},
}
5、子组件中
<el-input type="textarea" resize="none" :rows="5" v-model="sendContent"></el-input>
<el-button type="primary" @click="sendMessage" :disabled="sendContent==''">发送</el-button>
...
<script>
import {connectServer} from "../utils/signalR.js" //引入局部方法
import bus from "../utils/bus.js"
export default {
name:'chat',
props:{
options:{
type: Object,
default:{}
}
},
data(){
return{
sendContent:'',
isConnect: false,//判断当前的连接状态
}
},
watch:{
'options.connectFlag':{
immediate:true,
handler(val){
if(val === 1){
this.startConnect()
}else if (val === 2){
//如果当前没有连接
if(!this.isConnect){
console.log('当前没有连接')
return
}
//业务需要,先调用LeaveGroup,然后关闭连接。如果需要直接关闭,可以再把endConnect方法拿出来调用
this.sendMsg("LeaveGroup", {id:this.options.id})
this.isConnect = false
}
}
}
},
mounted(){
bus.$on('handleRefreshChatData', (data) => {
console.log('获取接收数据',data)
});
},
methods:{
startConnect(){
//需要增加必填数据非空的判断
if(!(this.options.curUserId && this.options.sender && this.options.targetApiUrl )){
console.log('curUserId,sender,targetApiUrl为必填参数')
return
}
let createUserDto = {
"UserId": this.options.curUserId,
"UserName": this.options.sender,
};
connectServer(this.options.targetApiUrl, createUserDto)
this.isConnect = true
},
sendMessage(){
//如果当前没有连接
if(!this.isConnect){
console.log('当前没有连接')
return
}
//调用接口
this.sendMsg("Send", {id:this.options.id, data:this.sendContent})
//清空消息发送框
this.sendContent = ''
//发消息后 消息下拉到底部
//document.getElementsByClassName('position-box')[0].scrollIntoView();
}
}
}
</script>