From 621d4c82af768f64824505a0cd00abc25bcb71e5 Mon Sep 17 00:00:00 2001 From: ZyGuo Date: Wed, 10 Jun 2026 09:18:38 +0800 Subject: [PATCH 1/2] chore: apik --- offline-backend-20260512/backend/config.yaml | 66 ++++++++++---------- 1 file changed, 34 insertions(+), 32 deletions(-) diff --git a/offline-backend-20260512/backend/config.yaml b/offline-backend-20260512/backend/config.yaml index 152ebfb2..ba4e5c20 100644 --- a/offline-backend-20260512/backend/config.yaml +++ b/offline-backend-20260512/backend/config.yaml @@ -14,7 +14,7 @@ models: display_name: DeepSeek Chat use: langchain_openai:ChatOpenAI model: deepseek-chat - api_key: sk-e1c22b7931dc446f8b67e57878edd105 + api_key: sk-386b6ab4ce7146588bf69e4e70d2de99 base_url: https://api.deepseek.com request_timeout: 600.0 max_retries: 2 @@ -94,7 +94,7 @@ models: display_name: Qwen/Qwen3.6-27B use: langchain_openai:ChatOpenAI model: Qwen/Qwen3.6-27B - api_key: sk-ighylafootabtuthwueirmoycccyqtdgbifyhozduvolkdyt + api_key: sk-ighylafootabtuthwueirmoycccyqtdgbifyhozduvolkdyt base_url: https://api.siliconflow.cn/v1/ max_tokens: 4096 temperature: 1.0 @@ -202,31 +202,30 @@ auth_login: # 口令不对直接 401。password 留空则默认口令为 123ewq。仅作用于用户名直登。 username_login: require_password: false - password: "" + password: '' # token 换登录:前端用 ?authToken=上游token 进入,后端调用 token_info_url # (把该 token 直接拼成 Authorization: Bearer 头)换出用户名,再登录; # 用户名不在库里时自动注册。 token_login: enabled: false - token_info_url: "https://ch1.b.uat.4.cn/consumer/login/getTokenInfo" + token_info_url: 'https://ch1.b.uat.4.cn/consumer/login/getTokenInfo' # 已弃用:鉴权头现由前端传入的 token 拼成 "Bearer ",此项不再生效,保留仅兼容。 - service_authorization: "Bearer admin" + service_authorization: 'Bearer admin' timeout_seconds: 10 # 上游是 HTTPS。UAT/内网常用自签或私有 CA 证书,默认 verify=true 会握手失败导致 # 永远 401。此处 uat 域名按自签处理,先关校验;生产请置 true 或配 ca_cert_path。 verify_ssl: false - ca_cert_path: "" # 可选:PEM 格式 CA 包路径,设置后优先生效并启用校验 + ca_cert_path: '' # 可选:PEM 格式 CA 包路径,设置后优先生效并启用校验 # 日志系统入口(仅管理员可见):右下角「设置」菜单中会多出一个「日志系统」入口, # 点击后在新标签页打开下面的 url。enabled 关掉则不显示该入口。 - database: backend: sqlite sqlite_dir: .deer-flow/data - pool_size: 20 # 基础连接池(postgres/mysql 生效;sqlite 忽略) - max_overflow: 20 # 高峰期可临时超出 pool_size 的额外连接数,真实上限 = pool_size + max_overflow - pool_timeout: 30 # 池满时等待空闲连接的秒数,超时报错 + pool_size: 20 # 基础连接池(postgres/mysql 生效;sqlite 忽略) + max_overflow: 20 # 高峰期可临时超出 pool_size 的额外连接数,真实上限 = pool_size + max_overflow + pool_timeout: 30 # 池满时等待空闲连接的秒数,超时报错 echo_sql: false checkpointer: @@ -238,35 +237,38 @@ checkpointer: # users/{user_id}/memory_config.json > .deer-flow/memory_user_overrides.json > 此处 memory: enabled: true - version: v1 # 记忆版本: 'v1'(原版 DeerFlow, memory.json + LLM 自动提取) - # 'v2'(USER.md/MEMORY.md + 可选 Hindsight) - provider: hindsight # 'builtin' | 'hindsight'(外部 provider 名) - # builtin 始终启用,这里只决定 external 选哪个 - # (version=v1 时此字段忽略) + version: + v1 # 记忆版本: 'v1'(原版 DeerFlow, memory.json + LLM 自动提取) + # 'v2'(USER.md/MEMORY.md + 可选 Hindsight) + provider: + hindsight # 'builtin' | 'hindsight'(外部 provider 名) + # builtin 始终启用,这里只决定 external 选哪个 + # (version=v1 时此字段忽略) # V1 专属配置 —— version=v1 时生效 v1: - max_facts: 100 # 最多保留的事实条数,超出时驱逐最低置信度的事实 + max_facts: 100 # 最多保留的事实条数,超出时驱逐最低置信度的事实 fact_confidence_threshold: 0.7 # 事实置信度阈值,低于此值不保存 - debounce_seconds: 30 # 对话结束后延迟多少秒才触发 LLM 提取 - model_name: "" # 用于事实提取的 LLM 模型名;空则继承全局默认模型 - token_budget: 2000 # 注入系统提示词的 token 预算 + debounce_seconds: 30 # 对话结束后延迟多少秒才触发 LLM 提取 + model_name: '' # 用于事实提取的 LLM 模型名;空则继承全局默认模型 + token_budget: 2000 # 注入系统提示词的 token 预算 builtin: enabled: true memory_char_limit: 2200 user_char_limit: 1375 deduplicate_on_load: true - hindsight: # provider=hindsight 时生效,需另行部署 Hindsight 服务 - mode: local_external # 'cloud' | 'local_embedded' | 'local_external' + hindsight: # provider=hindsight 时生效,需另行部署 Hindsight 服务 + mode: local_external # 'cloud' | 'local_embedded' | 'local_external' api_url: http://47.88.25.99:18888 - api_key: "" # 部署 Hindsight 后填,或改成 $HINDSIGHT_API_KEY 并设同名环境变量 - # 注意:写成 $VAR 但环境变量未设置会导致配置加载失败 - bank_id_template: "deerflow-user-{user_id}" - work_bank_id_template: "deerflow-work-{user_id}-{agent_id}" + api_key: + '' # 部署 Hindsight 后填,或改成 $HINDSIGHT_API_KEY 并设同名环境变量 + # 注意:写成 $VAR 但环境变量未设置会导致配置加载失败 + bank_id_template: 'deerflow-user-{user_id}' + work_bank_id_template: 'deerflow-work-{user_id}-{agent_id}' memory_mode: context # 'context' | 'tools' | 'hybrid' - bank_mission: "你是一个中文记忆助手,负责从对话中提炼和存储重要信息。所有记忆内容必须使用中文记录。" - bank_retain_mission: "请从以下对话中提炼重要信息,包括用户的偏好、需求、背景知识和关键事实。所有提炼的内容必须用中文表达。" + bank_mission: '你是一个中文记忆助手,负责从对话中提炼和存储重要信息。所有记忆内容必须使用中文记录。' + bank_retain_mission: '请从以下对话中提炼重要信息,包括用户的偏好、需求、背景知识和关键事实。所有提炼的内容必须用中文表达。' recall_budget: mid # 'low' | 'mid' | 'high' recall_max_tokens: 4096 recall_max_input_chars: 800 @@ -274,8 +276,8 @@ memory: auto_retain: true retain_async: true retain_every_n_turns: 1 - retain_user_prefix: "User" - retain_assistant_prefix: "Assistant" + retain_user_prefix: 'User' + retain_assistant_prefix: 'Assistant' # background_extraction:预留功能,代码尚未实现 —— 仅设计文档存在。 # 待对应版本支持后,取消下面整段注释即可启用(漏记兜底)。 @@ -293,7 +295,7 @@ memory: max_tokens: 2000 include_builtin: true include_hindsight: true - context_tag: "memory-context" # 包裹 Hindsight recall 的标签名 + context_tag: 'memory-context' # 包裹 Hindsight recall 的标签名 security: scan_content: true # 注入/外渗模式扫描 @@ -311,5 +313,5 @@ ai_writing: log_system: enabled: true - url: "https://your-log-system.example.com" - label: "日志系统" + url: 'https://your-log-system.example.com' + label: '日志系统' From 3f014a6fe1bb7e63289fc2009a2f23687b54a159 Mon Sep 17 00:00:00 2001 From: ZyGuo Date: Fri, 12 Jun 2026 16:32:28 +0800 Subject: [PATCH 2/2] =?UTF-8?q?feat:=20chats=5Fiframe=E5=8E=BB=E6=8E=89?= =?UTF-8?q?=E4=BE=A7=E8=BE=B9=E6=A0=8F=E5=92=8C=E4=B8=BB=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- frontend-web/src/App.tsx | 3 +- .../page-layout/chats-iframe-route.test.mjs | 33 +++++++++++++++++++ .../core/page-layout/chats-iframe-route.ts | 16 +++++++++ frontend-web/src/pages/PageRoutes.tsx | 17 ++++++---- frontend-web/src/pages/WorkspaceRoutes.tsx | 14 ++++++-- 5 files changed, 74 insertions(+), 9 deletions(-) create mode 100644 frontend-web/src/core/page-layout/chats-iframe-route.test.mjs create mode 100644 frontend-web/src/core/page-layout/chats-iframe-route.ts diff --git a/frontend-web/src/App.tsx b/frontend-web/src/App.tsx index 277f3974..e2c8695c 100644 --- a/frontend-web/src/App.tsx +++ b/frontend-web/src/App.tsx @@ -7,6 +7,7 @@ import { QueryClientProvider } from "@/components/query-client-provider"; import { AuthSyncWatcher } from "@/core/auth/sync"; import { I18nProvider } from "@/core/i18n/context"; import { detectLocale } from "@/core/i18n/locale"; +import { resolveForcedThemeForPath } from "@/core/page-layout/chats-iframe-route"; import { ChatProvider } from "@/contexts/ChatContext"; import { ThemeProvider } from "@/contexts/ThemeContext"; @@ -29,7 +30,7 @@ import { NotFoundPage } from "./pages/NotFoundPage"; function AppProviders({ children }: { children: React.ReactNode }) { const locale = useMemo(() => detectLocale(), []); const location = useLocation(); - const forcedTheme = location.pathname === "/landing" ? "light" : undefined; + const forcedTheme = resolveForcedThemeForPath(location.pathname); return ( { + assert.equal( + isChatsIframeWorkspacePath("/page/workspace/chats_iframe/new"), + true, + ); + assert.equal( + isChatsIframeWorkspacePath("/page/workspace/chats_iframe/thread-123"), + true, + ); + assert.equal(isChatsIframeWorkspacePath("/page/workspace/chats/new"), false); + assert.equal(isChatsIframeWorkspacePath("/landing"), false); +}); + +test("forces light theme for landing and chats_iframe routes only", () => { + assert.equal(resolveForcedThemeForPath("/landing"), "light"); + assert.equal( + resolveForcedThemeForPath("/page/workspace/chats_iframe/new"), + "light", + ); + assert.equal( + resolveForcedThemeForPath("/page/workspace/chats_iframe/thread-123"), + "light", + ); + assert.equal(resolveForcedThemeForPath("/page/workspace/chats/new"), undefined); +}); diff --git a/frontend-web/src/core/page-layout/chats-iframe-route.ts b/frontend-web/src/core/page-layout/chats-iframe-route.ts new file mode 100644 index 00000000..30c6ba78 --- /dev/null +++ b/frontend-web/src/core/page-layout/chats-iframe-route.ts @@ -0,0 +1,16 @@ +export function isChatsIframeWorkspacePath(pathname: string): boolean { + return ( + pathname === "/page/workspace/chats_iframe/new" || + pathname.startsWith("/page/workspace/chats_iframe/") + ); +} + +export function resolveForcedThemeForPath( + pathname: string, +): "light" | undefined { + if (pathname === "/landing" || isChatsIframeWorkspacePath(pathname)) { + return "light"; + } + + return undefined; +} diff --git a/frontend-web/src/pages/PageRoutes.tsx b/frontend-web/src/pages/PageRoutes.tsx index 96400566..1e9b0e43 100644 --- a/frontend-web/src/pages/PageRoutes.tsx +++ b/frontend-web/src/pages/PageRoutes.tsx @@ -3,8 +3,10 @@ import { Navigate, Route, Routes } from "react-router-dom"; import { PageSidebar } from "@/components/page-sidebar"; import { PageSidebarDark } from "@/components/page-sidebar-dark"; +import { isChatsIframeWorkspacePath } from "@/core/page-layout/chats-iframe-route"; import { readSidebarEnabled } from "@/core/page-layout/sidebar-enabled"; import { useTheme } from "@/contexts/ThemeContext"; +import { useLocation } from "react-router-dom"; import WorkspaceRoutes from "./WorkspaceRoutes"; import StrategyRoutes from "./StrategyRoutes"; @@ -16,17 +18,20 @@ import NotebookRoutes from "./NotebookRoutes"; function PageLayout() { const [collapsed, setCollapsed] = useState(false); const sidebarEnabled = useMemo(() => readSidebarEnabled(), []); + const location = useLocation(); const { theme } = useTheme(); const isDark = theme === "dark"; + const pageSidebarAllowed = + sidebarEnabled && !isChatsIframeWorkspacePath(location.pathname); // h-full(100%)而非 h-screen(100vh):配合 globals.css 的 html/body/#root height:100% // 高度链,根布局跟随容器高度。全屏下 100% 解析到视口,与 h-screen 等价;无界等嵌套 // 下容器不占满整屏时,高度才能正确收缩而非锁死整屏。 return (
- {sidebarEnabled &&
} + {pageSidebarAllowed &&
}
- {sidebarEnabled && ( + {pageSidebarAllowed && ( isDark ? ( } diff --git a/frontend-web/src/pages/WorkspaceRoutes.tsx b/frontend-web/src/pages/WorkspaceRoutes.tsx index 462b5d5b..bb7df093 100644 --- a/frontend-web/src/pages/WorkspaceRoutes.tsx +++ b/frontend-web/src/pages/WorkspaceRoutes.tsx @@ -67,6 +67,7 @@ export function WorkspaceLayout({ children, pageSidebarCollapsed, pageSidebarHidden = false, + workspaceSidebarHidden = false, headerHidden = false, compactWorkspaceSidebar = false, wrapperOverflowHidden = false, @@ -76,6 +77,7 @@ export function WorkspaceLayout({ children: ReactNode; pageSidebarCollapsed: boolean; pageSidebarHidden?: boolean; + workspaceSidebarHidden?: boolean; headerHidden?: boolean; compactWorkspaceSidebar?: boolean; wrapperOverflowHidden?: boolean; @@ -109,7 +111,9 @@ export function WorkspaceLayout({ data-page-sidebar-collapsed={pageSidebarCollapsed} defaultOpen > - + {!workspaceSidebarHidden && ( + + )} @@ -205,7 +209,11 @@ export default function WorkspaceRoutes({ + @@ -217,6 +225,8 @@ export default function WorkspaceRoutes({ element={