perf: 待办消息支持指定成员

This commit is contained in:
kuaifan 2022-07-08 09:14:40 +08:00
parent 488259d442
commit e97f2271fa
7 changed files with 147 additions and 35 deletions

View File

@ -1022,6 +1022,10 @@ class DialogController extends AbstractController
* @apiName msg__todo
*
* @apiParam {Number} msg_id 消息ID
* @apiParam {String} type 设待办对象
* - all: 会话全部成员(默认)
* - user: 会话指定成员
* @apiParam {Array} userids 会员ID组type=user有效格式: [userid1, userid2, userid3]
*
* @apiSuccess {Number} ret 返回状态码1正确、0错误
* @apiSuccess {String} msg 返回信息(错误描述)
@ -1032,6 +1036,16 @@ class DialogController extends AbstractController
$user = User::auth();
//
$msg_id = intval(Request::input("msg_id"));
$type = trim(Request::input("type", "all"));
$userids = Request::input('userids');
//
if ($type === 'user') {
if (empty($userids)) {
return Base::retError("选择指定成员");
}
} else {
$userids = [];
}
//
$msg = WebSocketDialogMsg::whereId($msg_id)->first();
if (empty($msg)) {
@ -1039,7 +1053,7 @@ class DialogController extends AbstractController
}
WebSocketDialog::checkDialog($msg->dialog_id);
//
return $msg->toggleTodoMsg($user->userid);
return $msg->toggleTodoMsg($user->userid, $userids);
}
/**

View File

@ -351,6 +351,7 @@ class UsersController extends AbstractController
* - keys.disable 0-排除禁止默认1-含禁止2-仅禁止
* - keys.project_id 在指定项目ID
* - keys.no_project_id 不在指定项目ID
* - keys.dialog_id 在指定对话ID
* @apiParam {Object} sorts 排序方式
* - sorts.az 按字母asc|desc
* @apiParam {Number} updated_time 在这个时间戳之后更新的
@ -401,6 +402,11 @@ class UsersController extends AbstractController
$query->select('userid')->from('project_users')->where('project_id', $keys['no_project_id']);
});
}
if (intval($keys['dialog_id']) > 0) {
$builder->whereIn('userid', function ($query) use ($keys) {
$query->select('userid')->from('web_socket_dialog_users')->where('dialog_id', $keys['dialog_id']);
});
}
if (in_array($sorts['az'], ['asc', 'desc'])) {
$builder->orderBy('az', $sorts['az']);
}

View File

@ -301,9 +301,10 @@ class WebSocketDialogMsg extends AbstractModel
/**
* 设待办、取消待办
* @param int $sender 设待办的会员ID
* @param array $userids 设置给指定会员
* @return mixed
*/
public function toggleTodoMsg($sender)
public function toggleTodoMsg($sender, $userids = [])
{
if (in_array($this->type, ['tag', 'todo', 'notice'])) {
return Base::retError('此消息不支持社待办');
@ -328,6 +329,7 @@ class WebSocketDialogMsg extends AbstractModel
'id' => $this->id,
'type' => $this->type,
'msg' => $this->msg,
'userids' => implode(",", $userids),
]
], $sender);
if (Base::isSuccess($res)) {
@ -336,8 +338,11 @@ class WebSocketDialogMsg extends AbstractModel
$dialog->pushMsg('update', array_merge($resData, ['dialog_id' => $this->dialog_id]));
//
if ($this->todo) {
$userids = $dialog->dialogUser->pluck('userid')->toArray();
foreach ($userids as $userid) {
$useridList = $dialog->dialogUser->pluck('userid')->toArray();
foreach ($useridList as $userid) {
if ($userids && !in_array($userid, $userids)) {
continue;
}
WebSocketDialogMsgTodo::createInstance([
'dialog_id' => $this->dialog_id,
'msg_id' => $this->id,

View File

@ -86,6 +86,10 @@
type: Number,
default: 0
},
dialogId: {
type: Number,
default: 0
},
},
data() {
return {
@ -161,6 +165,7 @@
key,
project_id: this.projectId,
no_project_id: this.noProjectId,
dialog_id: this.dialogId,
},
take: 50
},

View File

@ -9,6 +9,13 @@
<div class="todo-user"><UserAvatar :userid="source.userid" :tooltipDisabled="source.userid == userId" :show-name="true" :show-icon="false"/></div>
{{$L(source.msg.action === 'remove' ? '取消待办' : (source.msg.action === 'done' ? '完成' : '设待办'))}}
"{{$A.getMsgSimpleDesc(source.msg.data)}}"
<div v-if="formatTodoUser(source.msg.data).length > 0" class="todo-users">
<span>{{$L('给')}}</span>
<template v-for="(item, index) in formatTodoUser(source.msg.data)">
<div v-if="index < 3" class="todo-user"><UserAvatar :userid="item" :tooltipDisabled="item == userId" :show-name="true" :show-icon="false"/></div>
<div v-else-if="index == 3" class="todo-user">+{{formatTodoUser(source.msg.data).length - 3}}</div>
</template>
</div>
</div>
<div v-else-if="source.type === 'notice'" class="dialog-notice">
{{source.msg.notice}}
@ -136,6 +143,16 @@ export default {
this.$store.dispatch("dialogMsgRead", this.source);
},
formatTodoUser(data) {
if ($A.isJson(data)) {
const {userids} = data
if (userids) {
return userids.split(",")
}
}
return []
},
onViewTag() {
this.onViewReply({
msg_id: this.source.id,

View File

@ -280,6 +280,28 @@
</div>
</Modal>
<!-- 设置待办 -->
<Modal
v-model="todoSettingShow"
:title="$L('设置待办')"
:mask-closable="false">
<Form ref="todoSettingForm" :model="todoSettingData" label-width="auto" @submit.native.prevent>
<FormItem prop="type" :label="$L('当前会话')">
<RadioGroup v-model="todoSettingData.type">
<Radio label="all">{{$L('所有成员')}}</Radio>
<Radio label="user">{{$L('指定成员')}}</Radio>
</RadioGroup>
</FormItem>
<FormItem v-if="todoSettingData.type === 'user'" prop="userids">
<UserInput v-model="todoSettingData.userids" :dialog-id="dialogId" :placeholder="$L('选择指定成员')"/>
</FormItem>
</Form>
<div slot="footer" class="adaption">
<Button type="default" @click="todoSettingShow=false">{{$L('取消')}}</Button>
<Button type="primary" :loading="todoSettingLoad > 0" @click="onTodo('submit')">{{$L('确定')}}</Button>
</div>
</Modal>
<!--群设置-->
<DrawerOverlay
v-model="groupInfoShow"
@ -421,6 +443,13 @@ export default {
replyListShow: false,
replyListId: 0,
todoSettingShow: false,
todoSettingLoad: 0,
todoSettingData: {
type: 'all',
userids: [],
},
todoViewLoad: false,
todoViewShow: false,
todoViewMid: 0,
@ -1718,41 +1747,61 @@ export default {
});
},
onTodo() {
onTodo(type) {
if (this.operateVisible) {
return
}
const data = {
msg_id: this.operateItem.id,
}
//
$A.modalConfirm({
title: this.operateItem.todo ? '取消待办' : '设置待办',
content: this.operateItem.todo ? "撤回待办后,会话其他成员的待办也将消失。" : "设置为待办后,将通知会话所有成员。",
cancelText: '取消',
okText: '确定',
loading: true,
onOk: () => {
return new Promise((resolve, reject) => {
this.$store.dispatch("setLoad", {
key: `msg-${data.msg_id}`,
delay: 600
})
this.$store.dispatch("call", {
url: 'dialog/msg/todo',
data,
}).then(({data, msg}) => {
resolve(msg)
this.tagOrTodoSuccess(data)
this.onActive()
}).catch(({msg}) => {
reject(msg);
}).finally(_ => {
this.$store.dispatch("cancelLoad", `msg-${data.msg_id}`)
});
})
if (type === 'submit') {
if ($A.arrayLength(this.todoSettingData.userids) === 0) {
$A.messageWarning("选择指定成员");
return
}
});
this.todoSettingLoad++
this.onTodoSubmit(this.todoSettingData).then(msg => {
$A.messageSuccess(msg)
this.todoSettingShow = false
}).catch($A.messageError).finally(_ => {
this.todoSettingLoad--
})
} else {
this.todoSettingData = {
type: 'all',
userids: [],
msg_id: this.operateItem.id,
}
if (this.operateItem.todo) {
$A.modalConfirm({
content: "你确定取消待办吗?",
cancelText: '取消',
okText: '确定',
loading: true,
onOk: () => this.onTodoSubmit(this.todoSettingData)
});
} else {
this.todoSettingShow = true
}
}
},
onTodoSubmit(data) {
return new Promise((resolve, reject) => {
this.$store.dispatch("setLoad", {
key: `msg-${data.msg_id}`,
delay: 600
})
this.$store.dispatch("call", {
url: 'dialog/msg/todo',
data,
}).then(({data, msg}) => {
resolve(msg)
this.tagOrTodoSuccess(data)
this.onActive()
}).catch(({msg}) => {
reject(msg);
}).finally(_ => {
this.$store.dispatch("cancelLoad", `msg-${data.msg_id}`)
});
})
},
tagOrTodoSuccess(data) {

View File

@ -337,6 +337,22 @@
.dialog-todo {
cursor: pointer;
.todo-users {
display: inline-block;
> div + div {
padding-left: 8px;
position: relative;
&:before {
content: "";
position: absolute;
left: 0;
bottom: 0;
}
}
}
.todo-user {
display: inline-block;
}