Browse Source

reactor:呼叫中心底层方法重构;

zhangchong 10 months ago
parent
commit
e44497333d

+ 0 - 6
src/App.vue

@@ -82,12 +82,6 @@ onBeforeMount(async () => {
 	// 设置批量第三方 js
 	setIntroduction.jsCdn();
 });
-const unloadHandler = (e: BeforeUnloadEvent) => {
-	//发送消息
-	/*if (ola.ws) {
-		ola.logout();
-	}*/
-};
 // 页面加载时
 onMounted(() => {
 	window.addEventListener('beforeunload', (e) => unloadHandler(e));

+ 12 - 9
src/components/OrderDetail/index.vue

@@ -519,13 +519,13 @@
 </template>
 
 <script setup lang="ts" name="orderDetail">
-import { defineAsyncComponent, PropType, reactive, ref } from 'vue';
+import { defineAsyncComponent, onBeforeUnmount, onMounted, PropType, reactive, ref } from "vue";
 import { useRouter } from 'vue-router';
 import { throttle, transformFile } from '@/utils/tools';
 import { cancelDelay, endCounterSign, orderDetail } from '@/api/business/order';
 import { ElMessage, ElMessageBox } from 'element-plus';
-import { ola } from '@/utils/ola_api';
 import { formatDate } from '@/utils/formatTime';
+import {olaWs} from '@/utils/olaFn'
 
 // 引入组件
 const OrderExpandDetail = defineAsyncComponent(() => import('@/views/business/order/components/Order-expand-detail.vue')); // 扩展信息
@@ -712,8 +712,11 @@ const recordFile = (obj: any) => {
 	playRecordRef.value.openDialog(import.meta.env.VITE_RECORD_PREFIX + obj.recordingAbsolutePath, fileName, obj.recordingAbsolutePath);
 };
 // 电话外呼
-const callPhone = (number: number | string) => {
-	ola.dial(number);
+const callPhone = (phoneNumber: number | string) => {
+  if(!olaWs.value){
+    ElMessage.warning('请先签入'); return;
+  }
+  olaWs.value.dial(phoneNumber);
 };
 const orderRepeatRef = ref<RefType>();
 // 展示重复工单列表
@@ -862,15 +865,15 @@ const onCancelDelay = () => {
 		})
 		.catch(() => {});
 };
-// 暴露变量
-defineExpose({
-	openDialog,
-	closeDialog,
-});
 // 工单详情
 const onOrderDetail = () => {
 	openDialog(props.order);
 };
+// 暴露变量
+defineExpose({
+  openDialog,
+  closeDialog,
+});
 </script>
 <style lang="scss" scoped>
 .order-detail-container {

+ 4 - 39
src/layout/navBars/breadcrumb/telControl.vue

@@ -566,7 +566,6 @@ import {
 } from '@/api/public/wex';
 import signalR from '@/utils/signalR';
 import { Local } from '@/utils/storage';
-import { ola } from '@/utils/ola_api';
 import { useRouter } from 'vue-router';
 import mittBus from '@/utils/mitt';
 import { voiceAssistant } from '@/api/todo/voiceAssistant';
@@ -574,7 +573,7 @@ import { submitLog } from '@/api/public/log';
 import { getDataByCode } from '@/api/system/dict';
 import { useTransition, useDocumentVisibility } from '@vueuse/core';
 import { useWebSocket } from '@/hooks/useWebsocket';
-import { olaFn } from '@/utils/olaFn';
+import { olaFn,olaWs } from '@/utils/olaFn';
 // 引入组件
 const CommonAdvice = defineAsyncComponent(() => import('@/components/CommonAdvice/index.vue')); // 常用意见
 const AnnexList = defineAsyncComponent(() => import('@/components/AnnexList/index.vue'));
@@ -847,9 +846,7 @@ const websocket_connect = () => {
 			// pongTimeout: 1000,
 		},
 	});
-
 	console.log('链接呼叫中心', getNowDateTime());
-  mittBus.emit('globalOla',olaRef.value)
 };
 // 呼叫中心链接成功
 const onConnected = () => {
@@ -870,6 +867,7 @@ const onConnected = () => {
 		}
 	}
 	olaRef.value.login(array_ola_queue, currentTel.value.telNo, { type: 'onhook' });
+  olaWs.value = olaRef.value;
 	if (currentTel.value.telModel != 2) {
 		// 普通模式才链接语音助手
 		connectVoiceAssistant(currentTel.value.telNo); // 坐席助手开启
@@ -887,6 +885,7 @@ const onConnected = () => {
 // 呼叫中心链接关闭
 const onDisconnected = (event: any) => {
 	console.log('呼叫中心断开链接:', event);
+  olaWs.value = null;
 	resetState();
 	const currentTel = Local.get('currentTel');
 	const name: string = `天润分机号:${currentTel}的websocket断开链接`;
@@ -1243,41 +1242,7 @@ const onMessage = async (event: any) => {
 		// 其他消息
 		// console.log('command/reply', data);
 	}
-};
-// 呼叫中心链接
-const onConnect = () => {
-	Local.set('currentTel', currentTel.value.telNo);
-	olaRef.value.logout(currentTel.value.telNo); //连接之后,先登出一次,防止其他地方已经登陆
-	let array_ola_queue: EmptyArrayType = []; // 队列
-	if (currentTel.value.telModel === 2) {
-		// 外呼模式
-		let array = currentTel.value.queueCallOut.split(',');
-		for (let i = 0; i < array.length; i++) {
-			array_ola_queue[i] = array[i];
-		}
-	} else {
-		// 普通模式
-		let array = currentTel.value.queue.split(',');
-		for (let i = 0; i < array.length; i++) {
-			array_ola_queue[i] = array[i];
-		}
-	}
-	olaRef.value.login(array_ola_queue, currentTel.value.telNo, { type: 'onhook' });
-	if (currentTel.value.telModel != 2) {
-		// 普通模式才链接语音助手
-		connectVoiceAssistant(currentTel.value.telNo); // 坐席助手开启
-	}
-
-	const name: string = `天润分机号:${currentTel.value.telNo}的websocket链接成功`;
-	const remark: string = `天润websocket 链接成功:分机模式:${currentTel.value.telModel}`;
-	const request = {
-		creationTime: new Date(),
-		name,
-		remark,
-		executeUrl: import.meta.env.VITE_CALLCENTER_SOCKET_URL,
-	};
-	submitLogFn(request);
-};
+};;
 // 呼叫中心链接错误
 const onError = (ws: any, e: any) => {
 	console.log(`呼叫中心链接错误:${e}`);

+ 4 - 4
src/layout/navBars/breadcrumb/user.vue

@@ -153,7 +153,7 @@
 </template>
 
 <script setup lang="ts" name="layoutBreadcrumbUser">
-import { defineAsyncComponent, ref, computed, reactive, onMounted, onUnmounted } from "vue";
+import { defineAsyncComponent, ref, computed, reactive, onMounted, onUnmounted, onBeforeUnmount } from "vue";
 import { useRouter } from 'vue-router';
 import { ElMessageBox, ElMessage, ElNotification, FormInstance } from 'element-plus';
 import screenfull from 'screenfull';
@@ -166,8 +166,8 @@ import mittBus from '@/utils/mitt';
 import { changePwd } from '@/api/login/user';
 import { megcount } from '@/api/auxiliary/notice';
 import signalR from '@/utils/signalR';
-import { ola } from '@/utils/ola_api';
 import { dutyOff } from '@/api/public/wex';
+import { olaWs } from "@/utils/olaFn";
 
 // 引入组件
 const UserNews = defineAsyncComponent(() => import('@/layout/navBars/breadcrumb/userNews.vue'));
@@ -339,8 +339,8 @@ const onLogOut = () => {
 			.then(() => {
 				dutyOff(); // 呼叫中心签出
 				setTimeout(() => {
-					ola.logout(); // 呼叫中心退出登录
-					ola.close(); // 呼叫中心关闭
+          olaWs.value?.logout(); // 呼叫中心退出登录
+          olaWs.value?.close(); // 呼叫中心关闭
 					signalR.leaveAllGroupAndStop(); // 退出所有组
 					// 重置所有状态
 					usetelStatusStore.resetState();

+ 0 - 1
src/types/mitt.d.ts

@@ -20,6 +20,5 @@ declare type MittType = {
 	outboundConnect?: any; //外呼连接
 	ToDayWaitNum: any; // 今日等待
 	CurrentWaitNum: any; // 当前等待
-	globalOla:any; //全局电话
 	wsNotice: any;
 };

+ 2 - 1
src/utils/olaFn.ts

@@ -11,6 +11,7 @@ function resolveNestedOptions<T>(options: T | true): T {
 	if (options === true) return {} as T;
 	return options;
 }
+export const olaWs = ref(null); // 全局变量 当前呼叫中心链接
 export function olaFn(url: MaybeRefOrGetter<string | URL | undefined>, options: any) {
 	const {
 		onConnected,
@@ -502,4 +503,4 @@ export function olaFn(url: MaybeRefOrGetter<string | URL | undefined>, options:
 		password: options.password,
 		next_uuid,
 	};
-}
+}

+ 4 - 7
src/views/business/visit/component/Visit-detail.vue

@@ -444,10 +444,10 @@ import { ElMessage, FormInstance } from 'element-plus';
 import { commonEnum } from '@/utils/constants';
 import { storeToRefs } from 'pinia';
 import { useUserInfo } from '@/stores/userInfo';
-import { ola } from '@/utils/ola_api';
 import dayjs from 'dayjs';
 import { visitDetailBaseData, visitOrder } from '@/api/business/visit';
 import mittBus from '@/utils/mitt';
+import { olaWs } from "@/utils/olaFn";
 
 // 引入组件
 const CommonAdvice = defineAsyncComponent(() => import('@/components/CommonAdvice/index.vue')); // 常用意见
@@ -582,10 +582,10 @@ const onSmartRecord = () => {
 };
 // 呼叫
 const onCall = (phoneNumber: string) => {
-  if(!olaFn.value){
+  if(!olaWs.value){
     ElMessage.warning('请先签入'); return;
   }
-  olaFn.value.dial(phoneNumber);
+  olaWs.value.dial(phoneNumber);
 };
 // 选择不满意原因
 const selectReason = (val: any, index: number | string) => {
@@ -629,7 +629,6 @@ const onSubmit = (formEl: FormInstance | undefined) => {
 	});
 };
 // 选中常用意见
-const olaFn = ref(null);
 const chooseAdvice = (item: any, index: number | string) => {
 	if (state.ruleForm.visitDetails[index].visitContent === null) {
 		state.ruleForm.visitDetails[index].visitContent = '';
@@ -637,14 +636,12 @@ const chooseAdvice = (item: any, index: number | string) => {
 	state.ruleForm.visitDetails[index].visitContent += item.content;
 };
 const callId = ref<string>('');
+const olaFn = ref(null);
 onMounted(() => {
 	mittBus.on('outboundConnect', (data) => {
 		console.log(data, '外呼已经接通辣');
 		if (data.dnis === state.orderDetail.contact) callId.value = data.other_accept;
 	});
-  mittBus.on('globalOla', (data:any) => { // 全局的电话控件实例
-    olaFn.value = data;
-  })
 });
 onBeforeUnmount(() => {
 	mittBus.off('outboundConnect');

+ 7 - 2
src/views/tels/extension/index.vue

@@ -88,10 +88,11 @@ import { computed, onMounted, reactive, ref,onBeforeUnmount } from 'vue';
 import type { FormInstance } from 'element-plus';
 import { ElMessage, ElMessageBox } from 'element-plus';
 import signalR from '@/utils/signalR';
-import { ola } from '@/utils/ola_api';
 import { storeToRefs } from 'pinia';
 import { useTelStatus } from '@/stores/telStatus';
 import { extensionPaged, forceLogout } from '@/api/tels/extension';
+import mittBus from "@/utils/mitt";
+import { olaWs } from "@/utils/olaFn";
 
 const proTableRef = ref<RefType>(); // 表格ref
 // 表格配置项
@@ -187,7 +188,11 @@ const threeWayCount = computed(() => {
 });
 // 监听分机
 const onListen = (row: any) => {
-	ola.monitor(row.telNo, telStatusInfo.value.telsNo);
+  if(!olaWs.value){
+    ElMessage.warning('请先签入');
+    return;
+  }
+  olaWs.value.monitor(row.telNo, telStatusInfo.value.telsNo);
 };
 // 强制下线
 const onOffline = (row: any) => {

+ 84 - 84
src/views/tels/smartRecord/index.vue

@@ -58,55 +58,55 @@
 		&lt;!&ndash; 播放录音 &ndash;&gt;
 		<play-record ref="playRecordRef" />-->
 		<el-card shadow="never">
-				<el-form :model="state.testForm" @submit.native.prevent>
-					<el-row :gutter="10">
-						<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
-							<el-form-item prop="serIp" label="服务器ip:">
-								<el-input v-model="state.testForm.serIp" placeholder="例如:114.114.114.114" clearable />
-							</el-form-item>
-						</el-col>
-						<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
-							<el-form-item prop="serPort" label="服务器端口:">
-								<el-input v-model="state.testForm.serPort" placeholder="例如:29003" clearable />
-							</el-form-item>
-						</el-col>
-						<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
-							<el-form-item prop="queue" label="队列:">
-								<el-input v-model="state.testForm.queue" placeholder="例如:10010" clearable />
-							</el-form-item>
-						</el-col>
-						<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
-							<el-form-item prop="callNumber" label="分机:">
-								<el-input v-model="state.testForm.agent" placeholder="例如:1001" clearable />
-							</el-form-item>
-						</el-col>
-						<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
-							<el-form-item prop="agentPwd" label="分机密码:">
-								<el-input v-model="state.testForm.agentPwd" placeholder="例如:!@#123Qw" clearable />
-							</el-form-item>
-						</el-col>
-						<el-divider>
-							<span class="ss_title">连接状态:{{ wsStatus }}</span>
+			<el-form :model="state.testForm" @submit.native.prevent>
+				<el-row :gutter="10">
+					<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
+						<el-form-item prop="serIp" label="服务器ip:">
+							<el-input v-model="state.testForm.serIp" placeholder="例如:114.114.114.114" clearable />
+						</el-form-item>
+					</el-col>
+					<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
+						<el-form-item prop="serPort" label="服务器端口:">
+							<el-input v-model="state.testForm.serPort" placeholder="例如:29003" clearable />
+						</el-form-item>
+					</el-col>
+					<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
+						<el-form-item prop="queue" label="队列:">
+							<el-input v-model="state.testForm.queue" placeholder="例如:10010" clearable />
+						</el-form-item>
+					</el-col>
+					<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
+						<el-form-item prop="callNumber" label="分机:">
+							<el-input v-model="state.testForm.agent" placeholder="例如:1001" clearable />
+						</el-form-item>
+					</el-col>
+					<el-col :xs="24" :sm="12" :md="12" :lg="6" :xl="6">
+						<el-form-item prop="agentPwd" label="分机密码:">
+							<el-input v-model="state.testForm.agentPwd" placeholder="例如:!@#123Qw" clearable />
+						</el-form-item>
+					</el-col>
+					<el-divider>
+						<span class="ss_title">连接状态:{{ wsStatus }}</span>
 
-							<el-button @click="wsConnect" type="primary" class="ml10" v-if="showConnect">连接</el-button>
-						</el-divider>
-						<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24">
-							<div class="mb10">签入状态:{{ olaStatus }}</div>
-							<el-button @click="login" type="primary">签入</el-button>
-							<el-button @click="logout" type="primary">签出</el-button>
-							<el-button @click="ready" type="primary">示闲</el-button>
-							<el-button @click="unReady" type="primary">示忙</el-button>
-							<el-button @click="hold" type="primary">保持</el-button>
-							<el-button @click="unHold" type="primary">取消保持</el-button>
-							<el-button @click="hangup" type="primary">挂机</el-button>
-						</el-col>
-						<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24">
-							<el-form-item label="JSON数据">
-								{{jsonData}}
-							</el-form-item>
-						</el-col>
-					</el-row>
-				</el-form>
+						<el-button @click="websocket_connect" type="primary" class="ml10" v-if="showConnect">连接</el-button>
+					</el-divider>
+					<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24">
+						<div class="mb10">签入状态:{{ olaStatus }}</div>
+						<el-button @click="login" type="primary">签入</el-button>
+						<el-button @click="logout" type="primary">签出</el-button>
+						<el-button @click="ready" type="primary">示闲</el-button>
+						<el-button @click="unReady" type="primary">示忙</el-button>
+						<el-button @click="hold" type="primary">保持</el-button>
+						<el-button @click="unHold" type="primary">取消保持</el-button>
+						<el-button @click="hangup" type="primary">挂机</el-button>
+					</el-col>
+					<el-col :xs="24" :sm="24" :md="24" :lg="24" :xl="24">
+						<el-form-item label="JSON数据">
+							{{ jsonData }}
+						</el-form-item>
+					</el-col>
+				</el-row>
+			</el-form>
 		</el-card>
 	</div>
 </template>
@@ -114,15 +114,13 @@
 <script lang="tsx" setup name="telsSmartRecord">
 import { defineAsyncComponent, onMounted, reactive, ref } from 'vue';
 import type { FormInstance } from 'element-plus';
-import { ElMessageBox } from 'element-plus';
+import { ElMessage } from 'element-plus';
 import { downloadFileByStream } from '@/utils/tools';
 import { formatDate } from '@/utils/formatTime';
-import { shortcuts } from '@/utils/constants';
 import other from '@/utils/other';
 import { fileDownload } from '@/api/public/file';
 import { jthsRecord } from '@/api/todo/voiceAssistant';
-import { ola } from '@/utils/ola_api';
-import { forceLogout } from "@/api/tels/extension";
+import { olaFn } from '@/utils/olaFn';
 
 // 引入组件
 const PlayRecord = defineAsyncComponent(() => import('@/views/tels/callLog/component/Play-record.vue')); // 播放录音
@@ -257,28 +255,35 @@ onMounted(() => {
 const wsStatus = ref('Disconnected');
 const jsonData = ref('');
 const showConnect = ref(true);
-// 链接ws
-const wsConnect = () => {
+
+// 链接呼叫中心
+const olaRef = ref();
+const websocket_connect = () => {
 	const websocket_url = 'ws://' + state.testForm.serIp + ':' + state.testForm.serPort + '/ola_socket';
-	console.log('----00000-----');
-	ola.onConnect = onConnect;
-	console.log('-----11111----');
-	ola.onClose = onClose;
-	ola.onMessage = onMessage;
-	ola.connect(websocket_url, state.testForm.agent, state.testForm.agentPwd);
+	olaRef.value = olaFn(websocket_url, {
+		username: state.testForm.agent,
+		password: state.testForm.agentPwd,
+		onConnected: onConnected, // 连接成功
+		onDisconnected: onDisconnected, // 断开链接
+		onMessage: onMessage, // 接收消息
+		heartbeat: {
+			message: JSON.stringify({ cmd: 'ping' }),
+			interval: 5000,
+			// pongTimeout: 1000,
+		},
+	});
 };
-const onConnect = () => {
-	console.log('-----222222----');
-	console.log('websocket connected!');
-	ola._extn = state.testForm.agent;
+const onConnected = () => {
 	showConnect.value = false;
 	wsStatus.value = 'Connected';
-	ola.subscribe('ola.agent.' + state.testForm.agent);
-	ola.subscribe('ola.caller.' + state.testForm.agent);
-	ola.get_agent_state(state.testForm.agent);
 	//连接之后,先登出一次,防止其他地方已经登陆
-	ola.logout();
-	login();
+	olaRef.value.logout();
+};
+const onDisconnected = () => {
+	console.log('websocket closed!');
+	ElMessage.warning('链接断开');
+	wsStatus.value = 'Disconnected';
+	showConnect.value = true;
 };
 const login = () => {
 	let array_ola_queue: EmptyArrayType = []; // 队列
@@ -287,23 +292,19 @@ const login = () => {
 		for (let i = 0; i < array.length; i++) {
 			array_ola_queue[i] = array[i];
 		}
-		ola.login(array_ola_queue, state.testForm.agent, { type: 'onhook' });
+		olaRef.value.login(array_ola_queue, state.testForm.agent, { type: 'onhook' });
 	}
 };
 const logout = () => {
-	ola.logout();
+	olaRef.value.logout();
+	olaRef.value.close();
 	olaStatus.value = '未签入';
 };
-const onClose = () => {
-	console.log('websocket closed!');
-	wsStatus.value = 'Disconnected';
-	showConnect.value = true;
-};
 const olaStatus = ref('');
 const onMessage = (evt: any) => {
-	const data = JSON.parse(evt.data);
+	const data = JSON.parse(evt);
 	if (data.event_type === 'agent_state') {
-		jsonData.value = evt.data;
+		jsonData.value = evt;
 		if (data.state == 'login') {
 			olaStatus.value = '已签入';
 		} else if (data.state == 'logout') {
@@ -349,19 +350,18 @@ const onMessage = (evt: any) => {
 	}
 };
 const ready = () => {
-	ola.go_ready();
+	olaRef.value.go_ready();
 };
 const unReady = () => {
-	ola.go_break('');
+	olaRef.value.go_break('');
 };
 const hold = () => {
-	ola.hold();
+	olaRef.value.hold();
 };
 const unHold = () => {
-	ola.unhold();
+	olaRef.value.unhold();
 };
 const hangup = () => {
-	ola.hangup();
+	olaRef.value.hangup();
 };
-
 </script>