diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 08ebfa0..043e049 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -23,6 +23,10 @@ jobs: run: ruff check src/ tests/ - name: Ruff format check run: ruff format --check src/ tests/ + - name: Marketing version sync + # Fails if README/landing/OG-card versions drift from pyproject — + # the served social card once sat 3 minors behind silently. + run: python scripts/sync_marketing_version.py --check test: runs-on: ubuntu-latest diff --git a/README.md b/README.md index 6af2c50..b87cb61 100644 --- a/README.md +++ b/README.md @@ -16,7 +16,7 @@ An open-source project from **[NichevLabs](https://nichevlabs.com)**. **Multi-agent orchestration in plain Python.** Build agent graphs, compose pipelines with `|`, deploy with one command. No DSL, no compile step, no paid debugger. Works with OpenAI, Anthropic, Gemini, and Ollama. -> 🎉 **selectools is 1.0 — stable.** The public API is frozen; `@stable` symbols carry a 2-minor compatibility promise. Python 3.10+. Latest: [v1.2](#whats-new-in-v12) — four-stage guardrails, native structured output, and observability events. +> 🎉 **selectools is 1.0 — stable.** The public API is frozen; `@stable` symbols carry a 2-minor compatibility promise. Python 3.10+. Latest: [v1.3](#whats-new-in-v13) — tested public streaming contracts for structured-output chat agents. ### 3 Ways to Build @@ -32,6 +32,17 @@ result = AgentGraph.chain(planner, writer, reviewer).run("Write a blog post") # selectools serve agent.yaml ``` +## What's New in v1.3 + +### v1.3.0 — Streaming Contracts + +Makes `final_turn_only` structured output safe to rely on in streaming chat agents. Behaviors that integrators previously had to learn from the source are now **documented, tested public contracts** — enforced on every consumption surface: `astream()` chunks, the `stream_handler` callback, and the `selectools.serve` SSE stream. + +- **The synthesis turn never streams** — its JSON arrives only on the terminal `AgentResult` (`.content` / `.parsed`), never as chunks or through `stream_handler`. `StreamChunk(event="structured_synthesis_start")` fires once when the synthesis turn begins so clients can show a pending state. +- **`single_pass` no longer streams the structured answer** (*Changed*, `@beta` surface) — content is suppressed since it's the JSON envelope by construction; tool-call chunks still stream for activity display. Read the answer from `AgentResult.parsed`. +- **New `StreamChunk(event="structured_reuse")`** — when the converged loop answer validates and is reused, the just-streamed chunks WERE the answer; this signal lets a chat surface convert or retract the bubble. The serve SSE endpoint forwards event chunks as `{"type": "event", ...}`. +- **`should_finalize` message contract** — the predicate's `messages` view is documented: TOOL messages always carry `tool_name`, and `tool_result` holds the result text for successful runs while staying `None` for errors/denials (the supported failure discriminator). + ## What's New in v1.2 ### v1.2.0 — Tool-Boundary Guardrails Complete & Structured Synthesis Follow-ups diff --git a/docs/CLAUDE.md b/docs/CLAUDE.md index a30af61..01e8f1f 100644 --- a/docs/CLAUDE.md +++ b/docs/CLAUDE.md @@ -49,4 +49,5 @@ Every feature MUST update all of these: - CHANGELOG.md lives at repo root — must be copied into `docs/` before build - Examples gallery (`landing/examples/index.html`) must be regenerated when examples are added or edited: `python scripts/build_examples_gallery.py > landing/examples/index.html` - Hardcoded counts (model count, test count, example count) appear across many files — audit all +- **Marketing version strings** (README banner, landing status bar/footer, OG-card badges) are synced from `pyproject.toml` by `scripts/sync_marketing_version.py`. CI runs it with `--check` and fails on drift; the release flow (`release.py`) runs the write mode. After it bumps the OG **SVG**, re-render the PNG: `uv run --with playwright python scripts/render_og_image.py`. - `docs/ARCHITECTURE.md` must be updated when adding new components diff --git a/docs/assets/og-card.html b/docs/assets/og-card.html index 1c8a015..5dd9fdf 100644 --- a/docs/assets/og-card.html +++ b/docs/assets/og-card.html @@ -152,7 +152,7 @@ selectools - v1.2 · STABLE + v1.3 · STABLE
AI agents that are just Python.
diff --git a/docs/assets/og-image.svg b/docs/assets/og-image.svg index 819a3a0..5c49aa3 100644 --- a/docs/assets/og-image.svg +++ b/docs/assets/og-image.svg @@ -46,7 +46,7 @@ v1.2 · STABLE + font-weight="700" font-size="19" fill="#22d3ee">v1.3 · STABLE - v1.2.0 · Apache-2.0 · 9 providers · OpenAI · Anthropic · Gemini · Ollama · LiteLLM + v1.3.0 · Apache-2.0 · 9 providers · OpenAI · Anthropic · Gemini · Ollama · LiteLLM [•] selectools diff --git a/landing/index.html b/landing/index.html index 0b3409e..a997f5e 100644 --- a/landing/index.html +++ b/landing/index.html @@ -4461,7 +4461,7 @@

AI agents that are just Python.

115 examples
50 evaluators
9 providers
-
v1.2.0
+
v1.3.0
@@ -5840,7 +5840,7 @@

Type a question. Or browse the docs.

├── pypi/ # pip install selectools └── changelog/ # what shipped, what changed -# selectools v1.2.0 · Apache-2.0 · made by NichevLabs +# selectools v1.3.0 · Apache-2.0 · made by NichevLabs # for developers who ship