新开发

This commit is contained in:
张运江 2025-01-16 17:41:32 +08:00
parent 7b41f9f0db
commit c543998117
3 changed files with 269 additions and 17 deletions

View File

@ -504,9 +504,10 @@ import { values } from "lodash";
this.$message.warning(`请至少选中一个调解案件!`)
return
}
api.calling_batchcall({caseIdList: this.selectionData}).then(res => {
api.callingBatchcall({caseIdList: this.selectionData}).then(res => {
this.$message.success("智能外呼成功");
// this.getCaseInfoList(1)
this.jumpUrl(`/mediation-page?sourcePage=sourcePage&caseId=${this.selectionData[0]}&queue=1`)
})
},

View File

@ -30,22 +30,59 @@
</el-popover>
<div class="wrap-btn-left-dial pl-22 pr-24 f14 flex-row justify-content-between ml-16">
<div class="mr-24 flex-row justify-content-between align-items-center">
<div class="mr-8 f16 color-F53F3F"><i class="el-icon-video-pause"></i></div>
<div class="mr-8">暂停拨打</div>
<div class="mr-8 f12 color-000">01:00</div>
<div class="mr-8 f20"><i class="el-icon-phone-outline"></i></div>
<div class="mr-8 f20"><i class="el-icon-microphone"></i></div>
<div class="mr-8 ai-logo-img"></div>
<div class="flex-row justify-content-between align-items-center">
<div v-if="calling" class="mr-8 f16 color-F53F3F cursor-p" @click="pauseTimer()"><i class="el-icon-video-pause"></i></div>
<div v-else class="mr-8 f16 color-F53F3F cursor-p" @cilck="startCall()"><i class="el-icon-video-play"></i></div>
<div class="mr-8 cursor-p" v-if="calling" @click="pauseTimer()">暂停拨打</div>
<div class="mr-8 cursor-p" v-else @cilck="startCall()">开始拨打</div>
<div class="mr-8 f12 color-000" v-if="calling">{{formattedTime || '00:00'}}</div>
<div class="mr-8 f20 cursor-p" v-if="calling" @click="hungUp()"><i class="el-icon-phone-outline"></i></div>
<div class="mr-8 f20 cursor-p" v-if="calling && !isMute" @click="muteMic()"><i class="el-icon-microphone"></i></div>
<div class="mr-8 f20 cursor-p" v-if="calling && isMute" @click="unmuteMic()"><i class="el-icon-turn-off-microphone"></i></div>
<div class="mr-8 ai-logo-img" v-if="calling"></div>
</div>
<div class="flex-row justify-content-between align-items-center f14">
<div class="flex-row justify-content-between align-items-center mr-24">
<div class="mr-8 f16"><i class="el-icon-s-operation"></i></div>
<div>队列 <span class="color-000">200</span></div>
<el-popover
placement="bottom"
width="1000"
trigger="click">
<div>
<div class="f16 p-16 border-b-solid-lighter-1">{{queue ? '智能外呼案件列表' : '案件列表'}}</div>
<div class="p-16">
<el-table ref="queueTable" :data="queueList" style="width: 100%" highlight-current-row>
<el-table-column type="index" label="序号" width="50"></el-table-column>
<el-table-column prop="contact" label="被申请人姓名" width="150"></el-table-column>
<el-table-column prop="caseNo" label="案件编号"></el-table-column>
<el-table-column prop="phone" label="电话号码" width="150"></el-table-column>
<el-table-column prop="moneyAmount" label="逾期金额" width="150"></el-table-column>
<el-table-column label="操作" width="150" v-if="queue">
<template slot-scope="scope">
{{scope.row.index}}
<div v-if="scope.row.index === index" style="color:#4080FF">正在调解中...</div>
<div v-else-if="scope.row.status.code === 1" style="color:#BC6F60">未拨打<i class="el-icon-phone-outline el-icon--right"></i></div>
<div v-else style="color:#E5E6EB">已拨打</div>
</template>
</el-table-column>
</el-table>
</div>
</div>
<div slot="reference" class="flex-row justify-content-between align-items-center mr-24 cursor-p">
<div class="mr-8 f16"><i class="el-icon-s-operation"></i></div>
<div>{{queue ? '队列' : '列表'}} <span class="color-000">
{{queue ? callingInfoData.countInit : ''}}
</span></div>
</div>
</el-popover>
<div v-if="queue" class="flex-row justify-content-between align-items-center f14">
<div class="mr-24">已拨打 <span class="color-000">{{callingInfoData.countCall}}</span></div>
<div class="mr-24">已接通 <span class="color-000">{{callingInfoData.countOk}}</span></div>
<div>未接通 <span class="color-000">{{callingInfoData.countFail}}</span></div>
</div>
<div v-else class="flex-row justify-content-between align-items-center f14">
<div class="mr-24">今日已拨打 <span class="color-000">{{todayCountData.countCall}}</span></div>
<div class="mr-24">今日已接通 <span class="color-000">{{todayCountData.countOk}}</span></div>
<div>今日未接通 <span class="color-000">{{todayCountData.countFail}}</span></div>
</div>
<div class="mr-24">已拨打 <span class="color-000">200</span></div>
<div class="mr-24">已接通 <span class="color-000">200</span></div>
<div>未接通 <span class="color-000">200</span></div>
</div>
</div>
</div>
@ -261,6 +298,33 @@ export default {
{label:'适诉案件',value:'9'},{label:'可联账户',value:'10'},{label:'投诉倾向客户',value:'11'},{label:'分期客户',value:'12'},
{label:'其他/无标签',value:'13'}
],
queue: false,
queueList: [],
phoneNumber: '13982024318',
sessionId: '',
index: 0, //
calling: false, //
isMute: false, //
isPause: false, //
callingInfoData: {
countInit: 0,
countOk: 0,
countFail: 0,
countCall: 0,
},
todayCountData: {
countInit: 0,
countOk: 0,
countFail: 0,
countCall: 0,
},
startTime: 0,
elapsedTime: 0,
timerInterval: null,
isRunning: false,
};
},
computed: {
@ -287,11 +351,31 @@ export default {
let oh = document.documentElement.clientHeight;
return oh - 57 - 128
},
formattedTime() {
const totalSeconds = Math.floor(this.elapsedTime / 1000);
const minutes = Math.floor(totalSeconds / 60);
const seconds = totalSeconds % 60;
return `${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`;
},
},
async created() {
this.caseId = this.$route.query.caseId
this.caseId = this.$route.query.caseId || null
this.queue = this.$route.query.queue || null
this.getCaseInfoById();//
this.getmediate_record()
this.callingTodayCount() //
if (this.queue) {
await this.callingQueue() //
await this.callingInfo() //
}
const that = this
window.tccc.on('sessionEnded', (options) => {
console.log('监听挂断事件', options)
that.calling = false
that.resetTimer()
const that = this.nextCall()
})
},
beforeDestroy() {
// if(this.timer) { //
@ -365,6 +449,151 @@ export default {
}
})
},
async callingInfo() {
try {
let res = await api.callingInfo({})
this.callingInfoData = res
} catch (err) {}
},
async callingTodayCount() {
try {
let res = await api.callingTodayCount({})
this.todayCountData = res
} catch (err) {}
},
//
callingQueue() {
api.callingQueue({}).then(res => {
this.queueList = res.queue || []
this.caseId = String(res.queue[0].caseId) || ''
this.getCaseInfoById()
this.getmediate_record()
})
},
startCall () {
console.log('queueList==================',this.queueList)
for (let i=0; i < this.queueList.length; i++) {
if (this.queueList[i].status.code === 1) {
console.log('定位到可拨打的案件',i)
this.index = i
this.startOutboundCall()
return
}
}
},
//
async startOutboundCall() {
// this.phoneNumber = this.queueList[this.index].phone
this.calling = true
console.log('进入呼叫电话:', this.phoneNumber)
try {
let data = await window.tccc.Call.startOutboundCall({phoneNumber: this.phoneNumber})
this.sessionId = data.sessionId
console.log('呼叫成功', data)
this.callingSuccess()
this.startTimer()
} catch (err) {
this.$message.error('呼叫失败' + err.message)
console.log('呼叫失败',err.message)
this.callingFail()
//
} finally {}
},
//
async callingSuccess () {
try {
let res = await api.callingSuccess({caseId: this.caseId})
} catch (err) { }
},
//
async callingFail () {
try {
let res = await api.callingSuccess({caseId: this.caseId})
} catch (err) { }
},
//
async hungUp() {
try {
let res = await window.tccc.Call.hungUp({sessionId: this.sessionId})
this.calling = false
this.resetTimer()
this.nextCall()
} catch (err) {
//
} finally {}
},
//
nextCall() {
if (!this.queue) return
if (this.isPause) {
this.isPause = false
this.calling = false
return
}
const that = this
that.index ++
setTimeout(() => {
if (that.index <= that.queueList.length - 1) {
that.caseId = String(that.queueList[that.index].caseId) || ''
that.getCaseInfoById()
that.getmediate_record()
that.startOutboundCall()
}
}, 5000)
},
//
async deleteCall() {
try {
let data = await window.tccc.Call.deleteCall({sessionId: this.sessionId})
} catch (err) {
//
} finally {
}
},
//
async muteMic() {
try {
let data = await window.tccc.Call.muteMic({sessionId: this.sessionId})
this.isMute = true
this.$message.success('已静音')
} catch (err) {
//
this.$message.error('静音失败')
}
},
//
async unmuteMic() {
try {
let data = await window.tccc.Call.unmuteMic({sessionId: this.sessionId})
this.isMute = false
this.$message.success('已取消静音')
} catch (err) {
//
this.$message.error('取消静音失败')
}
},
startTimer() {
if (!this.isRunning) {
this.startTime = Date.now() - this.elapsedTime;
this.timerInterval = setInterval(() => {
this.elapsedTime = Date.now() - this.startTime;
}, 1000);
this.isRunning = true;
}
},
pauseTimer() {
if (this.isRunning) {
this.isPause=true
clearInterval(this.timerInterval);
this.isRunning = false;
}
},
resetTimer() {
clearInterval(this.timerInterval);
this.elapsedTime = 0;
this.isRunning = false;
},
}
};
</script>
@ -734,4 +963,7 @@ export default {
}
}
.cursor-p {
cursor: pointer;
}
</style>

View File

@ -299,10 +299,29 @@ const caseManagementApi = {
},
// 呼叫-发起批量智能外呼
calling_batchcall: data => {
callingBatchcall: data => {
return service.service.post(`${apiAdmin}api/trace/calling/batch-call`, data)
},
// 呼叫-当前呼叫队列
callingQueue: data => {
return service.service.post(`${apiAdmin}api/trace/calling/queue`, data)
},
// 呼叫-呼叫成功
callingSuccess: data => {
return service.service.post(`${apiAdmin}api/trace/calling/success`, data)
},
// 呼叫-呼叫失败
callingFail: data => {
return service.service.post(`${apiAdmin}api/trace/calling/fail`, data)
},
// 当前呼叫详情统计
callingInfo: data => {
return service.service.post(`${apiAdmin}api/trace/calling/info`, data)
},
// 今日呼叫统计
callingTodayCount: data => {
return service.service.post(`${apiAdmin}api/trace/calling/todayCount`, data)
},