Feat/meituan living assistant expert 内置美团生活助手专家 - #328
Merged
jubaoliang merged 4 commits intoAug 19, 2026
Merged
Conversation
新增专家模板 meituan-living-assistant(领券下单找我): - manifest.json:双语元信息、美团黄主题色、4 个快捷指令 - SOUL.md:角色人格与触发范围 - skills/meituan-deals/SKILL.md:完整流程状态机 (意图识别 → 扫码登录 → 领券/搜索/下单,含话术模板与错误码映射) - scripts/:run.js 统一 CLI 入口(领券/搜索/下单/定位/认证) Octop 适配改造: - Token 存储支持 OCTOP_AUTH_DIR 环境变量注入,实现多 Agent 凭据隔离 (run.js / auth.py / diag_*.py,未注入时回退原默认目录) - Python 解析优先使用 Octop 自托管 venv (OCTOP_PYTHON > $OCTOP_HOME/venv > /app/.venv > PATH 兜底) - npm bin 执行位自愈:专家模板经字节流播种后自动恢复 chmod +x - 定时领券改用 Octop 定时任务体系,替代原 crontab + state.json - dashboard iconForName 补充 utensils / bell 图标映射 来源:CodeBuddy 插件 meituan-living-assistant v1.0.2(美团官方)
Docker 镜像(python:3.12-slim)无 Node/npm,无法在 init 时安装 mtuser-pt-passport tgz。将预装好的 node_modules 产物随专家模板分发, 并精确反排除该子树(其余 node_modules 仍被忽略,不受影响)。
- run.js qrcode 命令:服务端接口失败时本地兜底(qrcode 库 PNG data URI → ASCII 字符画降级 → pip 自动安装重试),支付链接拦截保持不变 - 新增 qr_local.py:本地二维码生成(PNG/ASCII 双模式,JSON 输出) - SKILL.md Step 1.2:取消 miniprogram 客户端不生成二维码的限制 (Octop Web 控制台跑在 Linux 会被误判为 miniprogram,实际可扫码); 登录消息模板增加裸链接行,方便复制 - run.js 帮助文本同步更新
- Optional[X] → X | None(UP045)、导入排序(I001)、移除未用导入(F401) - try/except/pass → contextlib.suppress(SIM105) - if/else → 三元表达式(SIM108)、歧义变量名 l → ln(E741) - Qclaw_USER_ID 大小写为版本差异刻意保留,加 noqa(SIM112) - ruff format 统一格式(含 qr_local.py) make lint 本地全量通过:All checks passed
jubaoliang
added a commit
that referenced
this pull request
Aug 21, 2026
* feat(skills): allow Unicode skill names with filesystem-safe validation The create-form name pattern rejected CJK and other non-ASCII input, while source mode (and the recording workflow, which derives names from user titles) accepted them - the backend slug validator only rejects path-hostile names. Octop targets non-technical users, so the name field should not force ASCII slug conventions. - Replace the ASCII whitelist with a blacklist: reject only filesystem-hostile characters (/ \ : * ? " < > |, control chars), a leading dot, empty names, and names over 64 chars - Apply the same check to source-mode creation (frontmatter name), aligning both editor modes - Skip the check on edit: updateSkill keeps the existing slug, so legacy skills with odd names stay editable - Update zh/en namePattern copy and the placeholder examples * fix(chat): strip media-offload placeholder text from image history The MediaOffloadMiddleware writes a '[image offloaded: sha=… path=… size=…B mime=…; use read_file to retrieve bytes]' placeholder text block into LangGraph checkpoint state on every turn after the first one. That text is meant for the LLM to read_file the bytes back, not for the dashboard UI — after leaving and re-entering a chat, the user's image showed this internal text underneath it. On history serialization, strip the offload placeholder and the LLM-only 'User sent an image.' sentinel for user messages that carry an image in octop_inbound_attachments (the original image is rendered from there). The user's own caption is preserved. Pure-image user messages keep their entry (with empty content) so the dashboard still renders the attachment. * fix(dashboard): prevent AGENT_NOT_RUNNING race when saving page config (#293) Editing an expert's 页面配置 (welcome message + quick-start cards) and clicking 保存 surfaced "此专家未启用" (AGENT_NOT_RUNNING) on every save after the first. Two failures combined to cause it: 1. PATCH /agents/{aid} schedules a background harness reload (arebuild_agent = aremove_agent + slow acreate_agent compile, often 2-5s on Windows). During that window the agent is absent from the harness registry, but the DB row still says 'running'. 2. The manifest write was placed BEFORE the PATCH, so the first save landed before the reload started and worked. But every subsequent save (re-opening the drawer, expanding 页面配置, editing, saving again) hit the reload window from the previous PATCH — and require_running_workspace raised AGENT_NOT_RUNNING. The 'manifest before PATCH' ordering alone only protects the within-save race, not the cross-save one. Reproduction (live server, ENPKA2, 10 rapid saves with the WIP order): 2/10 manifest writes succeeded; 8/10 failed with AGENT_NOT_RUNNING. First save after a 3s wait: 10/10 succeeded — confirms the reload window is the cause. Fix: - Add writeManifestWithRetry (10 × 500ms = up to 5s, retries only on AGENT_NOT_RUNNING). Re-running for 5s is well within typical reload windows; the manifest is best-effort. - Wrap the manifest write in its own try/catch. On failure show a warning toast (yellow, with i18n key experts.manifestWriteFailed) so the user knows, but never block the PATCH — the agent's main config must always save. The drawer still closes and the success toast still fires after the PATCH. Scope of the change: - New: WelcomeConfig.tsx (the 页面配置 editor, used by EditAgentDrawer). - New: index.module.less styles for WelcomeConfig. - Modified: EditAgentDrawer.tsx (render the new collapse section, save the manifest with retry, fall back to a warning). - New i18n keys: experts.pageConfigTitle / welcomeMessageTitle / welcomeMessagePlaceholder / quickPromptsTitle / addQuickPrompt / quickPromptTitle(Placeholder) / quickPromptDescription(Placeholder) / quickPromptContent(Placeholder) / quickPromptColor / quickPromptIcon / quickPromptPreview / noQuickPrompts / noIcon / manifestWriteFailed in both zh.json and en.json; also backfilled experts.patchFailed in zh.json (was missing). Out of scope (pre-existing, surfaced during review): - WelcomeConfig's useImperativeHandle has no deps array — works correctly via closure but recreates the handle each render. - loadConfig() runs on mount; a click on 保存 during the load would write the empty initial state to manifest.json. Not addressed here. Verified: end-to-end against the live server, agent ENPKA2 and S35JZD, after a 3s settle the 2nd save succeeds on retry attempt 2 (~25ms after the first failed attempt), and 5 rapid back-to-back saves all land without surfacing a red error to the user. Co-authored-by: Georgyhongbo <georgyhongbo@users.noreply.github.com> * fix(chat): stop message-list jitter while typing during streaming (#303) adjustHeight() measured the live textarea by collapsing it to height:auto on every keystroke. That transient shrink reflows the flex layout and grows the message-list viewport (a sibling above the composer) for a moment; browsers clamp the list scrollTop to the larger viewport and the clamp STICKS after the height is restored. While a reply streams, the follow-to-bottom pin then snaps the list back down — the per-keystroke up/down jitter. Measure content height on a detached clone instead (cloneNode + position:fixed off-screen), so the live layout is never disturbed. Skip the write when the target height is unchanged (<0.5px). Verified with a frame-by-frame harness: typing-while-streaming bottom gap dropped from avg 8.6px/max 14px to 0.0/0.0. Co-authored-by: jubaoliang <jubaoliang@gmail.com> * fix(plugins): sanitize non-ASCII tool names for strict LLM tool-name APIs (#308) Plugin tools registered with Chinese names passed straight into the function-calling schema and failed on APIs that require ^[a-zA-Z0-9_-]{1,64}$. Rewrite illegal names to legal pinyin transliterations (underscore fallback when pypinyin is unavailable), dedupe collisions with _2/_3 suffixes, and keep the original name in a [原名: ...] description prefix. Config keys and plugin-side closures still use the original names, so routing and per-agent tool config are unaffected. Co-authored-by: jubaoliang <jubaoliang@gmail.com> * Feat/自定义主题色 (#334) * feat(dashboard): custom brand color palette with color picker Extend the 8 curated brand palettes with a 9th "custom" entry driven by a user-chosen hex color: - PaletteSwitcher gains a custom swatch plus a native color input (round swatch); picking a color switches the theme to "custom" - The full Ant Design brand token set and all brand-tinted CSS variables (~30 tokens incl. bubble gradient, sidebar, row-selected, shadows) are derived from the single hex at runtime: - solid states are darkened until white text reaches WCAG AA (4.5:1) - dark-mode text/links are lightened until readable on #0f1117 - customColor is persisted alongside preference/palette in the shared `theme` localStorage key (normalized to lowercase #rrggbb; invalid values fall back to the default #4B74FA) - ThemeContext injects the derived CSS block via a reusable <style id="octop-custom-palette"> element, refreshed on color/mode change; curated palettes are unchanged - charts (TokenUsage, Memory overview) resolve the custom brand via brandPrimary(palette, isDark, customColor) * fix(dashboard): unify custom color into one swatch and extend to expert colors Address three usability issues from the first custom-color iteration: 1. Single control instead of two: the theme palette row now shows ONE custom swatch (rainbow conic-gradient hint). Clicking it opens the Ant Design ColorPicker — pick from the palette or type a hex code; the chosen color fills the swatch and activates the custom palette. The separate "custom swatch + native color input" pair is gone. 2. Smooth picker: replaced the laggy native <input type="color"> with antd 5 ColorPicker (palette + gradient + hex input, dark-mode aware). 3. Expert colors get the same feature: ExpertColorPicker (create/edit expert, subagent form) now accepts a hex value and exposes the same custom swatch; callers hold palette-key-or-hex strings and persist custom hex directly to agent config / subagent frontmatter. A small hex readout shows the active custom color. Also raise workbox maximumFileSizeToCacheInBytes to 3 MiB — the antd ColorPicker color engine pushed vendor-antd past the 2 MiB default, which silently dropped it from the PWA precache and failed the build. * fix(experts): keep custom expert color selected when reopening settings The edit drawer reloaded agent details after mount and mapped the stored color with resolveExpertPalette(), which snaps any hex to the nearest curated swatch — so a saved custom color displayed as the closest preset instead of the custom swatch. Add parseStoredColor(): exact-match a curated swatch hex back to its palette key, keep any other valid hex as-is (custom), return null for invalid values. Both drawers and the initial state now round-trip custom hex without snapping. * fix(voice): MiMo TTS low-latency streaming, voice preset fix, TTS auto-activate (#331) 1. TTS providers now auto-activate after configuration when the active TTS is still "browser", mirroring the existing STT behavior. 2. Remove the invalid "mimo_default" voice option (not a valid MiMo preset voice ID). The UI defaults to 冰糖; the backend maps legacy "mimo_default" configs to 冰糖 so existing setups keep working. 3. MiMo TTS low-latency streaming end to end: - Backend: request pcm16 + stream, parse SSE audio chunks and wrap them in a live WAV container (24kHz PCM16LE mono) - Router: return audio/wav for mimo, audio/mpeg otherwise - Frontend: stream the response via requestStream and play chunks incrementally with WebAudio (WavStreamPlayer), falling back to the buffered blob path for non-WAV providers * Feat/meituan living assistant expert 内置美团生活助手专家 (#328) * feat(experts): 内置美团生活助手专家 新增专家模板 meituan-living-assistant(领券下单找我): - manifest.json:双语元信息、美团黄主题色、4 个快捷指令 - SOUL.md:角色人格与触发范围 - skills/meituan-deals/SKILL.md:完整流程状态机 (意图识别 → 扫码登录 → 领券/搜索/下单,含话术模板与错误码映射) - scripts/:run.js 统一 CLI 入口(领券/搜索/下单/定位/认证) Octop 适配改造: - Token 存储支持 OCTOP_AUTH_DIR 环境变量注入,实现多 Agent 凭据隔离 (run.js / auth.py / diag_*.py,未注入时回退原默认目录) - Python 解析优先使用 Octop 自托管 venv (OCTOP_PYTHON > $OCTOP_HOME/venv > /app/.venv > PATH 兜底) - npm bin 执行位自愈:专家模板经字节流播种后自动恢复 chmod +x - 定时领券改用 Octop 定时任务体系,替代原 crontab + state.json - dashboard iconForName 补充 utensils / bell 图标映射 来源:CodeBuddy 插件 meituan-living-assistant v1.0.2(美团官方) * fix(experts): gitignore 放行美团专家随包的 pt-passport 运行时 Docker 镜像(python:3.12-slim)无 Node/npm,无法在 init 时安装 mtuser-pt-passport tgz。将预装好的 node_modules 产物随专家模板分发, 并精确反排除该子树(其余 node_modules 仍被忽略,不受影响)。 * fix(experts): 美团专家登录二维码三级兜底与可复制裸链接 - run.js qrcode 命令:服务端接口失败时本地兜底(qrcode 库 PNG data URI → ASCII 字符画降级 → pip 自动安装重试),支付链接拦截保持不变 - 新增 qr_local.py:本地二维码生成(PNG/ASCII 双模式,JSON 输出) - SKILL.md Step 1.2:取消 miniprogram 客户端不生成二维码的限制 (Octop Web 控制台跑在 Linux 会被误判为 miniprogram,实际可扫码); 登录消息模板增加裸链接行,方便复制 - run.js 帮助文本同步更新 * style(experts): 修复美团专家脚本 ruff lint 错误 - Optional[X] → X | None(UP045)、导入排序(I001)、移除未用导入(F401) - try/except/pass → contextlib.suppress(SIM105) - if/else → 三元表达式(SIM108)、歧义变量名 l → ln(E741) - Qclaw_USER_ID 大小写为版本差异刻意保留,加 noqa(SIM112) - ruff format 统一格式(含 qr_local.py) make lint 本地全量通过:All checks passed * fix(dashboard): adjust CronJobs table layout for better content display (#326) - Set max-width for promptCell to 280px to prevent long instructions from stretching rows. - Change table scroll behavior to 'max-content' for improved responsiveness. - Update task type rendering to ensure consistent display with nowrap styling. These changes enhance the user interface by maintaining a clean layout and improving readability of task types. * fix(dashboard): move update progress/result prompts above release notes (#332) The upgrade progress bar and the "upgrade complete / restart required" prompts rendered below the (default-expanded) release notes collapse, pushing them out of the viewport with no visible cue — easy to miss. Reorder the panel: progress / result prompts now render directly under the action buttons (check / restart / upgrade), above the release notes. No logic changes; the two blocks are independent (both use margin-top). * feat: show memory slimming progress on chat and agent status (#321) * feat: show memory slimming progress on chat and agent status Expose memory_maintenance from the agent status API and pause send while this agent's SQLite is being compacted. Co-authored-by: Cursor <cursoragent@cursor.com> * chore(deps): 刷新 uv.lock —— harness 升级 + 补齐 pyproject 已声明但未锁的依赖 diff 有 5300 余行,但实质内容变更仅 5 条,其余全部是 uv 0.8.20 的锁格式重写 (revision 1 -> 3,为每条 sdist/wheel 记录追加 upload-time 字段,约 2600 条)。 schema 的 version 字段保持为 1 未变,按 uv 文档 revision 属向后兼容变更, 旧版本 uv 读取不会报错。 实质变更: - orcakit-harness-agent 0.9.20 -> 0.9.21 - harness-memory 0.9.5 -> 0.9.6 - harness-browser 0.7.4 -> 0.7.5 (pyproject 已要求 >=0.7.5) - octop 0.9.23 -> 0.9.24 (版本号跟进) - 新增 pypinyin 依赖声明 (pyproject 已声明 >=0.53) 后三条是在修既有问题:此前 pyproject 加入 harness-browser>=0.7.5 与 pypinyin 后未重新锁定,HEAD 上的 uv.lock 执行 uv lock --check 会失败。CI 的 make install 走 uv sync 且未加 --locked/--frozen,会在 runner 内自行重新解析,因此锁文件失配 不会让 CI 变红——这也意味着 CI 当前并未验证锁定的版本组合。 Co-Authored-By: Claude Opus 5 <noreply@anthropic.com> * typecheck --------- Co-authored-by: Cursor <cursoragent@cursor.com> Co-authored-by: Claude Opus 5 <noreply@anthropic.com> * fix(chat): hide stale scroll-to-bottom button after dock close (#304) A layout clamp (dock open/close, content shrink) can rewrite scrollTop to the bottom without a user gesture. Previously this could leave free mode active with a stale jump-to-bottom control while the user is pinned to the bottom, or surface the control after the dock interaction with no correction. - Pass gapToBottom + atBottomBandPx to shouldEnterFreeModeOnScrollUp so a scroll-up whose resulting position stays inside the bottom band is treated as a layout clamp, not user intent. - Re-check position on scroll-up and after resize in free mode: landing inside the bottom band resumes follow mode and hides the control. * feat(experts): allow custom agent id when creating experts (#333) Users could not choose the agent id when creating an expert (bundled, published, or SkillHub market) — a random 6-char id was always generated, making workspaces under ~/.octop/agents/ hard to identify. Backend: - Expose optional `agent_id` on all three creation endpoints (POST /agents/from-expert/{id}, POST /experts/hub/{slug}/install, POST /experts/published/{id}/install) and thread it through SkillHubMarketAgentCreateOptions / PublishedExpertInstallOptions. - Add validate_custom_agent_id(): 3-64 chars of [a-zA-Z0-9_-], must start/end with a letter or digit; reserved words (api/admin/agents/ experts) rejected — the id becomes a workspace directory name, so separators/dots/unicode are refused to keep every downstream path and URL usage safe. - New ErrorCodes AGENT_ID_INVALID (400) / AGENT_ID_TAKEN (409) with zh/en messages, replacing the generic AGENT_BUSY on duplicates. Dashboard: - "Custom ID (optional)" input on the create-expert drawer (shared by all three sources) with live format + reserved-word validation and a hint that it cannot be changed after creation. Omitting the field keeps the previous auto-generated short id. * fix(channels): add missing internal scroll to channels panel in fill layout (#340) The Personalization channels tab clips overflowing cards when the page is zoomed: the fill layout's fillChild is overflow:hidden and ChannelsPanel had no flex:1 nor a scroll container between the toolbar and the card grid, so cards pushed below the viewport could never be reached. Mirror the Skills tabbedBody pattern: pin the toolbar, wrap the grid (and the loading skeleton) in a scrollable body (flex:1, min-height:0, overflow:auto, 8px top padding so card hover lift stays inside the scrollport). Mobile keeps page-level scrolling via a max-width:767px override, matching fillChild. The Experts ChannelCatalogDrawer embed is unaffected (block wrapper makes flex:1 inert; auto-height overflow does not scroll). * feat(expert): extend meituan-living-assistant to 6 quick prompts (#344) Add two more quick start prompts to the built-in meituan-living-assistant expert (drinks search and group-buy ordering), plus the coffee and shopping-bag icons in the dashboard icon map. * fix: inject Admin env into running agents and sum turn token usage (#345) Running shells and Docker sandboxes now pick up ~/.octop/env (and workspace .env) without a full reload; MCP stdio no longer inherits the entire host environment. Usage accounting adds every model call in the turn, and workspace I/O survives the harness rebuild window. Co-authored-by: jubaoliang <jubaoliang@tencent.com> Co-authored-by: Cursor <cursoragent@cursor.com> * fix(dashboard): hide cron session routing when using a fresh thread (#347) Co-authored-by: jubaoliang <jubaoliang@tencent.com> Co-authored-by: Cursor <cursoragent@cursor.com> * Fix/agent env usage workspace (#351) * fix: inject Admin env into running agents and sum turn token usage Running shells and Docker sandboxes now pick up ~/.octop/env (and workspace .env) without a full reload; MCP stdio no longer inherits the entire host environment. Usage accounting adds every model call in the turn, and workspace I/O survives the harness rebuild window. Co-authored-by: Cursor <cursoragent@cursor.com> * feat: schema v7 identity, expert profiles, chat artifacts, and KB citations (#346) * feat: schema v7 identity, expert profiles, chat artifacts, and KB citations Fold integer PKs plus public string ids, document folders, agent profile columns, and thread artifacts into v7 SQL (not only Python helpers). Experts get workspace avatars and a single welcome_message; chat keeps file changes across sessions, shows knowledge citations, and can drag workspace files. Co-authored-by: Cursor <cursoragent@cursor.com> * chore: drop cron JobDrawer UX from the schema v7 PR Co-authored-by: Cursor <cursoragent@cursor.com> * fix: prefer tool-arg paths when recording chat artifacts Co-authored-by: Cursor <cursoragent@cursor.com> --------- Co-authored-by: jubaoliang <jubaoliang@tencent.com> Co-authored-by: Cursor <cursoragent@cursor.com> --------- Co-authored-by: jubaoliang <jubaoliang@tencent.com> Co-authored-by: Cursor <cursoragent@cursor.com> * fix(gateway): upgrade to 0.9.3 (#353) Co-authored-by: leoxyang <leoxyang@tencent.com> * fix(usage): add cache-aware token accounting (#352) Co-authored-by: leoxyang <leoxyang@tencent.com> * fix(cli): force utf-8 stdio so octop init does not crash on GBK consoles (#348) Chinese Windows (GBK/cp936) encode piped/redirected CLI stdout with the ANSI code page, so the checkmark success message in `octop init` raised UnicodeEncodeError after the DB and admin user were already created. Re-encode stdout/stderr to utf-8 at the CLI entry to cover the whole bug class (init, stub, QR art, future emoji). Add 3 unit tests (tests/unit/cli/test_main_encoding.py): two for the guard helper and an end-to-end `octop init` run under PYTHONIOENCODING=gbk. pytest -m "not live" passes locally; the 12 failures are pre-existing Windows/db-migration environment issues, unchanged by this patch. * 修复onnx向量模型调用 (#360) Co-authored-by: jubaoliang <jubaoliang@gmail.com> * fix(skills): keep sibling files when editing a skill's SKILL.md (#365) PUT /agents/{aid}/skills/{name} deleted the whole skills/<slug>/ directory before writing back the request payload. The dashboard editor sends only the SKILL.md content, so saving an edit on an imported multi-file skill (ZIP / SkillHub) wiped README.md, references/, workflows/ and every other sibling, leaving a lone SKILL.md behind. A content-only update now rewrites just the manifest in place. A full files payload still replaces the directory wholesale, matching create-with-overwrite / re-import semantics (and the truthiness check mirrors _files_from_skill_body so an empty files list falls back to the content path on both sides). * Feat/tencentcloud api expert (#370) * feat(experts): add tencentcloud-api built-in expert Port the standalone tencentcloud-api expert package into the Octop bundled expert library: - manifest.json: id/label/description/welcome/icon/color, prompt_files (SOUL.md) and five quick prompts (list CVM, launch pay-as-you-go CVM, security group, all-region scan, error diagnosis) - SOUL.md: persona covering intent -> API-doc retrieval -> tccli command construction, safety guardrails (confirm-before-change, cost alerts, irreversible-delete warnings), disambiguation rules, identity confirmation (GetCallerIdentity) and output conventions - skills/tcapi/: full SKILL.md workflow (env probe, doc retrieval via cloudcache, credential dual-path, call & JSON-safe parsing, error table, python fallback) plus references/ (auth/install/refs) The catalog discovers it automatically at server start via ExpertCatalog.refresh() scanning library/<id>/manifest.json. * feat(experts): prefer Octop venv tccli, add 6th quick prompt, automate OAuth Three improvements to the tencentcloud-api expert: 1. venv-first tccli resolution (SKILL.md Step 0 / Step 5, references/install.md): locate the Octop virtualenv via the running octop process (/proc/<pid>/cwd), probe venv tccli -> PATH -> auto-install into the venv with uv. Fallback python invocation in Step 5 now prefers the venv interpreter over system-wide probing. 2. Fully automated OAuth flow (SKILL.md Step 2): run 'BROWSER=echo tccli auth login' in the background so headless environments don't abort, extract the authorize URL from the log, surface it to the user, poll until the browser callback completes, then verify credentials and echo identity via GetCallerIdentity. Legacy tccli without 'auth login' is auto-upgraded in the venv before retrying. Error table updated accordingly. SOUL.md synced. 3. Sixth quick prompt '账号登录授权' in manifest.json for one-click sign-in with identity echo. * fix(experts): use credential-file mtime as OAuth success signal, never block-poll Real-world test feedback: the user completed browser authorization successfully, but the agent misjudged it as 'timed out because the user hasn't completed authorization' and re-issued a fresh login link (which invalidated the completed one). Root cause: the SKILL's wait loop (300 x 1s kill -0 polling) holds the tool call open until the agent's per-call execution timeout kills it. A tool timeout is NOT a login failure, but the agent conflated the two. Meanwhile the backgrounded 'tccli auth login' kept running: the OAuth callback landed and the credential was written to ~/.tccli/default.credential (verified: file existed, type=oauth, GetCallerIdentity returned the account). Changes (SKILL.md Step 2.2, error table, SOUL.md, references/auth.md): - Success criterion is the credential file mtime, not process exit: record a baseline before handing the link out, then compare after the user reports back. Log line '登录成功, 密钥凭证已被写入' is an equivalent signal. - Forbid long blocking polls: hand the link to the user, keep probing windows short (<=30s), return control to the conversation, and confirm via file mtime + GetCallerIdentity on the next turn. - Never re-run 'auth login' when the credential file already updated: a new login invalidates the previous (already authorized) link and forces the user to click again. - On TokenFailure/RefreshTokenError, check the credential file first before declaring it invalid (the previous attempt may have succeeded and been misjudged). - Document the remote/callback caveat: OAuth redirects to localhost:9000-9100 on the tccli host; when the user's browser is not on the same machine (server deployments), the callback cannot reach tccli — fall back to copying the oauth credential file or manual 'tccli configure'. * chore(experts): move sign-in quick prompt to first position Put '账号登录授权' (fully automated OAuth sign-in with identity echo) at the top of the quick prompts so new users authorize first, then explore the resource-management prompts. * feat(experts): actively listen for OAuth callback instead of waiting for user reply Previously after handing out the authorize link the agent ended its turn and only verified on the user's next message. Now the agent keeps bounded listening windows on the credential file so the moment the user clicks 'authorize' in the browser, the flow continues automatically — zero user replies needed. Listening protocol (SKILL.md Step 2.2 / SOUL.md / references/auth.md): - One listening window: compare mtime of ~/.tccli/<profile>.credential against /tmp/tccli_auth.log every 3s, up to 60s per window (must stay below the tool execution timeout). Credential newer than log -> AUTH_DONE, verify immediately. - Window expiry is NOT failure: never re-issue the link (that would invalidate the user's in-flight authorization), just open another window (3-5 windows ≈ 3-5 min total), then optionally return control to the conversation and confirm via the verification script later. - Verification scheme unchanged (authoritative): credential mtime > login-log mtime, then 'tccli sts GetCallerIdentity' identity echo. - Baseline uses the login log's mtime instead of a shell variable because shell state does not survive across tool calls. - Tool timeout of a listening window still != login failure: run the standalone verification script afterwards, judge by the credential file only. Dry-run validated: link extraction, silent window expiry with no credential, and both verification branches behave as specified. * feat(experts): add clinical learning subscription assistant (#369) * feat(experts): add clinical learning subscription assistant 基层医生学习小助手专家包(26 个文件): - 通用助手 + 医学学习安全域作用域隔离,通用能力不被医学规则误伤 - 8 个 skills:指南学习/章节展开/学习路径图/备考选材/医保回顾/学习诊断/更新提醒/来源核验/登记 - 输出校验器按模块作用域生效;反绕过规则(创作包装不改变内容性质) - 自包含:脚本仅标准库依赖,可整包迁移 附专家包模板测试。 * feat(experts): progressive disclosure + registration-first bootstrap + py3.9 compat - SOUL 瘦身(14.7kB→12kB):能力细则下沉回各 skill,保留身份/禁令/安全域/分流 - SOUL 新增新用户识别:主动引导登记,个性化功能先登记 - BOOTSTRAP 重写为登记优先短流程(含首条回复示例),用户可拒绝不纠缠 - AGENTS 新增医学输出四条硬格式(模板头/来源行含正例/边界声明/禁编造) - 子代理定义补格式要求;审校员必查项加格式合规 - clinical_profile.py 兼容 Python 3.9(datetime.UTC→timezone.utc) - 三处统一:脚本失败只报告,禁止手改 USER.md/state.json * feat(experts): enable daily guideline learning via weak-dedup cron protocol - clinical_profile.py 新增 delivery-check/delivery-record:按逻辑日期幂等去重, 记录后自动推进单元;兼容 Python 3.9(_UTC 运行时解析) - cron-presets.json 每日学习预设从 blocked 改为 enabled_weak_delivery, prompt 内嵌防重规程(查重→校验→记账→输出) - SOUL/AGENTS/guideline-learning/doctor-registration 解锁通用 cron 投递, 统一弱投递口径:账本只防重复、不是送达回执、不宣称已确认送达 - 订阅任务创建默认微信通道,创建后核对绑定并如实告知 - 新增弱投递账本测试(幂等+推进) * feat(experts): expand evidence whitelist with official and semi-official sources Add verified domains per source-tier rules (V2.0 doc section 9.2): - S-tier official: cde.org.cn (CDE), cdr-adr.org.cn (ADR monitoring) - A-tier societies: cmda.net (CMDA), cpma.org.cn (CPMA) - Semi-official: cha.org.cn, csco.org.cn, cnsoc.org, pmph.com * fix(experts): drop wechat-only gate for clinical subscription cron 平台 cronjob_create 自动绑定当前会话通道(微信/QQ/dashboard/CLI), 无需微信绑定门禁。移除 cron-presets.json 的 :weixin:/allow_dashboard 门禁、AGENTS.md §4.7 与 doctor-registration 流程的微信绑定要求,回执 统一为已启用并推送至当前会话通道。clinical_profile 默认值改为未创建并 对历史 state 兼容;simulate_weixin_flow 改为任意会话均可创建。每日指南 学习用通用 cron + 弱投递防重,选定指南轨道前不推送。新增 TEST_CASES.md。 * refactor(experts): progressive disclosure + skill routing + i18n + source policy - 顶层精简去重:SOUL/AGENTS/BOOTSTRAP 互不重复,细则下沉 skill/reference - 新增 skill:intent-routing(意图路由)、output-format(医学输出校验)、subscription-setup(订阅创建,从 doctor-registration 拆出) - guideline-learning 改为流程约束,操作细则下沉 references/learning-operations.md - BOOTSTRAP 渐进式入口(7-20骨架+当前需求),安全底线自含(首次SOUL不加载) - 中文化:validate_output errors 改中文,manifest 删 en 只留 zh - cron prompt 加输出约束(简体中文+静默执行+不输出思考),三 task 补 prompt - 信源白名单 A/B/C/D 四级:新增 ndcpa/natcm/std.samr(B)、guidelines-registry(C) - 删除 TEST_CASES.md * fix(manifest): 恢复 en 字段(19 quick_prompts+welcome); fix(bootstrap): 首次开场话术改介绍+5项+隐私+征求同意 * fix(experts): tighten clinical source verification * docs(experts): refine clinical assistant description * fix(experts): improve clinical learning cycle completion * perf(experts): speed up verified clinical guidance * fix(experts): suppress preview validation preamble * fix(experts): limit browser automation usage * fix(experts): suppress validation status preambles * feat(experts): add controlled secondary source fallback --------- Co-authored-by: leoxyang <leoxyang@tencent.com> * feat: workspace backend sandboxing, execute-env injection, and ephemeral image refs (#376) * feat: workspace backend sandboxing, execute-env injection, and ephemeral image refs Workspace file-I/O hardening across backend and dashboard: - Host directory sandboxing via root_dir allow-list and denied prefixes - Execute-environment defaults injected into harness backend specs - Ephemeral workspace image rematerialization for model calls - Attachment hint expansion and inbound store improvements - Portable memory backend and skill workspace catalog updates - Dashboard UI for agent backend fields and root-dir selection - Bump harness-agent 0.9.23 / harness-memory 0.9.7; docs + install notes * feat: add user invitation codes with admin management and redeem flow - Add user_invites table (migration 009) plus SQLite/Postgres reconcile paths - Add InviteRepo and InviteService for create/revoke/list/redeem - Expose public validate/redeem endpoints and admin create/revoke/list routers - Extract default-agent bootstrap into octop.infra.agents.default_agent - Add invite error codes and en/zh i18n strings - Dashboard: invite drawer, login redeem UI, users list, and locales * fix: add Windows cross-platform guards for pre-existing sandbox/rootfs tests - Guard POSIX/container-only tests (rootfs-absolute /.octop/... workspace paths) with posix_only in test_thread_artifacts.py and test_agent_manager.py - Normalize the rendered workspace path assertion in test_octop_builtin_skills.py (forward slashes on Windows, not str(tmp_path) backslashes) - Canonicalize ws_dir before the prefix check in attachment hint/path tests (tempfile may yield an 8.3 short path on Windows while the resolved attachment path uses the long form) These failures predate the user-invites commit and are unrelated to it; the product path logic is correct. --------- Co-authored-by: jubaoliang <jubaoliang@tencent.com> * chore: release 0.9.25 --------- Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com> Co-authored-by: chujieHong <2280628443@qq.com> Co-authored-by: chujieHong <31946519+chujieHong@users.noreply.github.com> Co-authored-by: Georgyhongbo <georgyhongbo@users.noreply.github.com> Co-authored-by: 猫猫摸大鱼 <58991169+miaowmint@users.noreply.github.com> Co-authored-by: liukewia <liukewia@gmail.com> Co-authored-by: 薄生 <67680641+Bosheng0422@users.noreply.github.com> Co-authored-by: Cursor <cursoragent@cursor.com> Co-authored-by: Claude Opus 5 <noreply@anthropic.com> Co-authored-by: jubaoliang <jubaoliang@tencent.com> Co-authored-by: Panda <163635413+Pandakingxbc@users.noreply.github.com> Co-authored-by: leoxyang <leoxyang@tencent.com> Co-authored-by: XiaoChen <1326713348@qq.com>
12 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
内置「美团生活助手」专家模板(领券 / 搜索 / 下单全流程),并修复 Linux 部署下登录二维码缺失的问题。
Target branch
develop(feature / fix — default)main(release/*orhotfix/*only)Type of change
Test plan
make allpasses locallyChecklist
CHANGELOG.md(if user-facing)