mirror of
https://github.com/agentscope-ai/ReMe.git
synced 2026-08-28 05:25:04 +00:00
feat: distribute Studio as an optional package (#454)
This commit is contained in:
parent
29eb51d7ba
commit
2a05914150
22 changed files with 426 additions and 34 deletions
2
.github/workflows/pre-commit.yml
vendored
2
.github/workflows/pre-commit.yml
vendored
|
|
@ -23,7 +23,7 @@ jobs:
|
||||||
pip install -U setuptools wheel
|
pip install -U setuptools wheel
|
||||||
- name: Install
|
- name: Install
|
||||||
run: |
|
run: |
|
||||||
pip install -q -e ".[dev,core]"
|
pip install -q -e packages/reme_ai_studio -e ".[dev,core]"
|
||||||
- name: Install pre-commit
|
- name: Install pre-commit
|
||||||
run: |
|
run: |
|
||||||
pre-commit install
|
pre-commit install
|
||||||
|
|
|
||||||
25
.github/workflows/python-publish.yml
vendored
25
.github/workflows/python-publish.yml
vendored
|
|
@ -29,30 +29,33 @@ jobs:
|
||||||
node-version: '22'
|
node-version: '22'
|
||||||
cache: npm
|
cache: npm
|
||||||
cache-dependency-path: website/package-lock.json
|
cache-dependency-path: website/package-lock.json
|
||||||
|
- name: Set up Python
|
||||||
|
uses: actions/setup-python@v6
|
||||||
|
with:
|
||||||
|
python-version: '3.11'
|
||||||
- name: Build web workspace
|
- name: Build web workspace
|
||||||
working-directory: website
|
working-directory: website
|
||||||
run: |
|
run: |
|
||||||
npm ci
|
npm ci
|
||||||
npm run build:static
|
npm run build:static
|
||||||
rm -rf ../reme/web
|
- name: Prepare Studio package
|
||||||
mkdir -p ../reme/web
|
run: python scripts/package_studio.py
|
||||||
cp -R dist-static/. ../reme/web/
|
|
||||||
- name: Set up Python
|
|
||||||
uses: actions/setup-python@v6
|
|
||||||
with:
|
|
||||||
python-version: '3.11'
|
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
run: |
|
run: |
|
||||||
python -m pip install --upgrade pip
|
python -m pip install --upgrade pip
|
||||||
pip install setuptools wheel build
|
pip install setuptools wheel build
|
||||||
- name: Build package
|
- name: Build package
|
||||||
run: python -m build
|
run: |
|
||||||
|
python -m build --outdir dist
|
||||||
|
python -m build packages/reme_ai_studio --outdir dist
|
||||||
- name: Test installation
|
- name: Test installation
|
||||||
run: |
|
run: |
|
||||||
WHEEL="$(ls dist/*.whl)"
|
REME_WHEEL="$(pwd)/$(ls dist/reme_ai-[0-9]*.whl)"
|
||||||
pip install "${WHEEL}[core]"
|
python -m zipfile -l "${REME_WHEEL}" | (! grep 'reme/web/')
|
||||||
|
pip install --find-links "$(pwd)/dist" "${REME_WHEEL}[core]"
|
||||||
python -c "import reme; print(reme.__version__)"
|
python -c "import reme; print(reme.__version__)"
|
||||||
python -c "from importlib.resources import files; assert (files('reme') / 'web' / 'index.html').is_file()"
|
python -c "from reme_ai_studio import static_dir; assert (static_dir() / 'index.html').is_file()"
|
||||||
|
python -c "from reme.utils import resolve_web_static_dir; assert (resolve_web_static_dir() / 'index.html').is_file()"
|
||||||
- name: Publish package to PyPI
|
- name: Publish package to PyPI
|
||||||
uses: pypa/gh-action-pypi-publish@release/v1
|
uses: pypa/gh-action-pypi-publish@release/v1
|
||||||
with:
|
with:
|
||||||
|
|
|
||||||
2
.github/workflows/unittest.yml
vendored
2
.github/workflows/unittest.yml
vendored
|
|
@ -32,7 +32,7 @@ jobs:
|
||||||
- name: Install dependencies
|
- name: Install dependencies
|
||||||
run: |
|
run: |
|
||||||
python -m pip install --upgrade pip setuptools wheel
|
python -m pip install --upgrade pip setuptools wheel
|
||||||
pip install -e ".[dev,core]"
|
pip install -e packages/reme_ai_studio -e ".[dev,core]"
|
||||||
pip install coverage
|
pip install coverage
|
||||||
|
|
||||||
- name: Run unit tests
|
- name: Run unit tests
|
||||||
|
|
|
||||||
2
.github/workflows/windows-smoke.yml
vendored
2
.github/workflows/windows-smoke.yml
vendored
|
|
@ -32,7 +32,7 @@ jobs:
|
||||||
- name: Install package
|
- name: Install package
|
||||||
run: |
|
run: |
|
||||||
python -m pip install --upgrade pip setuptools wheel
|
python -m pip install --upgrade pip setuptools wheel
|
||||||
pip install -e ".[dev,core]"
|
pip install -e packages/reme_ai_studio -e ".[dev,core]"
|
||||||
|
|
||||||
- name: Run version job
|
- name: Run version job
|
||||||
run: reme start service.backend=cli job=version
|
run: reme start service.backend=cli job=version
|
||||||
|
|
|
||||||
|
|
@ -86,12 +86,16 @@ Install from pip:
|
||||||
pip install "reme-ai[core]"
|
pip install "reme-ai[core]"
|
||||||
```
|
```
|
||||||
|
|
||||||
|
The base `reme-ai` package contains only the Python service and library. ReMe Studio is distributed separately and is
|
||||||
|
installed by the `web` and `core` extras. Use `pip install reme-ai` for embedded or headless integrations that do not
|
||||||
|
need the frontend, or `pip install "reme-ai[web]"` when Studio is needed without the other `core` integrations.
|
||||||
|
|
||||||
Install from source:
|
Install from source:
|
||||||
|
|
||||||
```bash
|
```bash
|
||||||
git clone https://github.com/agentscope-ai/ReMe.git
|
git clone https://github.com/agentscope-ai/ReMe.git
|
||||||
cd ReMe
|
cd ReMe
|
||||||
pip install -e ".[core]"
|
pip install -e packages/reme_ai_studio -e ".[core]"
|
||||||
```
|
```
|
||||||
|
|
||||||
### Environment Variables
|
### Environment Variables
|
||||||
|
|
@ -134,7 +138,8 @@ reme start service.port=8181
|
||||||
|
|
||||||
After startup, check the service status. If you use a custom port, replace `2333` in the URL below with that port.
|
After startup, check the service status. If you use a custom port, replace `2333` in the URL below with that port.
|
||||||
|
|
||||||
When the web build is available, the HTTP service also serves **ReMe Studio** at <http://127.0.0.1:2333/>. Studio can
|
When the `web` or `core` extra is installed, the HTTP service also serves **ReMe Studio** at
|
||||||
|
<http://127.0.0.1:2333/>. Studio can
|
||||||
browse, edit, and search the workspace, chat with the read-only workspace agent, and inspect the digest wikilink graph.
|
browse, edit, and search the workspace, chat with the read-only workspace agent, and inspect the digest wikilink graph.
|
||||||
Set `service.web_enabled=false` to disable it, or use `service.web_static_dir` / `REME_WEB_STATIC_DIR` to provide a
|
Set `service.web_enabled=false` to disable it, or use `service.web_static_dir` / `REME_WEB_STATIC_DIR` to provide a
|
||||||
custom static build. The Job API remains available when no web build is found.
|
custom static build. The Job API remains available when no web build is found.
|
||||||
|
|
|
||||||
|
|
@ -39,7 +39,7 @@ The project requires Python 3.11 or later. A virtual environment is recommended:
|
||||||
```bash
|
```bash
|
||||||
python -m venv .venv
|
python -m venv .venv
|
||||||
source .venv/bin/activate
|
source .venv/bin/activate
|
||||||
pip install -e ".[dev,full]"
|
pip install -e packages/reme_ai_studio -e ".[dev,full]"
|
||||||
pre-commit install
|
pre-commit install
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -166,10 +166,10 @@ HTTP service behavior:
|
||||||
| `enable_serve: false` | No endpoint is registered. |
|
| `enable_serve: false` | No endpoint is registered. |
|
||||||
|
|
||||||
After registering Job endpoints, the HTTP service can also mount the ReMe Studio single-page application. The default is
|
After registering Job endpoints, the HTTP service can also mount the ReMe Studio single-page application. The default is
|
||||||
`service.web_enabled=true`. Builds are resolved from `service.web_static_dir`, `REME_WEB_STATIC_DIR`, packaged
|
`service.web_enabled=true`. Builds are resolved from `service.web_static_dir`, `REME_WEB_STATIC_DIR`, the optional
|
||||||
`reme/web`, and source-tree locations such as `website/dist-static`. If no `index.html` is found, only the frontend is
|
`reme-ai-studio` package installed by the `web` and `core` extras, and source-tree locations such as
|
||||||
skipped and the Job API remains available. The Studio `GET` fallback does not replace existing `POST /<job.name>`
|
`website/dist-static`. If no `index.html` is found, only the frontend is skipped and the Job API remains available. The
|
||||||
routes.
|
Studio `GET` fallback does not replace existing `POST /<job.name>` routes.
|
||||||
|
|
||||||
MCP service behavior:
|
MCP service behavior:
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ Install from source:
|
||||||
```bash
|
```bash
|
||||||
git clone https://github.com/agentscope-ai/ReMe.git
|
git clone https://github.com/agentscope-ai/ReMe.git
|
||||||
cd ReMe
|
cd ReMe
|
||||||
pip install -e ".[core]"
|
pip install -e packages/reme_ai_studio -e ".[core]"
|
||||||
```
|
```
|
||||||
|
|
||||||
Installing the `core` extra is recommended. The current code imports the AgentScope wrapper, and self-evolving memory
|
Installing the `core` extra is recommended. The current code imports the AgentScope wrapper, and self-evolving memory
|
||||||
|
|
@ -56,7 +56,8 @@ reme help
|
||||||
|
|
||||||
`reme help` lists server actions. Ordinary commands invoke server Jobs over HTTP.
|
`reme help` lists server actions. Ordinary commands invoke server Jobs over HTTP.
|
||||||
|
|
||||||
When the package includes the web build, open <http://127.0.0.1:2333/> for ReMe Studio. It uses the same service to
|
The base `reme-ai` package does not include frontend assets. Install `reme-ai[web]` or `reme-ai[core]`, then open
|
||||||
|
<http://127.0.0.1:2333/> for ReMe Studio. It uses the same service to
|
||||||
browse, edit, and search the workspace and inspect the digest wikilink graph. Disable it with
|
browse, edit, and search the workspace and inspect the digest wikilink graph. Disable it with
|
||||||
`service.web_enabled=false`, or provide a custom build with `service.web_static_dir` / `REME_WEB_STATIC_DIR`. The Job
|
`service.web_enabled=false`, or provide a custom build with `service.web_static_dir` / `REME_WEB_STATIC_DIR`. The Job
|
||||||
API still starts if no web build is found.
|
API still starts if no web build is found.
|
||||||
|
|
|
||||||
|
|
@ -37,7 +37,7 @@ ReMe 的核心代码位于:
|
||||||
```bash
|
```bash
|
||||||
python -m venv .venv
|
python -m venv .venv
|
||||||
source .venv/bin/activate
|
source .venv/bin/activate
|
||||||
pip install -e ".[dev,full]"
|
pip install -e packages/reme_ai_studio -e ".[dev,full]"
|
||||||
pre-commit install
|
pre-commit install
|
||||||
```
|
```
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -161,8 +161,9 @@ HTTP service 行为:
|
||||||
| `enable_serve: false` | 不注册 endpoint |
|
| `enable_serve: false` | 不注册 endpoint |
|
||||||
|
|
||||||
HTTP service 还可以在所有 Job endpoint 注册完成后挂载 ReMe Studio 单页应用。默认 `service.web_enabled=true`;构建产物按
|
HTTP service 还可以在所有 Job endpoint 注册完成后挂载 ReMe Studio 单页应用。默认 `service.web_enabled=true`;构建产物按
|
||||||
`service.web_static_dir`、`REME_WEB_STATIC_DIR`、包内 `reme/web` 和源码树 `website/dist-static` 等候选位置解析。找不到
|
`service.web_static_dir`、`REME_WEB_STATIC_DIR`、由 `web` 或 `core` extra 安装的可选 `reme-ai-studio` 包,以及源码树
|
||||||
`index.html` 时只跳过前端,Job API 仍然可用。Studio 的 `GET` fallback 不会覆盖已有的 `POST /<job.name>`。
|
`website/dist-static` 等候选位置解析。找不到 `index.html` 时只跳过前端,Job API 仍然可用。Studio 的 `GET` fallback 不会覆盖
|
||||||
|
已有的 `POST /<job.name>`。
|
||||||
|
|
||||||
MCP service 行为:
|
MCP service 行为:
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -15,7 +15,7 @@ pip install "reme-ai[core]"
|
||||||
```bash
|
```bash
|
||||||
git clone https://github.com/agentscope-ai/ReMe.git
|
git clone https://github.com/agentscope-ai/ReMe.git
|
||||||
cd ReMe
|
cd ReMe
|
||||||
pip install -e ".[core]"
|
pip install -e packages/reme_ai_studio -e ".[core]"
|
||||||
```
|
```
|
||||||
|
|
||||||
`core` extra 建议安装:当前代码会导入 AgentScope wrapper,自进化记忆也依赖它。
|
`core` extra 建议安装:当前代码会导入 AgentScope wrapper,自进化记忆也依赖它。
|
||||||
|
|
@ -55,7 +55,8 @@ reme help
|
||||||
|
|
||||||
`reme help` 会列出服务端 action。普通命令会通过 HTTP 调用服务端 Job。
|
`reme help` 会列出服务端 action。普通命令会通过 HTTP 调用服务端 Job。
|
||||||
|
|
||||||
如果安装包中包含 Web 构建产物,浏览器打开 <http://127.0.0.1:2333/> 即可进入 ReMe Studio,在同一服务中浏览、编辑和搜索
|
基础 `reme-ai` 包不包含前端资源。安装 `reme-ai[web]` 或 `reme-ai[core]` 后,浏览器打开
|
||||||
|
<http://127.0.0.1:2333/> 即可进入 ReMe Studio,在同一服务中浏览、编辑和搜索
|
||||||
workspace,并查看 digest Wikilink 图。可用 `service.web_enabled=false` 关闭,或通过 `service.web_static_dir` /
|
workspace,并查看 digest Wikilink 图。可用 `service.web_enabled=false` 关闭,或通过 `service.web_static_dir` /
|
||||||
`REME_WEB_STATIC_DIR`
|
`REME_WEB_STATIC_DIR`
|
||||||
指定自定义静态目录;找不到构建产物时,Job API 仍会正常启动。
|
指定自定义静态目录;找不到构建产物时,Job API 仍会正常启动。
|
||||||
|
|
|
||||||
203
packages/reme_ai_studio/README.md
Normal file
203
packages/reme_ai_studio/README.md
Normal file
|
|
@ -0,0 +1,203 @@
|
||||||
|
# ReMe Studio
|
||||||
|
|
||||||
|
English | [简体中文](#简体中文)
|
||||||
|
|
||||||
|
ReMe Studio is the local web workspace for ReMe. It lets you browse and edit user-owned workspace files, explore memory
|
||||||
|
links, and chat with the ReMe Agent without moving durable memory into a separate application database. Search indexes,
|
||||||
|
graphs, and other derived metadata remain rebuildable from the source files.
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## Installation
|
||||||
|
|
||||||
|
Install Studio together with ReMe's optional integrations:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
pip install "reme-ai[core]"
|
||||||
|
```
|
||||||
|
|
||||||
|
For Studio without the other optional integrations, use `pip install "reme-ai[web]"`. The base `reme-ai` package is
|
||||||
|
headless and does not include the frontend assets.
|
||||||
|
|
||||||
|
## Features
|
||||||
|
|
||||||
|
- **Workspace browsing**: browse the full workspace or focus on journal and knowledge files through dedicated views. The
|
||||||
|
navigator refreshes as files change on disk.
|
||||||
|
- **Markdown editing and preview**: open multiple files in tabs, render Markdown front matter and GitHub Flavored
|
||||||
|
Markdown, edit with Monaco, save with optimistic modification-time checks, and download files locally.
|
||||||
|
- **Memory graph**: inspect indexed wikilinks under the `wiki`, `personal`, and
|
||||||
|
`procedure` knowledge roots, follow inbound and outbound links, and open the corresponding Markdown source.
|
||||||
|
- **Agent chat**: stream conversations with the read-only workspace Agent, see tool calls and token usage, and drag
|
||||||
|
workspace files into the conversation as references.
|
||||||
|
- **Service management**: inspect service and component memory usage, review the effective redacted configuration and
|
||||||
|
version, and rebuild derived indexes without modifying source memory files.
|
||||||
|
- **Personalization**: switch between English and Chinese, and use light, dark, or system appearance.
|
||||||
|
|
||||||
|
## Requirements
|
||||||
|
|
||||||
|
- Python 3.11 or newer with ReMe installed.
|
||||||
|
- A running ReMe HTTP service. Agent chat additionally requires a working Agent and model configuration.
|
||||||
|
- Node.js 22.13 or newer is required only when developing or building Studio from source.
|
||||||
|
|
||||||
|
See the [repository README](https://github.com/agentscope-ai/ReMe#readme) for ReMe installation and backend configuration.
|
||||||
|
|
||||||
|
## Development
|
||||||
|
|
||||||
|
Start ReMe from the repository root, then run the frontend in another terminal:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# Terminal 1, from the repository root
|
||||||
|
reme start
|
||||||
|
|
||||||
|
# Terminal 2
|
||||||
|
cd website
|
||||||
|
npm install
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
Open <http://localhost:3000>. The frontend connects to
|
||||||
|
`http://127.0.0.1:2333` by default. Override it when needed:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
NEXT_PUBLIC_REME_API_URL=http://127.0.0.1:8000 npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
## ReMe-hosted static build
|
||||||
|
|
||||||
|
ReMe can serve Studio from the same FastAPI process as its HTTP API. Build the static variant and restart ReMe:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd website
|
||||||
|
npm ci
|
||||||
|
npm run build:static
|
||||||
|
cd ..
|
||||||
|
reme start
|
||||||
|
```
|
||||||
|
|
||||||
|
Open <http://127.0.0.1:2333>. The static build uses same-origin requests by default. For standalone static development,
|
||||||
|
run `npm run dev:static` and set
|
||||||
|
`VITE_REME_API_URL` to the running ReMe service URL when necessary.
|
||||||
|
|
||||||
|
The regular `npm run build` command remains the vinext/Sites deployment build;
|
||||||
|
`npm run build:static` creates `dist-static/` exclusively for FastAPI and Python package distribution.
|
||||||
|
|
||||||
|
## Configuration
|
||||||
|
|
||||||
|
The workspace hides dotfiles and dot-directories. It displays only Markdown and text files by default. Configure the
|
||||||
|
allowed extensions as a comma-separated list in `.env.local`:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
NEXT_PUBLIC_REME_WORKSPACE_EXTENSIONS=md,txt,mdx
|
||||||
|
```
|
||||||
|
|
||||||
|
The memory graph requires an index built by ReMe. Rebuilding the index from the Studio settings regenerates derived data
|
||||||
|
from workspace files and does not modify the source memory.
|
||||||
|
|
||||||
|
## Checks
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm run format:check
|
||||||
|
npm run lint
|
||||||
|
npm run build
|
||||||
|
npm run build:static
|
||||||
|
npm test
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
# 简体中文
|
||||||
|
|
||||||
|
[English](#reme-studio) | 简体中文
|
||||||
|
|
||||||
|
ReMe Studio 是 ReMe 的本地 Web 工作区。你可以在这里浏览和编辑自己拥有的工作区文件、探索记忆之间的联系,并与 ReMe Agent
|
||||||
|
对话,而无需将持久记忆迁移到独立的应用数据库中。搜索索引、图谱和其他派生元数据均可根据源文件重建。
|
||||||
|
|
||||||
|

|
||||||
|
|
||||||
|
## 安装
|
||||||
|
|
||||||
|
安装 Studio 和 ReMe 的可选集成功能:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
pip install "reme-ai[core]"
|
||||||
|
```
|
||||||
|
|
||||||
|
如果只需要 Studio,不需要其他可选集成,可以使用 `pip install "reme-ai[web]"`。基础 `reme-ai` 包以无界面模式分发,
|
||||||
|
不包含前端资源。
|
||||||
|
|
||||||
|
## 功能
|
||||||
|
|
||||||
|
- **浏览工作区**:浏览完整工作区,或通过独立视图聚焦日记和知识文件;磁盘中的文件发生变化后,导航器会自动刷新。
|
||||||
|
- **Markdown 编辑与预览**:在多个标签页中打开文件,渲染 Markdown front matter 和 GitHub Flavored Markdown,使用 Monaco
|
||||||
|
编辑器编辑,通过修改时间检查安全保存,并可将文件下载到本地。
|
||||||
|
- **记忆图谱**:查看知识库 `wiki`、`personal` 和 `procedure` 目录中已索引的 wikilink,检查入链和出链,并从图谱打开对应的
|
||||||
|
Markdown 源文件。
|
||||||
|
- **Agent 对话**:与只读工作区 Agent 进行流式对话,查看工具调用和 token 用量,还可将工作区文件拖入对话作为引用。
|
||||||
|
- **服务管理**:查看服务及组件的内存使用情况、当前生效的脱敏配置和版本,并在不修改记忆源文件的情况下重建派生索引。
|
||||||
|
- **个性化设置**:切换中英文界面,并使用浅色、深色或跟随系统的外观。
|
||||||
|
|
||||||
|
## 环境要求
|
||||||
|
|
||||||
|
- Python 3.11 或更高版本,并已安装 ReMe。
|
||||||
|
- 正在运行的 ReMe HTTP 服务。Agent 对话还需要可用的 Agent 和模型配置。
|
||||||
|
- 只有从源码开发或构建 Studio 时才需要 Node.js 22.13 或更高版本。
|
||||||
|
|
||||||
|
ReMe 的安装和后端配置请参阅[仓库中文 README](https://github.com/agentscope-ai/ReMe/blob/main/README_ZH.md)。
|
||||||
|
|
||||||
|
## 本地开发
|
||||||
|
|
||||||
|
先在仓库根目录启动 ReMe,然后在另一个终端运行前端:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
# 终端 1:仓库根目录
|
||||||
|
reme start
|
||||||
|
|
||||||
|
# 终端 2
|
||||||
|
cd website
|
||||||
|
npm install
|
||||||
|
npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
打开 <http://localhost:3000>。前端默认连接 `http://127.0.0.1:2333`,需要时可覆盖该地址:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
NEXT_PUBLIC_REME_API_URL=http://127.0.0.1:8000 npm run dev
|
||||||
|
```
|
||||||
|
|
||||||
|
## 由 ReMe 托管的静态构建
|
||||||
|
|
||||||
|
ReMe 可以通过提供 HTTP API 的同一个 FastAPI 进程托管 Studio。构建静态版本并重启 ReMe:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
cd website
|
||||||
|
npm ci
|
||||||
|
npm run build:static
|
||||||
|
cd ..
|
||||||
|
reme start
|
||||||
|
```
|
||||||
|
|
||||||
|
打开 <http://127.0.0.1:2333>。静态构建默认使用同源请求。进行独立的静态开发时,运行
|
||||||
|
`npm run dev:static`;如有需要,将 `VITE_REME_API_URL` 设置为正在运行的 ReMe 服务地址。
|
||||||
|
|
||||||
|
常规的 `npm run build` 命令仍用于 vinext/Sites 部署构建;`npm run build:static` 仅为 FastAPI 和 Python 包分发生成
|
||||||
|
`dist-static/`。
|
||||||
|
|
||||||
|
## 配置
|
||||||
|
|
||||||
|
工作区会隐藏点文件和点目录,并且默认只显示 Markdown 和文本文件。可以在 `.env.local` 中通过逗号分隔的列表配置允许显示的扩展名:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
NEXT_PUBLIC_REME_WORKSPACE_EXTENSIONS=md,txt,mdx
|
||||||
|
```
|
||||||
|
|
||||||
|
记忆图谱依赖 ReMe 构建的索引。在 Studio 设置中重建索引时,只会根据工作区文件重新生成派生数据,不会修改记忆源文件。
|
||||||
|
|
||||||
|
## 检查
|
||||||
|
|
||||||
|
```bash
|
||||||
|
npm run format:check
|
||||||
|
npm run lint
|
||||||
|
npm run build
|
||||||
|
npm run build:static
|
||||||
|
npm test
|
||||||
|
```
|
||||||
24
packages/reme_ai_studio/pyproject.toml
Normal file
24
packages/reme_ai_studio/pyproject.toml
Normal file
|
|
@ -0,0 +1,24 @@
|
||||||
|
[project]
|
||||||
|
name = "reme-ai-studio"
|
||||||
|
version = "0.4.1.6"
|
||||||
|
description = "Optional ReMe Studio static frontend."
|
||||||
|
readme = "README.md"
|
||||||
|
license = "Apache-2.0"
|
||||||
|
requires-python = ">=3.11"
|
||||||
|
|
||||||
|
[project.urls]
|
||||||
|
Homepage = "https://github.com/agentscope-ai/ReMe/tree/main/website"
|
||||||
|
Documentation = "https://reme.agentscope.io"
|
||||||
|
Repository = "https://github.com/agentscope-ai/ReMe"
|
||||||
|
|
||||||
|
[tool.setuptools]
|
||||||
|
package-dir = { "" = "src" }
|
||||||
|
packages = ["reme_ai_studio"]
|
||||||
|
include-package-data = false
|
||||||
|
|
||||||
|
[tool.setuptools.package-data]
|
||||||
|
"reme_ai_studio" = ["static/**"]
|
||||||
|
|
||||||
|
[build-system]
|
||||||
|
requires = ["setuptools>=45", "wheel"]
|
||||||
|
build-backend = "setuptools.build_meta"
|
||||||
11
packages/reme_ai_studio/src/reme_ai_studio/__init__.py
Normal file
11
packages/reme_ai_studio/src/reme_ai_studio/__init__.py
Normal file
|
|
@ -0,0 +1,11 @@
|
||||||
|
"""Static asset provider for the optional ReMe Studio frontend."""
|
||||||
|
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
|
||||||
|
def static_dir() -> Path:
|
||||||
|
"""Return the installed Studio static asset directory."""
|
||||||
|
return Path(__file__).resolve().parent / "static"
|
||||||
|
|
||||||
|
|
||||||
|
__all__ = ["static_dir"]
|
||||||
2
packages/reme_ai_studio/src/reme_ai_studio/static/.gitignore
vendored
Normal file
2
packages/reme_ai_studio/src/reme_ai_studio/static/.gitignore
vendored
Normal file
|
|
@ -0,0 +1,2 @@
|
||||||
|
*
|
||||||
|
!.gitignore
|
||||||
|
|
@ -42,6 +42,9 @@ dependencies = [
|
||||||
]
|
]
|
||||||
|
|
||||||
[project.optional-dependencies]
|
[project.optional-dependencies]
|
||||||
|
web = [
|
||||||
|
"reme-ai-studio==0.4.1.6",
|
||||||
|
]
|
||||||
core = [
|
core = [
|
||||||
"agentscope==2.0.4.post1",
|
"agentscope==2.0.4.post1",
|
||||||
"claude-agent-sdk>=0.2.126",
|
"claude-agent-sdk>=0.2.126",
|
||||||
|
|
@ -55,6 +58,7 @@ core = [
|
||||||
"neo4j>=6.2.0",
|
"neo4j>=6.2.0",
|
||||||
"networkx>=3.4.2",
|
"networkx>=3.4.2",
|
||||||
"polars>=1.43.0",
|
"polars>=1.43.0",
|
||||||
|
"reme-ai-studio==0.4.1.6",
|
||||||
]
|
]
|
||||||
dev = [
|
dev = [
|
||||||
"pre-commit>=4.6.1",
|
"pre-commit>=4.6.1",
|
||||||
|
|
@ -80,7 +84,6 @@ include-package-data = true
|
||||||
|
|
||||||
[tool.setuptools.package-data]
|
[tool.setuptools.package-data]
|
||||||
"*" = ["py.typed", "**/*.yaml", "**/*.json"]
|
"*" = ["py.typed", "**/*.yaml", "**/*.json"]
|
||||||
"reme" = ["web/**"]
|
|
||||||
"reme.components.tokenizer" = ["stopwords"]
|
"reme.components.tokenizer" = ["stopwords"]
|
||||||
|
|
||||||
[tool.setuptools.dynamic]
|
[tool.setuptools.dynamic]
|
||||||
|
|
|
||||||
|
|
@ -8,20 +8,39 @@ from pathlib import Path
|
||||||
REME_WEB_STATIC_DIR = "REME_WEB_STATIC_DIR"
|
REME_WEB_STATIC_DIR = "REME_WEB_STATIC_DIR"
|
||||||
|
|
||||||
|
|
||||||
|
def _packaged_studio_dir() -> Path | None:
|
||||||
|
"""Return the static directory supplied by the optional Studio package."""
|
||||||
|
try:
|
||||||
|
from reme_ai_studio import static_dir
|
||||||
|
except ImportError:
|
||||||
|
return None
|
||||||
|
return static_dir()
|
||||||
|
|
||||||
|
|
||||||
def resolve_web_static_dir(configured_dir: str | None = None) -> Path | None:
|
def resolve_web_static_dir(configured_dir: str | None = None) -> Path | None:
|
||||||
"""Return the first directory containing a built workspace ``index.html``."""
|
"""Return the first directory containing a built workspace ``index.html``."""
|
||||||
package_dir = Path(__file__).resolve().parent.parent
|
package_dir = Path(__file__).resolve().parent.parent
|
||||||
repository_dir = package_dir.parent
|
repository_dir = package_dir.parent
|
||||||
cwd = Path.cwd()
|
cwd = Path.cwd()
|
||||||
candidates = [
|
explicit_candidates = [
|
||||||
configured_dir,
|
configured_dir,
|
||||||
os.getenv(REME_WEB_STATIC_DIR),
|
os.getenv(REME_WEB_STATIC_DIR),
|
||||||
|
]
|
||||||
|
for candidate in explicit_candidates:
|
||||||
|
if not candidate:
|
||||||
|
continue
|
||||||
|
path = Path(candidate).expanduser().resolve()
|
||||||
|
if path.is_dir() and (path / "index.html").is_file():
|
||||||
|
return path
|
||||||
|
|
||||||
|
fallback_candidates = [
|
||||||
|
_packaged_studio_dir(),
|
||||||
package_dir / "web",
|
package_dir / "web",
|
||||||
repository_dir / "website" / "dist-static",
|
repository_dir / "website" / "dist-static",
|
||||||
cwd / "website" / "dist-static",
|
cwd / "website" / "dist-static",
|
||||||
cwd / "web_dist",
|
cwd / "web_dist",
|
||||||
]
|
]
|
||||||
for candidate in candidates:
|
for candidate in fallback_candidates:
|
||||||
if not candidate:
|
if not candidate:
|
||||||
continue
|
continue
|
||||||
path = Path(candidate).expanduser().resolve()
|
path = Path(candidate).expanduser().resolve()
|
||||||
|
|
|
||||||
58
scripts/package_studio.py
Normal file
58
scripts/package_studio.py
Normal file
|
|
@ -0,0 +1,58 @@
|
||||||
|
"""Prepare the optional ReMe Studio Python distribution."""
|
||||||
|
|
||||||
|
from __future__ import annotations
|
||||||
|
|
||||||
|
import argparse
|
||||||
|
import shutil
|
||||||
|
from pathlib import Path
|
||||||
|
|
||||||
|
REPOSITORY_DIR = Path(__file__).resolve().parents[1]
|
||||||
|
WEBSITE_DIR = REPOSITORY_DIR / "website"
|
||||||
|
PACKAGE_DIR = REPOSITORY_DIR / "packages" / "reme_ai_studio"
|
||||||
|
STATIC_DIR = PACKAGE_DIR / "src" / "reme_ai_studio" / "static"
|
||||||
|
|
||||||
|
_RAW_WEBSITE_URL = "https://raw.githubusercontent.com/agentscope-ai/ReMe/main/website"
|
||||||
|
_REPOSITORY_URL = "https://github.com/agentscope-ai/ReMe"
|
||||||
|
|
||||||
|
|
||||||
|
def build_readme() -> str:
|
||||||
|
"""Compose the PyPI description from the English and Chinese Studio docs."""
|
||||||
|
english = (WEBSITE_DIR / "README.md").read_text(encoding="utf-8")
|
||||||
|
chinese = (WEBSITE_DIR / "README_ZH.md").read_text(encoding="utf-8")
|
||||||
|
english = english.replace("English | [简体中文](./README_ZH.md)", "English | [简体中文](#简体中文)")
|
||||||
|
chinese = chinese.replace(
|
||||||
|
"# ReMe Studio\n\n[English](./README.md) | 简体中文",
|
||||||
|
"# 简体中文\n\n[English](#reme-studio) | 简体中文",
|
||||||
|
)
|
||||||
|
for relative, absolute in {
|
||||||
|
"./public/og.jpg": f"{_RAW_WEBSITE_URL}/public/og.jpg",
|
||||||
|
"../README.md": f"{_REPOSITORY_URL}#readme",
|
||||||
|
"../README_ZH.md": f"{_REPOSITORY_URL}/blob/main/README_ZH.md",
|
||||||
|
}.items():
|
||||||
|
english = english.replace(relative, absolute)
|
||||||
|
chinese = chinese.replace(relative, absolute)
|
||||||
|
return f"{english.rstrip()}\n\n---\n\n{chinese.rstrip()}\n"
|
||||||
|
|
||||||
|
|
||||||
|
def prepare_package(*, copy_static: bool = True) -> None:
|
||||||
|
"""Generate the PyPI README and optionally stage the static build."""
|
||||||
|
(PACKAGE_DIR / "README.md").write_text(build_readme(), encoding="utf-8")
|
||||||
|
if not copy_static:
|
||||||
|
return
|
||||||
|
source = WEBSITE_DIR / "dist-static"
|
||||||
|
if not (source / "index.html").is_file():
|
||||||
|
raise FileNotFoundError(f"Studio static build is unavailable: {source}")
|
||||||
|
shutil.rmtree(STATIC_DIR, ignore_errors=True)
|
||||||
|
shutil.copytree(source, STATIC_DIR)
|
||||||
|
|
||||||
|
|
||||||
|
def main() -> None:
|
||||||
|
"""Run the package preparation command."""
|
||||||
|
parser = argparse.ArgumentParser(description=__doc__)
|
||||||
|
parser.add_argument("--readme-only", action="store_true", help="Generate only the PyPI README")
|
||||||
|
args = parser.parse_args()
|
||||||
|
prepare_package(copy_static=not args.readme_only)
|
||||||
|
|
||||||
|
|
||||||
|
if __name__ == "__main__":
|
||||||
|
main()
|
||||||
|
|
@ -1,7 +1,8 @@
|
||||||
"""HTTP service coverage for the optional bundled web workspace."""
|
"""HTTP service coverage for the optional bundled web workspace."""
|
||||||
|
|
||||||
|
import sys
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from types import SimpleNamespace
|
from types import ModuleType, SimpleNamespace
|
||||||
|
|
||||||
import pytest
|
import pytest
|
||||||
from fastapi.testclient import TestClient
|
from fastapi.testclient import TestClient
|
||||||
|
|
@ -100,3 +101,13 @@ def test_static_dir_configuration_precedes_environment(monkeypatch, tmp_path: Pa
|
||||||
|
|
||||||
assert resolve_web_static_dir(str(configured)) == configured.resolve()
|
assert resolve_web_static_dir(str(configured)) == configured.resolve()
|
||||||
assert resolve_web_static_dir() == environment.resolve()
|
assert resolve_web_static_dir() == environment.resolve()
|
||||||
|
|
||||||
|
|
||||||
|
def test_static_dir_uses_optional_studio_package(monkeypatch, tmp_path: Path) -> None:
|
||||||
|
"""Use static assets supplied by the separately installed Studio wheel."""
|
||||||
|
static_dir = _static_build(tmp_path / "studio")
|
||||||
|
studio = ModuleType("reme_ai_studio")
|
||||||
|
studio.static_dir = lambda: static_dir # type: ignore[attr-defined]
|
||||||
|
monkeypatch.setitem(sys.modules, "reme_ai_studio", studio)
|
||||||
|
|
||||||
|
assert resolve_web_static_dir() == static_dir.resolve()
|
||||||
|
|
|
||||||
28
tests/unit/test_package_versions.py
Normal file
28
tests/unit/test_package_versions.py
Normal file
|
|
@ -0,0 +1,28 @@
|
||||||
|
"""Keep the separately published distributions version-compatible."""
|
||||||
|
|
||||||
|
from pathlib import Path
|
||||||
|
import tomllib
|
||||||
|
|
||||||
|
import reme
|
||||||
|
from scripts.package_studio import build_readme
|
||||||
|
|
||||||
|
|
||||||
|
def test_studio_package_and_extra_versions_match_reme() -> None:
|
||||||
|
"""Require one version bump to update both wheels and their exact pin."""
|
||||||
|
repository = Path(__file__).resolve().parents[2]
|
||||||
|
main_config = tomllib.loads((repository / "pyproject.toml").read_text(encoding="utf-8"))
|
||||||
|
studio_config = tomllib.loads(
|
||||||
|
(repository / "packages" / "reme_ai_studio" / "pyproject.toml").read_text(encoding="utf-8"),
|
||||||
|
)
|
||||||
|
expected_dependency = f"reme-ai-studio=={reme.__version__}"
|
||||||
|
|
||||||
|
assert studio_config["project"]["version"] == reme.__version__
|
||||||
|
assert main_config["project"]["optional-dependencies"]["web"] == [expected_dependency]
|
||||||
|
assert expected_dependency in main_config["project"]["optional-dependencies"]["core"]
|
||||||
|
|
||||||
|
|
||||||
|
def test_studio_readme_is_generated_from_website_docs() -> None:
|
||||||
|
"""Keep the packaged PyPI description synchronized with the source docs."""
|
||||||
|
repository = Path(__file__).resolve().parents[2]
|
||||||
|
packaged_readme = repository / "packages" / "reme_ai_studio" / "README.md"
|
||||||
|
assert packaged_readme.read_text(encoding="utf-8") == build_readme()
|
||||||
|
|
@ -8,6 +8,17 @@ graphs, and other derived metadata remain rebuildable from the source files.
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
|
## Installation
|
||||||
|
|
||||||
|
Install Studio together with ReMe's optional integrations:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
pip install "reme-ai[core]"
|
||||||
|
```
|
||||||
|
|
||||||
|
For Studio without the other optional integrations, use `pip install "reme-ai[web]"`. The base `reme-ai` package is
|
||||||
|
headless and does not include the frontend assets.
|
||||||
|
|
||||||
## Features
|
## Features
|
||||||
|
|
||||||
- **Workspace browsing**: browse the full workspace or focus on journal and knowledge files through dedicated views. The
|
- **Workspace browsing**: browse the full workspace or focus on journal and knowledge files through dedicated views. The
|
||||||
|
|
@ -24,9 +35,9 @@ graphs, and other derived metadata remain rebuildable from the source files.
|
||||||
|
|
||||||
## Requirements
|
## Requirements
|
||||||
|
|
||||||
- Node.js 22.13 or newer.
|
|
||||||
- Python 3.11 or newer with ReMe installed.
|
- Python 3.11 or newer with ReMe installed.
|
||||||
- A running ReMe HTTP service. Agent chat additionally requires a working Agent and model configuration.
|
- A running ReMe HTTP service. Agent chat additionally requires a working Agent and model configuration.
|
||||||
|
- Node.js 22.13 or newer is required only when developing or building Studio from source.
|
||||||
|
|
||||||
See the [repository README](../README.md) for ReMe installation and backend configuration.
|
See the [repository README](../README.md) for ReMe installation and backend configuration.
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -7,6 +7,17 @@ ReMe Studio 是 ReMe 的本地 Web 工作区。你可以在这里浏览和编辑
|
||||||
|
|
||||||

|

|
||||||
|
|
||||||
|
## 安装
|
||||||
|
|
||||||
|
安装 Studio 和 ReMe 的可选集成功能:
|
||||||
|
|
||||||
|
```bash
|
||||||
|
pip install "reme-ai[core]"
|
||||||
|
```
|
||||||
|
|
||||||
|
如果只需要 Studio,不需要其他可选集成,可以使用 `pip install "reme-ai[web]"`。基础 `reme-ai` 包以无界面模式分发,
|
||||||
|
不包含前端资源。
|
||||||
|
|
||||||
## 功能
|
## 功能
|
||||||
|
|
||||||
- **浏览工作区**:浏览完整工作区,或通过独立视图聚焦日记和知识文件;磁盘中的文件发生变化后,导航器会自动刷新。
|
- **浏览工作区**:浏览完整工作区,或通过独立视图聚焦日记和知识文件;磁盘中的文件发生变化后,导航器会自动刷新。
|
||||||
|
|
@ -20,9 +31,9 @@ ReMe Studio 是 ReMe 的本地 Web 工作区。你可以在这里浏览和编辑
|
||||||
|
|
||||||
## 环境要求
|
## 环境要求
|
||||||
|
|
||||||
- Node.js 22.13 或更高版本。
|
|
||||||
- Python 3.11 或更高版本,并已安装 ReMe。
|
- Python 3.11 或更高版本,并已安装 ReMe。
|
||||||
- 正在运行的 ReMe HTTP 服务。Agent 对话还需要可用的 Agent 和模型配置。
|
- 正在运行的 ReMe HTTP 服务。Agent 对话还需要可用的 Agent 和模型配置。
|
||||||
|
- 只有从源码开发或构建 Studio 时才需要 Node.js 22.13 或更高版本。
|
||||||
|
|
||||||
ReMe 的安装和后端配置请参阅[仓库中文 README](../README_ZH.md)。
|
ReMe 的安装和后端配置请参阅[仓库中文 README](../README_ZH.md)。
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue