mirror of
https://github.com/agentscope-ai/ReMe.git
synced 2026-10-12 03:50:59 +00:00
fix(codex): retain status resources for active MCP connections
This commit is contained in:
parent
d5e948a0b1
commit
593c0ce6ba
8 changed files with 39 additions and 8 deletions
|
|
@ -223,6 +223,7 @@ with the previous address; switch back to retry them. Changes made during consol
|
|||
| --- | --- |
|
||||
| No MCP settings entry | Confirm your desktop version meets the requirement above, then open the installed ReMe detail and its `reme` MCP card; confirm it is enabled and restart. |
|
||||
| Hooks settings keep loading or do not show ReMe | Open a local project folder and select the local host before reopening Hooks settings; see below. |
|
||||
| Status cannot open after an update, with `No such file or directory` pointing to an old plugin version | Fully quit and reopen Codex, then reopen ReMe status from MCP settings. Closing the card or starting a new conversation does not reload an existing MCP connection. |
|
||||
| Blank status card followed by a plugin feature loading error | Check network access to the Codex sandbox page; see below. |
|
||||
| Connection healthy, no recording or recall | Review every ReMe Hook; check the auto switches and recent activity. Health does not prove Hook execution. |
|
||||
| Turns stay queued | Keep Codex and ReMe running. Check the ReMe model configuration and service logs, and confirm the startup command includes `service.tool_error_on_failure=true`. |
|
||||
|
|
|
|||
|
|
@ -217,6 +217,7 @@ ReMe-Example-7319 的评审时间和项目关键词是什么?
|
|||
| --- | --- |
|
||||
| 找不到 MCP 设置 | 确认桌面端符合上述版本要求,再打开已安装的 ReMe 详情及 `reme` MCP 卡片;确认启用后重启。 |
|
||||
| Hooks 设置一直加载或没有 ReMe | 先打开本地项目文件夹并选择本机,再重新进入 Hooks 设置;见下方说明。 |
|
||||
| 升级后状态页打不开,`No such file or directory` 指向旧插件版本 | 完全退出并重新打开 Codex,再从 MCP 设置打开 ReMe status。关闭卡片或新建会话不会重新加载已有的 MCP 连接。 |
|
||||
| 状态卡片空白,随后提示“插件功能未成功加载” | 检查 Codex 沙箱页面的网络访问;见下方说明。 |
|
||||
| 连接健康,但没有记录或召回 | 检查全部 ReMe Hook 的信任状态、自动开关及最近活动;连接健康不代表 Hook 已执行。 |
|
||||
| 记录一直在队列中 | 保持 Codex 和 ReMe 运行,检查 ReMe 模型配置和服务日志,并确认启动命令包含 `service.tool_error_on_failure=true`。 |
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
{
|
||||
"name": "reme",
|
||||
"version": "0.2.5",
|
||||
"version": "0.2.6",
|
||||
"description": "Automatic memory, focused recall, runtime status, and consolidation through ReMe MCP.",
|
||||
"author": {
|
||||
"name": "EconML team of Alibaba Tongyi Lab",
|
||||
|
|
|
|||
|
|
@ -77,6 +77,10 @@ def status_text(snapshot: dict, language: str) -> str:
|
|||
|
||||
def register_tools(server: FastMCP) -> None:
|
||||
"""Keep local tools discoverable even while the upstream service is unavailable."""
|
||||
# Codex may remove this installation cache before closing the existing MCP connection.
|
||||
root = Path(__file__).parent
|
||||
status_html = (root / "ui/status.html").read_text(encoding="utf-8")
|
||||
plugin_version = json.loads((root / ".codex-plugin/plugin.json").read_text(encoding="utf-8"))["version"]
|
||||
|
||||
@server.tool(name=SEARCH, title="Search ReMe memory", annotations={"readOnlyHint": True})
|
||||
async def search(
|
||||
|
|
@ -110,8 +114,7 @@ def register_tools(server: FastMCP) -> None:
|
|||
@server.resource(STATUS_URI, title="ReMe status", mime_type="text/html;profile=mcp-app", meta=STATUS_META)
|
||||
def status_view() -> ResourceResult:
|
||||
"""Serve a self-contained read-only view without exposing a local HTTP server."""
|
||||
html = (Path(__file__).parent / "ui/status.html").read_text(encoding="utf-8")
|
||||
return ResourceResult([ResourceContent(html, mime_type="text/html;profile=mcp-app", meta=STATUS_META)])
|
||||
return ResourceResult([ResourceContent(status_html, mime_type="text/html;profile=mcp-app", meta=STATUS_META)])
|
||||
|
||||
@server.tool(
|
||||
name=STATUS,
|
||||
|
|
@ -126,11 +129,10 @@ def register_tools(server: FastMCP) -> None:
|
|||
service_snapshot(config, "health_check"),
|
||||
service_snapshot(config, "status"),
|
||||
)
|
||||
manifest = Path(__file__).parent / ".codex-plugin/plugin.json"
|
||||
snapshot = {
|
||||
"checked_at": time.time(),
|
||||
"language": config["language"],
|
||||
"plugin_version": json.loads(manifest.read_text(encoding="utf-8"))["version"],
|
||||
"plugin_version": plugin_version,
|
||||
"mcpUrl": config["mcpUrl"],
|
||||
"service": {"health_check": health, "status": components},
|
||||
**local_status(config),
|
||||
|
|
|
|||
|
|
@ -658,7 +658,7 @@
|
|||
}
|
||||
const host = await transport.request("ui/initialize", {
|
||||
protocolVersion: "2026-01-26",
|
||||
appInfo: { name: "reme-status", version: "0.2.5" },
|
||||
appInfo: { name: "reme-status", version: "0.2.6" },
|
||||
appCapabilities: { availableDisplayModes: ["fullscreen"] }
|
||||
});
|
||||
if (host.protocolVersion !== "2026-01-26") throw new Error("Unsupported UI protocol");
|
||||
|
|
|
|||
|
|
@ -235,7 +235,7 @@ $("refresh").addEventListener("click", async () => {
|
|||
async function connect() {
|
||||
if (window.parent === window) { text("loading", t("noHost")); return; }
|
||||
const host = await transport.request("ui/initialize", {
|
||||
protocolVersion: "2026-01-26", appInfo: { name: "reme-status", version: "0.2.5" },
|
||||
protocolVersion: "2026-01-26", appInfo: { name: "reme-status", version: "0.2.6" },
|
||||
appCapabilities: { availableDisplayModes: ["fullscreen"] },
|
||||
});
|
||||
if (host.protocolVersion !== "2026-01-26") throw new Error("Unsupported UI protocol");
|
||||
|
|
|
|||
|
|
@ -22,7 +22,7 @@ def snapshot(language):
|
|||
return {
|
||||
"checked_at": 1790757300,
|
||||
"language": language,
|
||||
"plugin_version": "0.2.5",
|
||||
"plugin_version": "0.2.6",
|
||||
"mcpUrl": "http://localhost:2333/mcp",
|
||||
"service": {
|
||||
"health_check": {"reachable": True, "answer": "ReMe v0.4.1.13 - healthy"},
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@
|
|||
import asyncio
|
||||
import importlib
|
||||
import json
|
||||
import shutil
|
||||
from datetime import datetime, timezone
|
||||
from pathlib import Path
|
||||
from unittest.mock import AsyncMock
|
||||
|
|
@ -220,6 +221,32 @@ async def test_status_opens_a_self_contained_fullscreen_app_resource(plugin):
|
|||
assert "<script src=" not in content.text
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
async def test_status_survives_removal_of_its_installation_cache(plugin, monkeypatch, tmp_path):
|
||||
config, module, _ = plugin
|
||||
features = importlib.import_module("reme_tools")
|
||||
cache = tmp_path / "plugin-cache/old-version"
|
||||
(cache / "ui").mkdir(parents=True)
|
||||
(cache / ".codex-plugin").mkdir()
|
||||
html = (PLUGIN / "ui/status.html").read_text(encoding="utf-8")
|
||||
(cache / "ui/status.html").write_text(html, encoding="utf-8")
|
||||
(cache / ".codex-plugin/plugin.json").write_text(json.dumps({"version": "old-version"}), encoding="utf-8")
|
||||
monkeypatch.setattr(features, "__file__", str(cache / "reme_tools.py"))
|
||||
monkeypatch.setattr(features, "call_async", AsyncMock(return_value={"answer": "healthy"}))
|
||||
server = module.create_server()
|
||||
|
||||
async with Client(server) as client:
|
||||
shutil.rmtree(cache) # Codex can remove the old cache while its MCP connection is still alive.
|
||||
content = (await client.read_resource(features.STATUS_URI))[0]
|
||||
assert content.text == html
|
||||
status = (await client.call_tool(module.STATUS, {})).structured_content
|
||||
assert status["plugin_version"] == "old-version"
|
||||
assert status["service"]["health_check"] == {"reachable": True, "answer": "healthy"}
|
||||
await client.call_tool(module.SETTINGS_UPDATE, {"set": {"language": "zh"}})
|
||||
assert (await client.call_tool(module.STATUS, {})).structured_content["language"] == "zh"
|
||||
assert config.load_config()["language"] == "zh"
|
||||
|
||||
|
||||
@pytest.mark.asyncio
|
||||
async def test_focused_search_uses_live_defaults_validates_input_and_reports_empty(plugin, monkeypatch):
|
||||
config, module, _ = plugin
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue