diff --git a/app/Http/Controllers/Api/SystemController.php b/app/Http/Controllers/Api/SystemController.php
index 9217da61e..2611ef6bb 100755
--- a/app/Http/Controllers/Api/SystemController.php
+++ b/app/Http/Controllers/Api/SystemController.php
@@ -156,6 +156,7 @@ class SystemController extends AbstractController
$setting['unclaimed_task_reminder_time'] = $setting['unclaimed_task_reminder_time'] ?: '';
$setting['task_ai_auto_analyze'] = $setting['task_ai_auto_analyze'] ?: 'open';
$setting['department_owner_project_view'] = $setting['department_owner_project_view'] ?: 'open';
+ $setting['app_ai_hidden'] = config('dootask.app_ai_hidden');
$setting['server_timezone'] = config('app.timezone');
$setting['server_version'] = Base::getVersion();
// 指定人员名单仅管理员可见
diff --git a/config/dootask.php b/config/dootask.php
index 80e0f3188..37f7d4a65 100644
--- a/config/dootask.php
+++ b/config/dootask.php
@@ -8,6 +8,9 @@ return [
// 许可证显示开关:设为 'hidden' 时隐藏系统许可证信息(Doo::license)
'system_license' => env('SYSTEM_LICENSE'),
+ // 移动 APP AI 界面开关:设为 true 时仅在移动 APP 隐藏 AI 相关界面
+ 'app_ai_hidden' => filter_var(env('APP_AI_HIDDEN', false), FILTER_VALIDATE_BOOLEAN),
+
// 演示账号:登录页展示的演示账号(SystemController::demo)
'demo_account' => env('DEMO_ACCOUNT'),
diff --git a/resources/ai-kb/zh/concept/mobile-client/feature-diff.md b/resources/ai-kb/zh/concept/mobile-client/feature-diff.md
index e69b6731e..00f17a310 100644
--- a/resources/ai-kb/zh/concept/mobile-client/feature-diff.md
+++ b/resources/ai-kb/zh/concept/mobile-client/feature-diff.md
@@ -19,7 +19,8 @@ negative:
- 移动端缺失的复杂功能不会硬塞,大屏复杂操作仍建议在桌面端完成
- 桌面端独有的能力(截图、全局快捷键、托盘)由原生 OS 集成,移动端无对应概念
- 微应用 / 插件部分能在移动端打开(走 WebView),但触屏不一定可用
-last_verified: v1.7.90
+ - 部署环境可通过 APP_AI_HIDDEN=true 隐藏移动 APP 的 AI 界面,但不会关闭 Web、Electron 或服务端 AI 接口
+last_verified: v1.9.18
---
# 移动端与桌面端功能差异
@@ -31,7 +32,7 @@ last_verified: v1.7.90
- 项目(成员、视图基本浏览)
- 文件(上传、下载、预览)
- 通知与日程
-- AI 助手(基础对话)
+- AI 助手(基础对话;部署环境未隐藏移动 APP AI 界面时)
## 移动端独有
- 底部 Tabbar 原生导航
@@ -61,6 +62,9 @@ last_verified: v1.7.90
| 报表 / 仪表盘 | 完整图表 + 编辑 | 仅查看 |
| 会议 | 创建 / 主持 / 屏幕共享 | 主要参会,部分高级功能受限 |
+## AI 界面部署开关
+部署管理员可设置 `APP_AI_HIDDEN=true`,仅在 iOS / Android APP 隐藏 AI 助手、AI 微应用、AI 生成与分析入口,以及邮箱符合 `ai-*@bot.system` 的 AI 机器人单聊入口。任务、项目或普通群聊中已有的 AI 消息仍会显示并正常通知;Web 和 Electron 客户端不受影响,该配置也不会禁用服务端 AI 接口或删除会话、消息。
+
## 选哪端做什么
- **创建复杂任务 / 编辑长文档** → 桌面端
- **快速回消息 / 收推送 / 移动审批** → 移动端
diff --git a/resources/assets/js/App.vue b/resources/assets/js/App.vue
index a73ea076b..5bd02fde9 100755
--- a/resources/assets/js/App.vue
+++ b/resources/assets/js/App.vue
@@ -42,7 +42,7 @@
-
+
@@ -100,7 +100,7 @@ import MobileNotification from "./components/Mobile/Notification.vue";
import MobileBack from "./components/Mobile/Back.vue";
import DropdownMenu from "./components/DropdownMenu";
import {ctrlPressed} from "./mixins/ctrlPressed";
-import {mapState} from "vuex";
+import {mapGetters, mapState} from "vuex";
import emitter from "./store/events";
import AIAssistant from "./components/AIAssistant";
import UserDetail from "./pages/manage/components/UserDetail.vue";
@@ -152,6 +152,8 @@ export default {
},
computed: {
+ ...mapGetters(['aiVisible']),
+
...mapState(['ws', 'themeConf', 'windowOrientation', 'safeAreaSize', 'isFirstPage', 'mobileTabbar', 'themeName']),
statusColor({routeName, windowLandscape}) {
diff --git a/resources/assets/js/components/AIAssistant/float-button.vue b/resources/assets/js/components/AIAssistant/float-button.vue
index 7e0950299..e980eb264 100644
--- a/resources/assets/js/components/AIAssistant/float-button.vue
+++ b/resources/assets/js/components/AIAssistant/float-button.vue
@@ -24,7 +24,7 @@
\ No newline at end of file
+
diff --git a/resources/assets/js/pages/manage/messenger.vue b/resources/assets/js/pages/manage/messenger.vue
index d640f5d60..a75650240 100644
--- a/resources/assets/js/pages/manage/messenger.vue
+++ b/resources/assets/js/pages/manage/messenger.vue
@@ -380,7 +380,12 @@ export default {
'longpressData'
]),
- ...mapGetters(['getDialogDraft', 'tagDialogDraft']),
+ ...mapGetters([
+ 'appAiHidden',
+ 'getDialogDraft',
+ 'tagDialogDraft',
+ 'visibleDialogs',
+ ]),
contactAvatarSize() {
return this.windowPortrait ? 36 : 30
@@ -389,19 +394,19 @@ export default {
dialogList() {
const {dialogActive, dialogSearchKey, dialogSearchList} = this
if (dialogSearchList.length > 0) {
- return dialogSearchList.sort((a, b) => {
+ return dialogSearchList.filter(dialog => !this.appAiHidden || !$A.isAiBotDialog(dialog)).sort((a, b) => {
// 搜索结果排在后面
return (a.is_search === true ? 1 : 0) - (b.is_search === true ? 1 : 0)
})
}
if (dialogActive == '' && dialogSearchKey == '') {
- return this.cacheDialogs.filter(dialog => this.filterDialog(dialog)).sort(this.dialogSort);
+ return this.visibleDialogs.filter(dialog => this.filterDialog(dialog)).sort(this.dialogSort);
}
if (dialogActive == 'mark' && !dialogSearchKey) {
const lists = [];
this.dialogMsgs.filter(h => h.tag).forEach(h => {
let dialog = $A.cloneJSON(this.cacheDialogs).find(p => p.id == h.dialog_id)
- if (dialog) {
+ if (dialog && (!this.appAiHidden || !$A.isAiBotDialog(dialog))) {
dialog.last_msg = h;
dialog.search_msg_id = h.id;
lists.push(dialog);
@@ -409,7 +414,7 @@ export default {
});
return lists;
}
- const list = this.cacheDialogs.filter(dialog => {
+ const list = this.visibleDialogs.filter(dialog => {
if (!this.filterDialog(dialog)) {
return false;
}
@@ -508,7 +513,7 @@ export default {
msgUnread() {
return function (type) {
let num = 0
- this.cacheDialogs.some((dialog) => {
+ this.visibleDialogs.some((dialog) => {
switch (type) {
case 'project':
case 'task':
@@ -839,6 +844,9 @@ export default {
},
filterDialog(dialog) {
+ if (this.appAiHidden && $A.isAiBotDialog(dialog)) {
+ return false
+ }
if ((dialog.id > 0 && dialog.id == this.dialogId) || dialog.top_at || dialog.todo_num > 0 || $A.getDialogNum(dialog) > 0) {
return true
}
diff --git a/resources/assets/js/pages/manage/setting/components/SystemSetting.vue b/resources/assets/js/pages/manage/setting/components/SystemSetting.vue
index a083777e5..c7f6bf522 100644
--- a/resources/assets/js/pages/manage/setting/components/SystemSetting.vue
+++ b/resources/assets/js/pages/manage/setting/components/SystemSetting.vue
@@ -158,7 +158,7 @@
:placeholder="$L('请选择提醒时间')"
transfer/>
-
+
{{$L('开启')}}
{{$L('关闭')}}
@@ -354,7 +354,7 @@