refactor(chat): 重构聊天会话逻辑和API接口
This commit is contained in:
parent
a4876b3ef6
commit
eab59c8259
|
|
@ -218,9 +218,12 @@ const install = (Vue, vm) => {
|
|||
// 获取教师列表(学生端-招办在线)
|
||||
let GetTeacherListApi = (params = {}) =>
|
||||
vm.$u.get("api/Dialogue/GetTeacherList", params);
|
||||
// 获取会话列表
|
||||
// 获取会话列表-教师
|
||||
let GetDialogueListApi = (params = {}) =>
|
||||
vm.$u.get("api/Dialogue/GetDialogueList", params);
|
||||
// 获取会话列表-用户
|
||||
let GetDialogueList_UserApi = (params = {}) =>
|
||||
vm.$u.get("api/Dialogue/GetDialogueList_User", params);
|
||||
// 创建会话
|
||||
let AddDialogueApi = (params = {}) =>
|
||||
vm.$u.post("api/Dialogue/AddDialogue", params);
|
||||
|
|
@ -236,6 +239,9 @@ const install = (Vue, vm) => {
|
|||
// 置顶一个会话
|
||||
let OverheadOneDialogueApi = (params = {}) =>
|
||||
vm.$u.post("api/Dialogue/OverheadOneDialogue", params);
|
||||
// 删除会话
|
||||
let DeleteDialogueApi = (params = {}) =>
|
||||
vm.$u.post("api/Dialogue/DeleteDialogue", params);
|
||||
|
||||
// 将各个定义的接口名称,统一放进对象挂载到vm.$u.api(因为vm就是this,也即this.$u.api)下
|
||||
vm.$u.api = {
|
||||
|
|
@ -297,6 +303,7 @@ const install = (Vue, vm) => {
|
|||
UpdateUserApi,
|
||||
GetTeacherListApi,
|
||||
GetDialogueListApi,
|
||||
GetDialogueList_UserApi,
|
||||
AddDialogueApi,
|
||||
SendMessage_PrivateApi,
|
||||
GetChatHistoryDataApi,
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
<view class="chat-page">
|
||||
<!-- 顶部导航 -->
|
||||
<header-bar
|
||||
:title="vuex_msgUser.receiverName"
|
||||
:title="vuex_msgUser.name"
|
||||
leftIcon="arrow-left"
|
||||
@leftClick="handleLeftClick"
|
||||
></header-bar>
|
||||
|
|
@ -19,7 +19,7 @@
|
|||
<div class="teacher-info-card">
|
||||
<image class="teacher-avatar" :src="receiverHeadSculptureUrl"></image>
|
||||
<div class="teacher-info">
|
||||
<div class="teacher-name">{{ vuex_msgUser.receiverName }}</div>
|
||||
<div class="teacher-name">{{ vuex_msgUser.name }}</div>
|
||||
|
||||
<div class="teacher-school">
|
||||
<image
|
||||
|
|
@ -52,7 +52,7 @@
|
|||
<!-- 0 发送消息 -->
|
||||
<view
|
||||
class="message-right"
|
||||
v-if="message.interactMode === 0"
|
||||
v-if="message.senderId === vuex_user.Id"
|
||||
:id="'msg-' + message.id"
|
||||
>
|
||||
<view class="message-content">
|
||||
|
|
@ -68,7 +68,7 @@
|
|||
<!-- 1 收到消息 -->
|
||||
<view
|
||||
class="message-left"
|
||||
v-if="message.interactMode === 1"
|
||||
v-if="message.senderId !== vuex_user.Id"
|
||||
:id="'msg-' + message.id"
|
||||
>
|
||||
<image
|
||||
|
|
@ -179,8 +179,7 @@ export default {
|
|||
|
||||
onLoad(options) {
|
||||
console.log(this.vuex_msgList);
|
||||
console.log(this.vuex_msgUser,'this.vuex_msgUser');
|
||||
|
||||
console.log(this.vuex_msgUser, "this.vuex_msgUser");
|
||||
|
||||
this.baseUrl = this.$u.http.config.baseUrl;
|
||||
|
||||
|
|
@ -195,8 +194,8 @@ export default {
|
|||
|
||||
computed: {
|
||||
receiverHeadSculptureUrl() {
|
||||
if (this.vuex_msgUser.receiverHeadSculptureUrl) {
|
||||
return this.baseUrl + "/" + this.vuex_msgUser.receiverHeadSculptureUrl;
|
||||
if (this.vuex_msgUser.headSculptureUrl) {
|
||||
return this.baseUrl + "/" + this.vuex_msgUser.headSculptureUrl;
|
||||
}
|
||||
|
||||
return "/static/common/images/avatar_default2.png";
|
||||
|
|
@ -265,7 +264,7 @@ export default {
|
|||
message: this.messageValue,
|
||||
messageType: 0,
|
||||
filePath: "",
|
||||
interactMode: 0,
|
||||
// interactMode: 0,
|
||||
};
|
||||
|
||||
this.$store.commit("push_Msg", msgUserData);
|
||||
|
|
@ -308,17 +307,7 @@ export default {
|
|||
})
|
||||
.then((res) => {
|
||||
const msgList = res.data.item1.reverse();
|
||||
// 注:现在的消息返回值缺少 interactMode 字段,先手动mock
|
||||
|
||||
for (var i = 0; i < msgList.length; i++) {
|
||||
msgList[i].interactMode = msgList[i].interactMode || 0;
|
||||
|
||||
// if (this.PageIndex != 1) {
|
||||
// this.$store.commit("unshift_Msg", msgList[i]);
|
||||
// } else {
|
||||
// this.$store.commit("push_Msg", msgList[i]);
|
||||
// }
|
||||
}
|
||||
this.$store.commit("push_MsgList", msgList);
|
||||
});
|
||||
},
|
||||
|
|
|
|||
|
|
@ -114,14 +114,8 @@ export default {
|
|||
handleAskQuestion(teacher) {
|
||||
console.log("点击咨询:", teacher);
|
||||
|
||||
var msgUserData = {
|
||||
avatar: teacher.headSculptureUrl,
|
||||
friendId: teacher.id,
|
||||
friendName: teacher.name,
|
||||
};
|
||||
|
||||
// 进入对话会话
|
||||
this.$store.dispatch("openOrCreateDialogue", msgUserData);
|
||||
// 点击立即提问,进入对话会话
|
||||
this.$store.dispatch("createDialogue", teacher);
|
||||
|
||||
return;
|
||||
|
||||
|
|
|
|||
|
|
@ -235,7 +235,7 @@ const store = new Vuex.Store({
|
|||
// 获取聊天记录(私聊)
|
||||
async fetchChatRecord(
|
||||
{ commit, state },
|
||||
{ userId, friendId, chatType = 0, PageIndex = 1, PageSize = 20 }
|
||||
{ userId, friendId, PageIndex = 1, PageSize = 20 }
|
||||
) {
|
||||
const params = { userId, friendId, PageIndex, PageSize };
|
||||
|
||||
|
|
@ -260,65 +260,52 @@ const store = new Vuex.Store({
|
|||
}
|
||||
},
|
||||
|
||||
// 统一入口:打开或创建会话
|
||||
// 使用位置:所有需要进入聊天的入口调用该方法,避免各页面重复逻辑
|
||||
// 1) 获取最新会话列表
|
||||
// 2) 查找是否存在 friendId 对应的会话
|
||||
// 3) 有则设置当前会话并(可选)跳转;无则创建,成功后递归重试
|
||||
async openOrCreateDialogue({ commit, state, dispatch }, user) {
|
||||
const { friendId, friendName, avatar, chatType = 0 } = user || {};
|
||||
const attempt =
|
||||
user && typeof user.attempt === "number" ? user.attempt : 1;
|
||||
if (!friendId) return Promise.reject(new Error("缺少 friendId"));
|
||||
// 点击立即提问进入会话
|
||||
// 1) 创建新会话
|
||||
// 2) 获取接收者信息
|
||||
// 3) 进入会话
|
||||
async createDialogue({ commit, state, dispatch }, user) {
|
||||
const { id, dialogueManagementId } = user || {};
|
||||
if (!id) return Promise.reject(new Error("缺少 id"));
|
||||
|
||||
// 清空消息列表,避免旧消息干扰
|
||||
commit("push_MsgList", []);
|
||||
|
||||
// 第一步:获取列表(复用现有 action,保证 state 同步更新)
|
||||
const list = await dispatch("getUserlist");
|
||||
|
||||
// 第二步:查找是否存在该会话(兼容后端字段 friendId/receiverId)
|
||||
const target = (list || []).find(
|
||||
(i) => i && (i.receiverId === friendId || i.friendId === friendId)
|
||||
);
|
||||
if (target) {
|
||||
commit("set_MsgUser", target);
|
||||
|
||||
Vue.prototype.$u.api
|
||||
.GetReceiverUserInfoApi({ Id: friendId })
|
||||
.then((res) => {
|
||||
if (res.succeed && res.data) {
|
||||
commit("set_MsgUser", { ...target, ...res.data });
|
||||
}
|
||||
});
|
||||
|
||||
if (dialogueManagementId) {
|
||||
// 有会话ID,直接进入会话
|
||||
commit("set_MsgUser", { ...user });
|
||||
uni.navigateTo({
|
||||
url: `/pages/chat/index`,
|
||||
});
|
||||
|
||||
return target;
|
||||
return;
|
||||
}
|
||||
|
||||
// 第二次调用时,无论成功与否均在第三步(创建)之前结束
|
||||
if (attempt >= 2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// 第三步:不存在则创建,成功后重试本流程
|
||||
const res = await Vue.prototype.$u.api.AddDialogueApi({
|
||||
receiverId: friendId,
|
||||
onlineConsultationType: 0, // 0:招生在线;1:迎新在线(可按业务传入)
|
||||
// 没有会话id创建新会话
|
||||
const res1 = await Vue.prototype.$u.api.AddDialogueApi({
|
||||
receiverId: id,
|
||||
onlineConsultationType: 1, // 创建在线咨询固定传1
|
||||
});
|
||||
if (res && res.succeed === true) {
|
||||
// 创建成功后,重新执行流程(再次获取列表并进入会话)
|
||||
return dispatch("openOrCreateDialogue", {
|
||||
friendId,
|
||||
friendName,
|
||||
avatar,
|
||||
chatType,
|
||||
attempt: attempt + 1,
|
||||
|
||||
const resId = res1.data?.dialogueManagementId || "";
|
||||
|
||||
if (res1 && res1.succeed) {
|
||||
// 获取接收者信息,这里没啥用(先注释)
|
||||
// Vue.prototype.$u.api.GetReceiverUserInfoApi({ Id: id }).then((res) => {
|
||||
// if (res.succeed && res.data) {
|
||||
// commit("set_MsgUser", { ...res.data, dialogueManagementId });
|
||||
// uni.navigateTo({
|
||||
// url: `/pages/chat/index`,
|
||||
// });
|
||||
// return;
|
||||
// }
|
||||
// });
|
||||
commit("set_MsgUser", { ...user, dialogueManagementId: resId });
|
||||
uni.navigateTo({
|
||||
url: `/pages/chat/index`,
|
||||
});
|
||||
return;
|
||||
}
|
||||
|
||||
return Promise.reject(new Error(res?.error || "创建会话失败"));
|
||||
},
|
||||
},
|
||||
|
|
|
|||
Loading…
Reference in New Issue