mirror of
https://github.com/kuaifan/dootask.git
synced 2025-12-12 11:19:56 +00:00
feat: 添加用户机器人 webhook 事件配置,优化相关逻辑
This commit is contained in:
parent
6ffd169784
commit
f59bdaf5e0
@ -12,6 +12,7 @@ use App\Module\AI;
|
||||
use App\Module\Doo;
|
||||
use App\Models\File;
|
||||
use App\Models\User;
|
||||
use App\Models\UserBot;
|
||||
use App\Module\Base;
|
||||
use App\Module\Timer;
|
||||
use App\Models\Setting;
|
||||
@ -443,6 +444,29 @@ class DialogController extends AbstractController
|
||||
return Base::retError('打开会话失败');
|
||||
}
|
||||
$data = WebSocketDialog::synthesizeData($dialog->id, $user->userid);
|
||||
|
||||
if ($userid > 0) {
|
||||
$botTarget = User::whereUserid($userid)->whereBot(1)->first();
|
||||
if ($botTarget) {
|
||||
$userBot = UserBot::whereBotId($botTarget->userid)->first();
|
||||
if ($userBot) {
|
||||
$userBot->dispatchWebhook(UserBot::WEBHOOK_EVENT_DIALOG_OPEN, [
|
||||
'dialog_id' => $dialog->id,
|
||||
'dialog_type' => $dialog->type,
|
||||
'session_id' => $dialog->session_id,
|
||||
'dialog_name' => $dialog->getGroupName(),
|
||||
'user' => [
|
||||
'userid' => $user->userid,
|
||||
'email' => $user->email,
|
||||
'nickname' => $user->nickname,
|
||||
],
|
||||
], 10, [
|
||||
'dialog' => $dialog->id,
|
||||
'operator' => $user->userid,
|
||||
]);
|
||||
}
|
||||
}
|
||||
}
|
||||
return Base::retSuccess('success', $data);
|
||||
}
|
||||
|
||||
|
||||
@ -2150,7 +2150,8 @@ class UsersController extends AbstractController
|
||||
'users.nickname',
|
||||
'users.userimg',
|
||||
'user_bots.clear_day',
|
||||
'user_bots.webhook_url'
|
||||
'user_bots.webhook_url',
|
||||
'user_bots.webhook_events'
|
||||
])
|
||||
->orderByDesc('id')
|
||||
->get()
|
||||
@ -2160,6 +2161,7 @@ class UsersController extends AbstractController
|
||||
$bot['name'] = $bot['nickname'];
|
||||
$bot['avatar'] = $bot['userimg'];
|
||||
$bot['system_name'] = UserBot::systemBotName($bot['name']);
|
||||
$bot['webhook_events'] = UserBot::normalizeWebhookEvents($bot['webhook_events'] ?? null, empty($bot['webhook_events']));
|
||||
unset($bot['userid'], $bot['nickname'], $bot['userimg']);
|
||||
}
|
||||
|
||||
@ -2211,11 +2213,13 @@ class UsersController extends AbstractController
|
||||
'avatar' => $botUser->userimg,
|
||||
'clear_day' => 0,
|
||||
'webhook_url' => '',
|
||||
'webhook_events' => [UserBot::WEBHOOK_EVENT_MESSAGE],
|
||||
'system_name' => UserBot::systemBotName($botUser->email),
|
||||
];
|
||||
if ($userBot) {
|
||||
$data['clear_day'] = $userBot->clear_day;
|
||||
$data['webhook_url'] = $userBot->webhook_url;
|
||||
$data['webhook_events'] = $userBot->webhook_events;
|
||||
}
|
||||
return Base::retSuccess('success', $data);
|
||||
}
|
||||
@ -2296,6 +2300,9 @@ class UsersController extends AbstractController
|
||||
if (Arr::exists($data, 'webhook_url')) {
|
||||
$upBot['webhook_url'] = trim($data['webhook_url']);
|
||||
}
|
||||
if (Arr::exists($data, 'webhook_events')) {
|
||||
$upBot['webhook_events'] = UserBot::normalizeWebhookEvents($data['webhook_events'], false);
|
||||
}
|
||||
//
|
||||
if ($upUser) {
|
||||
$botUser->updateInstance($upUser);
|
||||
@ -2312,11 +2319,13 @@ class UsersController extends AbstractController
|
||||
'avatar' => $botUser->userimg,
|
||||
'clear_day' => 0,
|
||||
'webhook_url' => '',
|
||||
'webhook_events' => [UserBot::WEBHOOK_EVENT_MESSAGE],
|
||||
'system_name' => UserBot::systemBotName($botUser->email),
|
||||
];
|
||||
if ($userBot) {
|
||||
$data['clear_day'] = $userBot->clear_day;
|
||||
$data['webhook_url'] = $userBot->webhook_url;
|
||||
$data['webhook_events'] = $userBot->webhook_events;
|
||||
}
|
||||
return Base::retSuccess($botId ? '修改成功' : '添加成功', $data);
|
||||
}
|
||||
|
||||
@ -5,10 +5,12 @@ namespace App\Models;
|
||||
use App\Module\Base;
|
||||
use App\Module\Doo;
|
||||
use App\Module\Extranet;
|
||||
use App\Module\Ihttp;
|
||||
use App\Module\Timer;
|
||||
use App\Tasks\JokeSoupTask;
|
||||
use Cache;
|
||||
use Carbon\Carbon;
|
||||
use Throwable;
|
||||
|
||||
/**
|
||||
* App\Models\UserBot
|
||||
@ -20,6 +22,7 @@ use Carbon\Carbon;
|
||||
* @property \Illuminate\Support\Carbon|null $clear_at 下一次清理时间
|
||||
* @property string|null $webhook_url 消息webhook地址
|
||||
* @property int|null $webhook_num 消息webhook请求次数
|
||||
* @property array|null $webhook_events Webhook事件配置
|
||||
* @property \Illuminate\Support\Carbon|null $created_at
|
||||
* @property \Illuminate\Support\Carbon|null $updated_at
|
||||
* @method static \Illuminate\Database\Eloquent\Builder|AbstractModel cancelAppend()
|
||||
@ -44,6 +47,131 @@ use Carbon\Carbon;
|
||||
*/
|
||||
class UserBot extends AbstractModel
|
||||
{
|
||||
public const WEBHOOK_EVENT_MESSAGE = 'message';
|
||||
public const WEBHOOK_EVENT_DIALOG_OPEN = 'dialog_open';
|
||||
public const WEBHOOK_EVENT_MEMBER_JOIN = 'member_join';
|
||||
public const WEBHOOK_EVENT_MEMBER_LEAVE = 'member_leave';
|
||||
|
||||
protected $casts = [
|
||||
'webhook_events' => 'array',
|
||||
];
|
||||
|
||||
/**
|
||||
* 获取可选的 webhook 事件
|
||||
*
|
||||
* @return string[]
|
||||
*/
|
||||
public static function webhookEventOptions(): array
|
||||
{
|
||||
return [
|
||||
self::WEBHOOK_EVENT_MESSAGE,
|
||||
self::WEBHOOK_EVENT_DIALOG_OPEN,
|
||||
self::WEBHOOK_EVENT_MEMBER_JOIN,
|
||||
self::WEBHOOK_EVENT_MEMBER_LEAVE,
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* 标准化 webhook 事件配置
|
||||
*
|
||||
* @param mixed $events
|
||||
* @return array
|
||||
*/
|
||||
public static function normalizeWebhookEvents(mixed $events, bool $useFallback = true): array
|
||||
{
|
||||
if (is_string($events)) {
|
||||
$events = Base::json2array($events);
|
||||
}
|
||||
if ($events === null) {
|
||||
$events = [];
|
||||
}
|
||||
if (!is_array($events)) {
|
||||
$events = [$events];
|
||||
}
|
||||
$events = array_filter(array_map('strval', $events));
|
||||
$events = array_values(array_intersect($events, self::webhookEventOptions()));
|
||||
return $events ?: ($useFallback ? [self::WEBHOOK_EVENT_MESSAGE] : []);
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取 webhook 事件配置
|
||||
*
|
||||
* @param mixed $value
|
||||
* @return array
|
||||
*/
|
||||
public function getWebhookEventsAttribute(mixed $value): array
|
||||
{
|
||||
if ($value === null || $value === '') {
|
||||
return self::normalizeWebhookEvents(null, true);
|
||||
}
|
||||
return self::normalizeWebhookEvents($value, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* 设置 webhook 事件配置
|
||||
*
|
||||
* @param mixed $value
|
||||
* @return void
|
||||
*/
|
||||
public function setWebhookEventsAttribute(mixed $value): void
|
||||
{
|
||||
$useFallback = $value === null;
|
||||
$this->attributes['webhook_events'] = Base::array2json(self::normalizeWebhookEvents($value, $useFallback));
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断是否需要触发指定 webhook 事件
|
||||
*
|
||||
* @param string $event
|
||||
* @return bool
|
||||
*/
|
||||
public function shouldDispatchWebhook(string $event): bool
|
||||
{
|
||||
if (!$this->webhook_url) {
|
||||
return false;
|
||||
}
|
||||
if (!preg_match('/^https?:\/\//', $this->webhook_url)) {
|
||||
return false;
|
||||
}
|
||||
return in_array($event, $this->webhook_events ?? [], true);
|
||||
}
|
||||
|
||||
/**
|
||||
* 发送 webhook
|
||||
*
|
||||
* @param string $event
|
||||
* @param array $payload
|
||||
* @param int $timeout
|
||||
* @param array $context
|
||||
* @return array|null
|
||||
*/
|
||||
public function dispatchWebhook(string $event, array $payload, int $timeout = 30, array $context = []): ?array
|
||||
{
|
||||
if (!$this->shouldDispatchWebhook($event)) {
|
||||
return null;
|
||||
}
|
||||
|
||||
$payload = array_merge([
|
||||
'event' => $event,
|
||||
'timestamp' => time(),
|
||||
'bot_uid' => $this->bot_id,
|
||||
'owner_uid' => $this->userid,
|
||||
], $payload);
|
||||
|
||||
try {
|
||||
$result = Ihttp::ihttp_post($this->webhook_url, $payload, $timeout);
|
||||
$this->increment('webhook_num');
|
||||
return $result;
|
||||
} catch (Throwable $th) {
|
||||
info(Base::array2json(array_merge($context, [
|
||||
'bot_userid' => $this->bot_id,
|
||||
'event' => $event,
|
||||
'webhook_url' => $this->webhook_url,
|
||||
'error' => $th->getMessage(),
|
||||
])));
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 判断是否系统机器人
|
||||
|
||||
@ -461,7 +461,8 @@ class WebSocketDialog extends AbstractModel
|
||||
*/
|
||||
public function joinGroup($userid, $inviter, $important = null)
|
||||
{
|
||||
AbstractModel::transaction(function () use ($important, $inviter, $userid) {
|
||||
$addedUserIds = [];
|
||||
AbstractModel::transaction(function () use ($important, $inviter, $userid, &$addedUserIds) {
|
||||
foreach (is_array($userid) ? $userid : [$userid] as $value) {
|
||||
if ($value > 0) {
|
||||
$updateData = [
|
||||
@ -480,6 +481,7 @@ class WebSocketDialog extends AbstractModel
|
||||
]);
|
||||
}, $isInsert);
|
||||
if ($isInsert) {
|
||||
$addedUserIds[] = $value;
|
||||
WebSocketDialogMsg::sendMsg(null, $this->id, 'notice', [
|
||||
'notice' => User::userid2nickname($value) . " 已加入群组"
|
||||
], $inviter, true, true);
|
||||
@ -490,6 +492,16 @@ class WebSocketDialog extends AbstractModel
|
||||
$data = WebSocketDialog::generatePeople($this->id);
|
||||
$data['id'] = $this->id;
|
||||
$this->pushMsg("groupUpdate", $data);
|
||||
if ($addedUserIds) {
|
||||
$meta = ['action' => 'join'];
|
||||
if ($inviter > 0) {
|
||||
$actor = $this->getUserSnapshots([$inviter]);
|
||||
if (!empty($actor)) {
|
||||
$meta['actor'] = $actor[0];
|
||||
}
|
||||
}
|
||||
$this->dispatchMemberWebhook(UserBot::WEBHOOK_EVENT_MEMBER_JOIN, $addedUserIds, $meta);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -503,14 +515,15 @@ class WebSocketDialog extends AbstractModel
|
||||
public function exitGroup($userid, $type = 'exit', $checkDelete = true, $pushMsg = true)
|
||||
{
|
||||
$typeDesc = $type === 'remove' ? '移出' : '退出';
|
||||
AbstractModel::transaction(function () use ($pushMsg, $checkDelete, $typeDesc, $type, $userid) {
|
||||
$removedUserIds = [];
|
||||
AbstractModel::transaction(function () use ($pushMsg, $checkDelete, $typeDesc, $type, $userid, &$removedUserIds) {
|
||||
$builder = WebSocketDialogUser::whereDialogId($this->id);
|
||||
if (is_array($userid)) {
|
||||
$builder->whereIn('userid', $userid);
|
||||
} else {
|
||||
$builder->whereUserid($userid);
|
||||
}
|
||||
$builder->chunkById(100, function($list) use ($pushMsg, $checkDelete, $typeDesc, $type) {
|
||||
$builder->chunkById(100, function($list) use ($pushMsg, $checkDelete, $typeDesc, $type, &$removedUserIds) {
|
||||
/** @var WebSocketDialogUser $item */
|
||||
foreach ($list as $item) {
|
||||
if ($checkDelete) {
|
||||
@ -531,6 +544,7 @@ class WebSocketDialog extends AbstractModel
|
||||
}
|
||||
//
|
||||
$item->delete();
|
||||
$removedUserIds[] = $item->userid;
|
||||
//
|
||||
if ($pushMsg) {
|
||||
if ($type === 'remove') {
|
||||
@ -549,6 +563,87 @@ class WebSocketDialog extends AbstractModel
|
||||
$data = WebSocketDialog::generatePeople($this->id);
|
||||
$data['id'] = $this->id;
|
||||
$this->pushMsg("groupUpdate", $data);
|
||||
if ($removedUserIds) {
|
||||
$meta = ['action' => $type];
|
||||
$operatorId = User::userid();
|
||||
if ($operatorId > 0) {
|
||||
$actor = $this->getUserSnapshots([$operatorId]);
|
||||
if (!empty($actor)) {
|
||||
$meta['actor'] = $actor[0];
|
||||
}
|
||||
}
|
||||
$this->dispatchMemberWebhook(UserBot::WEBHOOK_EVENT_MEMBER_LEAVE, $removedUserIds, $meta);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 获取用户快照
|
||||
* @param array $userIds
|
||||
* @return array
|
||||
*/
|
||||
protected function getUserSnapshots(array $userIds): array
|
||||
{
|
||||
$userIds = array_values(array_unique(array_filter($userIds)));
|
||||
if (empty($userIds)) {
|
||||
return [];
|
||||
}
|
||||
return User::whereIn('userid', $userIds)
|
||||
->get(['userid', 'nickname', 'email', 'bot'])
|
||||
->map(function (User $user) {
|
||||
return [
|
||||
'userid' => $user->userid,
|
||||
'nickname' => $user->nickname,
|
||||
'email' => $user->email,
|
||||
'is_bot' => (bool)$user->bot,
|
||||
];
|
||||
})
|
||||
->values()
|
||||
->all();
|
||||
}
|
||||
|
||||
/**
|
||||
* 推送成员事件到机器人 webhook
|
||||
* @param string $event
|
||||
* @param array $memberIds
|
||||
* @param array $meta
|
||||
* @return void
|
||||
*/
|
||||
protected function dispatchMemberWebhook(string $event, array $memberIds, array $meta = []): void
|
||||
{
|
||||
$memberIds = array_values(array_unique(array_filter($memberIds)));
|
||||
if (empty($memberIds)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$botIds = $this->dialogUser()->where('bot', 1)->pluck('userid')->toArray();
|
||||
if (empty($botIds)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$userBots = UserBot::whereIn('bot_id', $botIds)->get();
|
||||
if ($userBots->isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
$members = $this->getUserSnapshots($memberIds);
|
||||
if (empty($members)) {
|
||||
return;
|
||||
}
|
||||
|
||||
$payload = array_merge([
|
||||
'dialog_id' => $this->id,
|
||||
'dialog_type' => $this->type,
|
||||
'group_type' => $this->group_type,
|
||||
'dialog_name' => $this->getGroupName(),
|
||||
'members' => $members,
|
||||
], array_filter($meta, fn ($value) => $value !== null));
|
||||
|
||||
foreach ($userBots as $userBot) {
|
||||
$userBot->dispatchWebhook($event, $payload, 10, [
|
||||
'dialog' => $this->id,
|
||||
'event_members' => $memberIds,
|
||||
]);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@ -427,6 +427,7 @@ class BotReceiveMsgTask extends AbstractTask
|
||||
private function handleWebhookRequest($sendText, $replyText, WebSocketDialogMsg $msg, WebSocketDialog $dialog, User $botUser)
|
||||
{
|
||||
$webhookUrl = null;
|
||||
$userBot = null;
|
||||
$extras = ['timestamp' => time()];
|
||||
|
||||
try {
|
||||
@ -530,13 +531,11 @@ class BotReceiveMsgTask extends AbstractTask
|
||||
return;
|
||||
}
|
||||
$userBot = UserBot::whereBotId($botUser->userid)->first();
|
||||
if ($userBot) {
|
||||
$userBot->webhook_num++;
|
||||
$userBot->save();
|
||||
$webhookUrl = $userBot->webhook_url;
|
||||
if (!$userBot || !$userBot->shouldDispatchWebhook(UserBot::WEBHOOK_EVENT_MESSAGE)) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
if (!preg_match("/^https?:\/\//", $webhookUrl)) {
|
||||
if (!$userBot && !preg_match("/^https?:\/\//", $webhookUrl)) {
|
||||
return;
|
||||
}
|
||||
} catch (\Exception $e) {
|
||||
@ -547,50 +546,60 @@ class BotReceiveMsgTask extends AbstractTask
|
||||
return;
|
||||
}
|
||||
//
|
||||
try {
|
||||
$data = [
|
||||
'text' => $sendText,
|
||||
'reply_text' => $replyText,
|
||||
'token' => User::generateToken($botUser),
|
||||
'session_id' => $dialog->session_id,
|
||||
'dialog_id' => $dialog->id,
|
||||
'dialog_type' => $dialog->type,
|
||||
'msg_id' => $msg->id,
|
||||
'msg_uid' => $msg->userid,
|
||||
'mention' => $this->mention ? 1 : 0,
|
||||
'bot_uid' => $botUser->userid,
|
||||
'version' => Base::getVersion(),
|
||||
'extras' => Base::array2json($extras)
|
||||
$data = [
|
||||
'text' => $sendText,
|
||||
'reply_text' => $replyText,
|
||||
'token' => User::generateToken($botUser),
|
||||
'session_id' => $dialog->session_id,
|
||||
'dialog_id' => $dialog->id,
|
||||
'dialog_type' => $dialog->type,
|
||||
'msg_id' => $msg->id,
|
||||
'msg_uid' => $msg->userid,
|
||||
'mention' => $this->mention ? 1 : 0,
|
||||
'bot_uid' => $botUser->userid,
|
||||
'version' => Base::getVersion(),
|
||||
'extras' => Base::array2json($extras)
|
||||
];
|
||||
// 添加用户信息
|
||||
$userInfo = User::find($msg->userid);
|
||||
if ($userInfo) {
|
||||
$data['msg_user'] = [
|
||||
'userid' => $userInfo->userid,
|
||||
'email' => $userInfo->email,
|
||||
'nickname' => $userInfo->nickname,
|
||||
'profession' => $userInfo->profession,
|
||||
'lang' => $userInfo->lang,
|
||||
'token' => User::generateTokenNoDevice($userInfo, now()->addHour()),
|
||||
];
|
||||
// 添加用户信息
|
||||
$userInfo = User::find($msg->userid);
|
||||
if ($userInfo) {
|
||||
$data['msg_user'] = [
|
||||
'userid' => $userInfo->userid,
|
||||
'email' => $userInfo->email,
|
||||
'nickname' => $userInfo->nickname,
|
||||
'profession' => $userInfo->profession,
|
||||
'lang' => $userInfo->lang,
|
||||
'token' => User::generateTokenNoDevice($userInfo, now()->addHour()),
|
||||
];
|
||||
}
|
||||
// 请求Webhook
|
||||
$result = Ihttp::ihttp_post($webhookUrl, $data, 30);
|
||||
if ($result['data'] && $data = Base::json2array($result['data'])) {
|
||||
if ($data['code'] != 200 && $data['message']) {
|
||||
WebSocketDialogMsg::sendMsg(null, $msg->dialog_id, 'text', [
|
||||
'text' => $result['data']['message']
|
||||
], $botUser->userid, false, false, true);
|
||||
}
|
||||
}
|
||||
} catch (\Throwable $th) {
|
||||
info(Base::array2json([
|
||||
'bot_userid' => $botUser->userid,
|
||||
}
|
||||
|
||||
$result = null;
|
||||
if ($userBot) {
|
||||
$result = $userBot->dispatchWebhook(UserBot::WEBHOOK_EVENT_MESSAGE, $data, 30, [
|
||||
'dialog' => $dialog->id,
|
||||
'msg' => $msg->id,
|
||||
'webhook_url' => $webhookUrl,
|
||||
'error' => $th->getMessage(),
|
||||
]));
|
||||
]);
|
||||
} else {
|
||||
try {
|
||||
$result = Ihttp::ihttp_post($webhookUrl, $data, 30);
|
||||
} catch (\Throwable $th) {
|
||||
info(Base::array2json([
|
||||
'bot_userid' => $botUser->userid,
|
||||
'dialog' => $dialog->id,
|
||||
'msg' => $msg->id,
|
||||
'webhook_url' => $webhookUrl,
|
||||
'error' => $th->getMessage(),
|
||||
]));
|
||||
}
|
||||
}
|
||||
|
||||
if ($result && isset($result['data'])) {
|
||||
$responseData = Base::json2array($result['data']);
|
||||
if (($responseData['code'] ?? 0) != 200 && !empty($responseData['message'])) {
|
||||
WebSocketDialogMsg::sendMsg(null, $msg->dialog_id, 'text', [
|
||||
'text' => $responseData['message']
|
||||
], $botUser->userid, false, false, true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@ -0,0 +1,39 @@
|
||||
<?php
|
||||
|
||||
use Illuminate\\Database\\Migrations\\Migration;
|
||||
use Illuminate\\Database\\Schema\\Blueprint;
|
||||
use Illuminate\\Support\\Facades\\DB;
|
||||
use Illuminate\\Support\\Facades\\Schema;
|
||||
|
||||
return new class extends Migration
|
||||
{
|
||||
/**
|
||||
* Run the migrations.
|
||||
*/
|
||||
public function up(): void
|
||||
{
|
||||
Schema::table('user_bots', function (Blueprint $table) {
|
||||
if (!Schema::hasColumn('user_bots', 'webhook_events')) {
|
||||
$table->text('webhook_events')->nullable()->after('webhook_num')->comment('Webhook事件配置');
|
||||
}
|
||||
});
|
||||
|
||||
DB::table('user_bots')
|
||||
->where(function ($query) {
|
||||
$query->whereNull('webhook_events')->orWhere('webhook_events', '');
|
||||
})
|
||||
->update(['webhook_events' => json_encode(['message'])]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Reverse the migrations.
|
||||
*/
|
||||
public function down(): void
|
||||
{
|
||||
Schema::table('user_bots', function (Blueprint $table) {
|
||||
if (Schema::hasColumn('user_bots', 'webhook_events')) {
|
||||
$table->dropColumn('webhook_events');
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
@ -106,6 +106,7 @@
|
||||
<p><span>ID:</span>{{ item.id }}</p>
|
||||
<p><span>{{ $L('清理时间') }}:</span>{{ item.clear_day }}</p>
|
||||
<p><span>Webhook:</span>{{ item.webhook_url || '-' }}</p>
|
||||
<p><span>{{ $L('Webhook事件') }}:</span>{{ formatWebhookEvents(item.webhook_events) }}</p>
|
||||
</div>
|
||||
<div class="modal-item-btns">
|
||||
<Button icon="md-chatbubbles" @click="applyClick({value: 'mybot-chat'}, item)">{{ $L('开始聊天') }}</Button>
|
||||
@ -140,6 +141,13 @@
|
||||
<FormItem prop="webhook_url" label="Webhook">
|
||||
<Input v-model="mybotModifyData.webhook_url" :maxlength="255" :show-word-limit="0.9" type="textarea" placeholder="Webhook"/>
|
||||
</FormItem>
|
||||
<FormItem prop="webhook_events" :label="$L('Webhook事件')">
|
||||
<CheckboxGroup v-model="mybotModifyData.webhook_events">
|
||||
<Checkbox v-for="option in webhookEventOptions" :key="option.value" :label="option.value">
|
||||
{{ $L(option.label) }}
|
||||
</Checkbox>
|
||||
</CheckboxGroup>
|
||||
</FormItem>
|
||||
</Form>
|
||||
<div slot="footer" class="adaption">
|
||||
<Button type="default" @click="mybotModifyShow=false">{{ $L('取消') }}</Button>
|
||||
@ -363,6 +371,12 @@ export default {
|
||||
mybotModifyShow: false,
|
||||
mybotModifyData: {},
|
||||
mybotModifyLoad: 0,
|
||||
webhookEventOptions: [
|
||||
{value: 'message', label: '接收消息'},
|
||||
{value: 'dialog_open', label: '打开会话'},
|
||||
{value: 'member_join', label: '成员加入'},
|
||||
{value: 'member_leave', label: '成员退出'},
|
||||
],
|
||||
//
|
||||
aibotShow: false,
|
||||
aibotList: AIBotList,
|
||||
@ -456,6 +470,37 @@ export default {
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
normalizeWebhookEvents(events = [], useFallback = false) {
|
||||
if (!Array.isArray(events)) {
|
||||
events = events ? [events] : [];
|
||||
}
|
||||
const allowed = this.webhookEventOptions.map(item => item.value);
|
||||
const result = events.filter(item => allowed.includes(item));
|
||||
if (result.length) {
|
||||
return Array.from(new Set(result));
|
||||
}
|
||||
return useFallback ? ['message'] : [];
|
||||
},
|
||||
enhanceMybotItem(item = {}) {
|
||||
const data = $A.cloneJSON(item || {});
|
||||
let events = data.webhook_events;
|
||||
if (typeof events === 'undefined' || events === null) {
|
||||
events = ['message'];
|
||||
}
|
||||
events = this.normalizeWebhookEvents(events, false);
|
||||
if (!events.length) {
|
||||
events = [];
|
||||
}
|
||||
data.webhook_events = events;
|
||||
return data;
|
||||
},
|
||||
formatWebhookEvents(events) {
|
||||
const values = this.normalizeWebhookEvents(events, false);
|
||||
const labels = this.webhookEventOptions
|
||||
.filter(option => values.includes(option.value))
|
||||
.map(option => this.$L(option.label));
|
||||
return labels.length ? labels.join('、') : '-';
|
||||
},
|
||||
getLogoClass(name) {
|
||||
name = name.replace(/([a-z])([A-Z])/g, '$1-$2').toLowerCase();
|
||||
return name
|
||||
@ -548,7 +593,7 @@ export default {
|
||||
this.$store.dispatch("call", {
|
||||
url: 'users/bot/list',
|
||||
}).then(({data}) => {
|
||||
this.mybotList = data.list;
|
||||
this.mybotList = (data.list || []).map(item => this.enhanceMybotItem(item));
|
||||
}).finally(_ => {
|
||||
this.mybotLoad--
|
||||
});
|
||||
@ -561,7 +606,7 @@ export default {
|
||||
},
|
||||
// 添加修改我的机器人
|
||||
addMybot(info) {
|
||||
this.mybotModifyData = $A.cloneJSON(info)
|
||||
this.mybotModifyData = this.enhanceMybotItem(info)
|
||||
this.mybotModifyShow = true;
|
||||
},
|
||||
// 删除我的机器人
|
||||
@ -600,11 +645,12 @@ export default {
|
||||
onMybotModify() {
|
||||
this.mybotModifyLoad++
|
||||
this.$store.dispatch("editUserBot", this.mybotModifyData).then(({data, msg}) => {
|
||||
const index = this.mybotList.findIndex(item => item.id === data.id);
|
||||
const botData = this.enhanceMybotItem(data);
|
||||
const index = this.mybotList.findIndex(item => item.id === botData.id);
|
||||
if (index > -1) {
|
||||
this.mybotList.splice(index, 1, data);
|
||||
this.mybotList.splice(index, 1, botData);
|
||||
} else {
|
||||
this.mybotList.unshift(data);
|
||||
this.mybotList.unshift(botData);
|
||||
}
|
||||
this.mybotModifyShow = false;
|
||||
this.mybotModifyData = {};
|
||||
|
||||
@ -462,6 +462,13 @@
|
||||
<FormItem v-if="typeof modifyData.webhook_url !== 'undefined'" prop="webhook_url" label="Webhook">
|
||||
<Input v-model="modifyData.webhook_url" :maxlength="255" />
|
||||
</FormItem>
|
||||
<FormItem v-if="typeof modifyData.webhook_events !== 'undefined'" prop="webhook_events" :label="$L('Webhook事件')">
|
||||
<CheckboxGroup v-model="modifyData.webhook_events">
|
||||
<Checkbox v-for="option in webhookEventOptions" :key="option.value" :label="option.value">
|
||||
{{$L(option.label)}}
|
||||
</Checkbox>
|
||||
</CheckboxGroup>
|
||||
</FormItem>
|
||||
</template>
|
||||
</Form>
|
||||
<div slot="footer" class="adaption">
|
||||
@ -768,6 +775,12 @@ export default {
|
||||
modifyAiShow: false,
|
||||
modifyData: {},
|
||||
modifyLoad: 0,
|
||||
webhookEventOptions: [
|
||||
{value: 'message', label: '接收消息'},
|
||||
{value: 'dialog_open', label: '打开会话'},
|
||||
{value: 'member_join', label: '成员加入'},
|
||||
{value: 'member_leave', label: '成员退出'},
|
||||
],
|
||||
|
||||
openId: 0,
|
||||
errorId: 0,
|
||||
@ -1449,6 +1462,28 @@ export default {
|
||||
|
||||
methods: {
|
||||
transformEmojiToHtml,
|
||||
normalizeWebhookEvents(events = [], useFallback = false) {
|
||||
if (!Array.isArray(events)) {
|
||||
events = events ? [events] : [];
|
||||
}
|
||||
const allowed = this.webhookEventOptions.map(item => item.value);
|
||||
const result = events.filter(item => allowed.includes(item));
|
||||
if (result.length) {
|
||||
return Array.from(new Set(result));
|
||||
}
|
||||
return useFallback ? ['message'] : [];
|
||||
},
|
||||
prepareWebhookEvents(events, useFallback = false) {
|
||||
let value = events;
|
||||
if (typeof value === 'undefined' || value === null) {
|
||||
value = useFallback ? ['message'] : [];
|
||||
}
|
||||
value = this.normalizeWebhookEvents(value, false);
|
||||
if (!value.length && useFallback) {
|
||||
return ['message'];
|
||||
}
|
||||
return value;
|
||||
},
|
||||
/**
|
||||
* 获取会话基本信息
|
||||
* @param dialog_id
|
||||
@ -2727,6 +2762,7 @@ export default {
|
||||
clear_day: 0,
|
||||
webhook_url: '',
|
||||
system_name: '',
|
||||
webhook_events: this.prepareWebhookEvents([], true),
|
||||
})
|
||||
this.modifyLoad++;
|
||||
this.$store.dispatch("call", {
|
||||
@ -2738,6 +2774,7 @@ export default {
|
||||
this.modifyData.clear_day = data.clear_day
|
||||
this.modifyData.webhook_url = data.webhook_url
|
||||
this.modifyData.system_name = data.system_name
|
||||
this.modifyData.webhook_events = this.prepareWebhookEvents(data.webhook_events, true)
|
||||
}).finally(() => {
|
||||
this.modifyLoad--;
|
||||
})
|
||||
@ -2892,6 +2929,7 @@ export default {
|
||||
name: this.modifyData.name,
|
||||
clear_day: this.modifyData.clear_day,
|
||||
webhook_url: this.modifyData.webhook_url,
|
||||
webhook_events: this.normalizeWebhookEvents(this.modifyData.webhook_events, false),
|
||||
dialog_id: this.modifyData.dialog_id
|
||||
}).then(({msg}) => {
|
||||
$A.messageSuccess(msg);
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user