From 0ac9500c82b8560003b398844a8120a5035c9e9f Mon Sep 17 00:00:00 2001 From: Tokisakix <2116884726@qq.com> Date: Fri, 31 Jul 2026 11:48:28 +0800 Subject: [PATCH] Align OpenRath v2.0.0 README and deployment reference --- .github/workflows/ci-v2-production.yml | 2 +- .github/workflows/release-v2-ga.yml | 2 +- .github/workflows/release-v2-rc.yml | 2 +- README.md | 76 ++++++++++++++----- README_zh.md | 70 +++++++++++++++-- deploy/compose/compose.yaml | 4 +- deploy/kubernetes/openrath.yaml | 4 +- .../reference_app.py | 2 +- docker/Dockerfile | 2 +- tests/deployment/test_reference_manifests.py | 2 +- 10 files changed, 131 insertions(+), 35 deletions(-) rename examples/v2_server_app.py => deploy/reference_app.py (97%) diff --git a/.github/workflows/ci-v2-production.yml b/.github/workflows/ci-v2-production.yml index 8c43e75..f3b87af 100644 --- a/.github/workflows/ci-v2-production.yml +++ b/.github/workflows/ci-v2-production.yml @@ -47,7 +47,7 @@ jobs: server /data - run: uv lock --check - run: uv sync --frozen --extra postgres --extra server --extra s3 --extra redis --extra otel - - run: uv run ruff check src tests scripts examples + - run: uv run ruff check src tests scripts deploy/reference_app.py - run: uv run ruff format --check src tests example - run: uv run mypy src/rath - name: Audit exact production dependency set diff --git a/.github/workflows/release-v2-ga.yml b/.github/workflows/release-v2-ga.yml index 3decda9..2a8b78e 100644 --- a/.github/workflows/release-v2-ga.yml +++ b/.github/workflows/release-v2-ga.yml @@ -120,7 +120,7 @@ jobs: uv lock --check uv sync --frozen --all-extras --all-groups uv run ruff format --check src tests example - uv run ruff check src tests scripts examples + uv run ruff check src tests scripts deploy/reference_app.py uv run mypy --no-incremental src/rath uv run pytest -q -n auto \ -m "not live_llm and not opensandbox and not openviking" diff --git a/.github/workflows/release-v2-rc.yml b/.github/workflows/release-v2-rc.yml index c3509e7..39e5559 100644 --- a/.github/workflows/release-v2-rc.yml +++ b/.github/workflows/release-v2-rc.yml @@ -55,7 +55,7 @@ jobs: uv lock --check uv sync --frozen --all-extras --all-groups uv run ruff format --check src tests example - uv run ruff check src tests scripts examples + uv run ruff check src tests scripts deploy/reference_app.py uv run mypy --no-incremental src/rath uv run pytest -q -n auto -m "not live_llm and not opensandbox and not openviking" uv run python scripts/export_openapi_v2.py --output "$RUNNER_TEMP/openapi-v2.json" diff --git a/README.md b/README.md index 96c39fa..a4dd876 100644 --- a/README.md +++ b/README.md @@ -54,18 +54,40 @@ Most agent frameworks begin with an agent loop. OpenRath begins with **Session** OpenRath is designed for this: many agents collaborating across many branchable sessions, while still tracing every role, workspace, memory write, and final output. -## v2.0.0 durable runtime (release candidate) - -The `2.0.0rc1` candidate adds explicit `@step` / `@router` execution plans, durable -Runs and checkpoints, effect reconciliation, tenant-scoped Agent Server APIs, -and governed Provider/Tool/Sandbox/Memory adapters. The HTTP contract is -currently **Beta**; v1 JSONL imports are historical and cannot resume an active -Run. +## OpenRath v2.0.0: Built for Production + +The defining change in OpenRath v2.0.0 is that OpenRath moves beyond a +composable Python framework and becomes a durable runtime designed for +production deployment. The existing Session-first Python API remains intact; +the release adds a production execution and operations layer around it. + +| Production concern | What OpenRath provides | +| --- | --- | +| Durable execution | Explicit `@step` / `@router` boundaries compile into immutable execution plans. Runs, Events, and Checkpoints survive process and worker restarts. | +| Resilient workers | Leases, fencing, retries, cancellation, deadlines, and resumable queues prevent stale workers from silently committing new state. | +| Controlled side effects | An Effect Ledger records outcomes and idempotency keys. Ambiguous non-idempotent effects stop in `NEEDS_REVIEW` instead of being replayed blindly. | +| Human decisions | Durable Interrupts pause a Run for approval or input and resume it without rebuilding hidden loop state. | +| Security and tenancy | Agent Server tokens carry explicit action grants; tenant/project scope, policy checks, secret references, trust labels, and audit remain separate boundaries. | +| Production operations | PostgreSQL is the durable source of truth, Redis can accelerate signaling, S3-compatible storage holds artifacts, and health, migration, telemetry, container, and Kubernetes references are included. | + +```text +@step / @router + | + v +ExecutionPlan -> Run -> Event -> Checkpoint + | | + | +-> Interrupt / Effect Ledger + | + +-> PostgreSQL durable state + +-> optional Redis signals + +-> S3-compatible artifacts + | + v + Agent Server HTTP + SSE +``` -Embedded mode is intended for a trusted process. Agent Server mode is the -strict durable profile: tokens need explicit action grants, object access is -tenant/project scoped, and synchronous steps cannot declare a preemptive -timeout. Use an async step or isolated executor for enforceable deadlines. +Embedded mode remains useful inside a trusted process. Agent Server mode is the +strict production profile: ```python runtime = LocalRuntime( @@ -76,12 +98,28 @@ runtime = LocalRuntime( server = AgentServer(store, runtime, auth=auth, audit_sink=audit) ``` -Production PostgreSQL schema migration is a separate operation: -`openrath-migrate` followed by `openrath-migrate --check`. Runtime identities -do not need DDL privileges. See -[`deploy/docs/operations-v2.md`](deploy/docs/operations-v2.md), -[`deploy/docs/migration-v2.md`](deploy/docs/migration-v2.md), and the generated -[`deploy/docs/openapi-v2.json`](deploy/docs/openapi-v2.json). +Install the production profile and run schema migration as a separate +operation: + +```bash +pip install "openrath[server,postgres]" +openrath-migrate +openrath-migrate --check +``` + +Runtime identities do not need DDL privileges. Tokens need explicit action +grants, object access is tenant/project scoped, and synchronous steps cannot +declare a preemptive timeout; use an async step or isolated executor when a +deadline must be enforced. + +OpenRath v2.0.0 is designed for production deployment while keeping interface +maturity explicit: the Agent Server HTTP surface remains **Beta**, and v1 JSONL +imports are historical records rather than resumable active Runs. Deployment, +migration, security, and operations guidance lives in +[`deploy/`](deploy/), including +[`operations-v2.md`](deploy/docs/operations-v2.md), +[`migration-v2.md`](deploy/docs/migration-v2.md), and the generated +[`openapi-v2.json`](deploy/docs/openapi-v2.json).

Multi-Agent Multi-Session Map @@ -344,6 +382,10 @@ python example/01_hello_agent.py Read [`example/README.md`](example/README.md) for setup details and shared helpers. +For complete, production-shaped scenarios with fixed inputs, durable state, QA, +and committed deliverables, see +[`Rath-Team/OpenRath-Example`](https://github.com/Rath-Team/OpenRath-Example). + --- ## Docs and Links diff --git a/README_zh.md b/README_zh.md index 87ea319..a6195ef 100644 --- a/README_zh.md +++ b/README_zh.md @@ -54,16 +54,67 @@ OpenRath 为此而设计:多个 Agent 在多个可分支 Session 上协作,同时仍能追踪每个 role、workspace、memory 写入和最终输出。 -## v2.0.0 durable runtime(候选版本) +## OpenRath v2.0.0:面向生产环境 + +OpenRath v2.0.0 最重要的变化,是 OpenRath 从一个可组合的 Python 框架, +进入可部署、可恢复、可运维的生产环境。原有以 Session 为核心的 Python API +保持不变;这个版本在其外层增加了一套生产级执行与运维体系。 + +| 生产环境关注点 | OpenRath 提供的能力 | +| --- | --- | +| 持久化执行 | 显式的 `@step` / `@router` 边界会编译成不可变执行计划;Run、Event 与 Checkpoint 能跨进程和 Worker 重启保留。 | +| Worker 故障恢复 | Lease、Fencing、Retry、Cancellation、Deadline 与可恢复队列,防止过期 Worker 静默提交新状态。 | +| 受控副作用 | Effect Ledger 记录执行结果与幂等键;无法确认的非幂等副作用会停在 `NEEDS_REVIEW`,而不是被盲目重放。 | +| 人工决策 | 持久化 Interrupt 可以暂停 Run 等待审批或输入,并在不重建隐藏循环状态的情况下恢复。 | +| 安全与租户隔离 | Agent Server Token 使用显式 Action Grant;Tenant/Project Scope、Policy、Secret Reference、Trust Label 与 Audit 保持为独立边界。 | +| 生产运维 | PostgreSQL 是持久化事实来源,Redis 可加速信号传递,S3 兼容存储保存 Artifact,并提供健康检查、迁移、遥测、容器与 Kubernetes 参考。 | + +```text +@step / @router + | + v +ExecutionPlan -> Run -> Event -> Checkpoint + | | + | +-> Interrupt / Effect Ledger + | + +-> PostgreSQL 持久化状态 + +-> 可选 Redis 信号 + +-> S3 兼容 Artifact + | + v + Agent Server HTTP + SSE +``` + +Embedded mode 仍适合可信进程内部使用。Agent Server mode 是严格的生产 +Profile: -`2.0.0rc1` 新增显式 `@step` / `@router` 执行计划、durable Run 与 -Checkpoint、effect reconciliation、tenant-scoped Agent Server API,以及受 -治理的 Provider/Tool/Sandbox/Memory adapter。HTTP contract 在 RC 阶段仍为 -**Beta**;v1 JSONL 导入仅作为历史记录,不能恢复 active Run。 +```python +runtime = LocalRuntime( + store, + effect_ledger=ledger, + production_mode=True, +) +server = AgentServer(store, runtime, auth=auth, audit_sink=audit) +``` -Embedded mode 面向可信本地进程。Agent Server mode 是严格的 durable -profile:token 必须具有显式 action grants,对象访问按 tenant/project -隔离;需要强制 deadline 时应使用 async step 或 isolated executor。 +安装生产 Profile,并将数据库 Schema 迁移作为独立操作执行: + +```bash +pip install "openrath[server,postgres]" +openrath-migrate +openrath-migrate --check +``` + +运行时身份不需要 DDL 权限。Token 必须拥有显式 Action Grant,对象访问按 +Tenant/Project 隔离;同步 Step 不能声明抢占式超时,需要强制 Deadline 时应使用 +Async Step 或隔离执行器。 + +OpenRath v2.0.0 面向生产部署,同时明确标注接口成熟度:Agent Server HTTP +接口仍为 **Beta**;v1 JSONL 导入属于历史记录,不能恢复 Active Run。部署、 +迁移、安全和运维指南位于 [`deploy/`](deploy/),包括 +[`operations-v2.md`](deploy/docs/operations-v2.md)、 +[`migration-v2.md`](deploy/docs/migration-v2.md) 和生成的 +[`openapi-v2.json`](deploy/docs/openapi-v2.json)。

多智能体多会话映射 @@ -326,6 +377,9 @@ python example/01_hello_agent.py 阅读 [`example/README.md`](example/README.md) 获取设置细节和共享 helpers。 +如需查看包含固定输入、持久化状态、质量检查和已提交交付物的完整生产化场景, +请访问 [`Rath-Team/OpenRath-Example`](https://github.com/Rath-Team/OpenRath-Example)。 + --- ## 文档与链接 diff --git a/deploy/compose/compose.yaml b/deploy/compose/compose.yaml index 650ab63..a4dc8d4 100644 --- a/deploy/compose/compose.yaml +++ b/deploy/compose/compose.yaml @@ -26,7 +26,7 @@ services: dockerfile: docker/Dockerfile image: openrath:2.0.0rc1 environment: - OPENRATH_APP: examples.v2_server_app:app + OPENRATH_APP: reference_app:app OPENRATH_POSTGRES_DSN: postgresql://openrath:${POSTGRES_PASSWORD:?set POSTGRES_PASSWORD}@postgres:5432/openrath OPENRATH_TOKEN: ${OPENRATH_TOKEN:?set OPENRATH_TOKEN} OPENRATH_TENANT_ID: ${OPENRATH_TENANT_ID:-default} @@ -61,7 +61,7 @@ services: dockerfile: docker/Dockerfile image: openrath:2.0.0rc1 entrypoint: ["openrath-worker"] - command: ["--app", "examples.v2_server_app:server"] + command: ["--app", "reference_app:server"] environment: OPENRATH_POSTGRES_DSN: postgresql://openrath:${POSTGRES_PASSWORD:?set POSTGRES_PASSWORD}@postgres:5432/openrath OPENRATH_TOKEN: ${OPENRATH_TOKEN:?set OPENRATH_TOKEN} diff --git a/deploy/kubernetes/openrath.yaml b/deploy/kubernetes/openrath.yaml index 7272c64..aea9d88 100644 --- a/deploy/kubernetes/openrath.yaml +++ b/deploy/kubernetes/openrath.yaml @@ -15,7 +15,7 @@ kind: ConfigMap metadata: name: openrath data: - OPENRATH_APP: examples.v2_server_app:app + OPENRATH_APP: reference_app:app OPENRATH_EMBEDDED_WORKER: "false" OPENRATH_DB_SCHEMA: openrath OPENRATH_TENANT_ID: default @@ -163,7 +163,7 @@ spec: image: ghcr.io/rath-team/openrath:2.0.0rc1 # Release automation must replace the review tag with image@sha256. imagePullPolicy: Always - command: ["openrath-worker", "--app", "examples.v2_server_app:server"] + command: ["openrath-worker", "--app", "reference_app:server"] envFrom: - configMapRef: name: openrath diff --git a/examples/v2_server_app.py b/deploy/reference_app.py similarity index 97% rename from examples/v2_server_app.py rename to deploy/reference_app.py index 026854c..cf09d74 100644 --- a/examples/v2_server_app.py +++ b/deploy/reference_app.py @@ -1,4 +1,4 @@ -"""Minimal standalone OpenRath v2 reference application.""" +"""Minimal deployable OpenRath v2 reference application.""" from __future__ import annotations diff --git a/docker/Dockerfile b/docker/Dockerfile index 13623f6..27e5a4a 100644 --- a/docker/Dockerfile +++ b/docker/Dockerfile @@ -32,7 +32,7 @@ RUN groupadd --system --gid 10001 openrath \ && useradd --system --uid 10001 --gid openrath --home /app openrath WORKDIR /app COPY --from=builder /opt/venv /opt/venv -COPY examples ./examples +COPY deploy/reference_app.py ./reference_app.py USER 10001:10001 EXPOSE 8000 ENTRYPOINT ["openrath-server"] diff --git a/tests/deployment/test_reference_manifests.py b/tests/deployment/test_reference_manifests.py index e949282..f59cf9c 100644 --- a/tests/deployment/test_reference_manifests.py +++ b/tests/deployment/test_reference_manifests.py @@ -28,7 +28,7 @@ def test_kubernetes_template_covers_workloads_and_dns() -> None: def test_reference_server_enables_audit_and_explicit_grants() -> None: - app = Path("examples/v2_server_app.py").read_text(encoding="utf-8") + app = Path("deploy/reference_app.py").read_text(encoding="utf-8") compose = Path("deploy/compose/compose.yaml").read_text(encoding="utf-8") assert "StructuredAuditSink()" in app assert 'os.environ["OPENRATH_GRANTS"]' in app