pi-agent-core-lc 0.1.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- pi_agent_core_lc-0.1.0/.cursorindexingignore +3 -0
- pi_agent_core_lc-0.1.0/.github/workflows/ci.yml +44 -0
- pi_agent_core_lc-0.1.0/.github/workflows/release.yml +112 -0
- pi_agent_core_lc-0.1.0/.gitignore +12 -0
- pi_agent_core_lc-0.1.0/AGENTS.md +74 -0
- pi_agent_core_lc-0.1.0/CHANGELOG.md +42 -0
- pi_agent_core_lc-0.1.0/LICENSE +21 -0
- pi_agent_core_lc-0.1.0/PKG-INFO +369 -0
- pi_agent_core_lc-0.1.0/README.md +325 -0
- pi_agent_core_lc-0.1.0/docs/AUDIT-2026-07-02.md +486 -0
- pi_agent_core_lc-0.1.0/docs/AUDIT-H1.md +141 -0
- pi_agent_core_lc-0.1.0/docs/AUDIT-H2.md +225 -0
- pi_agent_core_lc-0.1.0/docs/AUDIT-H3.md +186 -0
- pi_agent_core_lc-0.1.0/docs/AUDIT-H4.md +223 -0
- pi_agent_core_lc-0.1.0/docs/DESIGN.md +169 -0
- pi_agent_core_lc-0.1.0/docs/superpowers/specs/2026-05-25-phase2-production-enhancements-design.md +208 -0
- pi_agent_core_lc-0.1.0/docs/superpowers/specs/2026-07-03-p6-tool-ecosystem-design.md +300 -0
- pi_agent_core_lc-0.1.0/docs/superpowers/specs/2026-07-03-phase3-agent-harness-design.md +456 -0
- pi_agent_core_lc-0.1.0/examples/minimal_agent.py +49 -0
- pi_agent_core_lc-0.1.0/examples/production_agent.py +171 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/README.md +25 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/__init__.py +129 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/agent_harness.py +1018 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/compaction/__init__.py +43 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/compaction/compaction.py +257 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/compaction/utils.py +230 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/env.py +235 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/frontmatter.py +21 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/messages.py +151 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/prompt_templates.py +68 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/py.typed +0 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/__init__.py +34 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/jsonl_repo.py +137 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/jsonl_storage.py +327 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/memory_repo.py +58 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/memory_storage.py +149 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/repo_utils.py +34 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/session.py +320 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/session/uuid7.py +37 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/skills.py +174 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/system_prompt.py +22 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pi_agent_harness/types.py +617 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/pyproject.toml +46 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/fixtures/pi-v3-session-tree.jsonl +10 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/fixtures/pi-v3-session.jsonl +5 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/test_harness_agent.py +617 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/test_harness_compaction.py +593 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/test_harness_h4_resources_env.py +594 -0
- pi_agent_core_lc-0.1.0/packages/pi-agent-harness/tests/test_harness_session.py +536 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/__init__.py +69 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/adapters/__init__.py +12 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/adapters/langchain_convert.py +162 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/adapters/langchain_stream.py +767 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/adapters/langchain_tools.py +164 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/agent.py +450 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/agent_loop.py +777 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/__init__.py +123 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/_base.py +49 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/bash.py +474 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/edit.py +515 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/find.py +134 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/grep.py +370 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/ls.py +114 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/mutation_queue.py +38 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/output_accumulator.py +186 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/path_utils.py +107 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/read.py +139 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/truncate.py +227 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/coding_tools/write.py +71 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/event_stream.py +81 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/harness/__init__.py +127 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/messages.py +102 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/py.typed +0 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/queues.py +31 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/__init__.py +0 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/mock_stream.py +145 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_agent.py +143 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_agent_loop.py +771 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_bash.py +454 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_common.py +304 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_edit.py +210 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_factory.py +155 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_fs.py +240 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_coding_tools_search.py +285 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_convert.py +110 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_langchain_stream.py +739 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_langchain_tools.py +165 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_mock_usage.py +39 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_thinking.py +63 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_transform.py +133 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tests/test_usage.py +115 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/tools.py +34 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/transform.py +141 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/types.py +467 -0
- pi_agent_core_lc-0.1.0/pi_agent_core/validation.py +29 -0
- pi_agent_core_lc-0.1.0/plan.md +317 -0
- pi_agent_core_lc-0.1.0/pyproject.toml +81 -0
- pi_agent_core_lc-0.1.0/scripts/smoke_real_api.py +263 -0
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
branches: [main]
|
|
6
|
+
pull_request:
|
|
7
|
+
|
|
8
|
+
concurrency:
|
|
9
|
+
group: ${{ github.workflow }}-${{ github.ref }}
|
|
10
|
+
cancel-in-progress: true
|
|
11
|
+
|
|
12
|
+
jobs:
|
|
13
|
+
lint:
|
|
14
|
+
name: Ruff (lint + format)
|
|
15
|
+
runs-on: ubuntu-latest
|
|
16
|
+
steps:
|
|
17
|
+
- uses: actions/checkout@v7
|
|
18
|
+
- uses: actions/setup-python@v6
|
|
19
|
+
with:
|
|
20
|
+
python-version: "3.12"
|
|
21
|
+
- name: Install ruff
|
|
22
|
+
run: pip install "ruff==0.16.0"
|
|
23
|
+
- name: Lint
|
|
24
|
+
run: ruff check --output-format=github .
|
|
25
|
+
- name: Format check
|
|
26
|
+
run: ruff format --check .
|
|
27
|
+
|
|
28
|
+
test:
|
|
29
|
+
name: pytest (Python ${{ matrix.python-version }})
|
|
30
|
+
runs-on: ubuntu-latest
|
|
31
|
+
strategy:
|
|
32
|
+
fail-fast: false
|
|
33
|
+
matrix:
|
|
34
|
+
python-version: ["3.11", "3.12", "3.13"]
|
|
35
|
+
steps:
|
|
36
|
+
- uses: actions/checkout@v7
|
|
37
|
+
- uses: actions/setup-python@v6
|
|
38
|
+
with:
|
|
39
|
+
python-version: ${{ matrix.python-version }}
|
|
40
|
+
cache: pip
|
|
41
|
+
- name: Install packages (dev)
|
|
42
|
+
run: pip install -e ".[dev]" -e "./packages/pi-agent-harness"
|
|
43
|
+
- name: Run tests
|
|
44
|
+
run: pytest -v
|
|
@@ -0,0 +1,112 @@
|
|
|
1
|
+
name: Release
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
tags:
|
|
6
|
+
- "v*"
|
|
7
|
+
|
|
8
|
+
permissions:
|
|
9
|
+
contents: write
|
|
10
|
+
|
|
11
|
+
jobs:
|
|
12
|
+
test:
|
|
13
|
+
name: Pre-release tests
|
|
14
|
+
runs-on: ubuntu-latest
|
|
15
|
+
steps:
|
|
16
|
+
- uses: actions/checkout@v7
|
|
17
|
+
- uses: actions/setup-python@v6
|
|
18
|
+
with:
|
|
19
|
+
python-version: "3.12"
|
|
20
|
+
cache: pip
|
|
21
|
+
- name: Install packages (dev)
|
|
22
|
+
run: pip install -e ".[dev]" -e "./packages/pi-agent-harness"
|
|
23
|
+
- name: Run tests
|
|
24
|
+
run: pytest -v
|
|
25
|
+
- name: Lint
|
|
26
|
+
run: |
|
|
27
|
+
pip install "ruff==0.16.0"
|
|
28
|
+
ruff check .
|
|
29
|
+
ruff format --check .
|
|
30
|
+
|
|
31
|
+
build:
|
|
32
|
+
name: Build packages
|
|
33
|
+
needs: test
|
|
34
|
+
runs-on: ubuntu-latest
|
|
35
|
+
steps:
|
|
36
|
+
- uses: actions/checkout@v7
|
|
37
|
+
- uses: actions/setup-python@v6
|
|
38
|
+
with:
|
|
39
|
+
python-version: "3.12"
|
|
40
|
+
|
|
41
|
+
- name: Install build tools
|
|
42
|
+
run: pip install build
|
|
43
|
+
|
|
44
|
+
- name: Build pi-agent-core
|
|
45
|
+
run: python -m build --outdir dist/
|
|
46
|
+
|
|
47
|
+
- name: Build pi-agent-harness
|
|
48
|
+
run: python -m build --outdir dist/ packages/pi-agent-harness
|
|
49
|
+
|
|
50
|
+
- uses: actions/upload-artifact@v4
|
|
51
|
+
with:
|
|
52
|
+
name: dist
|
|
53
|
+
path: dist/
|
|
54
|
+
|
|
55
|
+
publish-pypi:
|
|
56
|
+
name: Publish to PyPI
|
|
57
|
+
needs: build
|
|
58
|
+
runs-on: ubuntu-latest
|
|
59
|
+
environment: pypi
|
|
60
|
+
steps:
|
|
61
|
+
- uses: actions/download-artifact@v4
|
|
62
|
+
with:
|
|
63
|
+
name: dist
|
|
64
|
+
path: dist/
|
|
65
|
+
|
|
66
|
+
- name: Publish to PyPI
|
|
67
|
+
uses: pypa/gh-action-pypi-publish@release/v1
|
|
68
|
+
with:
|
|
69
|
+
password: ${{ secrets.PYPI_API_TOKEN }}
|
|
70
|
+
|
|
71
|
+
github-release:
|
|
72
|
+
name: GitHub Release
|
|
73
|
+
needs: build
|
|
74
|
+
runs-on: ubuntu-latest
|
|
75
|
+
permissions:
|
|
76
|
+
contents: write
|
|
77
|
+
steps:
|
|
78
|
+
- uses: actions/checkout@v7
|
|
79
|
+
|
|
80
|
+
- uses: actions/download-artifact@v4
|
|
81
|
+
with:
|
|
82
|
+
name: dist
|
|
83
|
+
path: dist/
|
|
84
|
+
|
|
85
|
+
- name: Extract version from tag
|
|
86
|
+
id: version
|
|
87
|
+
run: echo "version=${GITHUB_REF#refs/tags/v}" >> "$GITHUB_OUTPUT"
|
|
88
|
+
|
|
89
|
+
- name: Extract changelog for this version
|
|
90
|
+
id: changelog
|
|
91
|
+
run: |
|
|
92
|
+
# Extract the section for current version from CHANGELOG.md
|
|
93
|
+
version="${{ steps.version.outputs.version }}"
|
|
94
|
+
body=$(awk -v ver="$version" '
|
|
95
|
+
/^## \[/ {
|
|
96
|
+
if (found) exit
|
|
97
|
+
if (index($0, "[" ver "]")) found=1
|
|
98
|
+
next
|
|
99
|
+
}
|
|
100
|
+
found { print }
|
|
101
|
+
' CHANGELOG.md)
|
|
102
|
+
# Write to file to preserve newlines
|
|
103
|
+
echo "$body" > /tmp/release-body.md
|
|
104
|
+
|
|
105
|
+
- name: Create GitHub Release
|
|
106
|
+
env:
|
|
107
|
+
GH_TOKEN: ${{ github.token }}
|
|
108
|
+
run: |
|
|
109
|
+
gh release create "${{ github.ref_name }}" \
|
|
110
|
+
--title "pi-python ${{ github.ref_name }}" \
|
|
111
|
+
--notes-file /tmp/release-body.md \
|
|
112
|
+
dist/*
|
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
# AGENTS.md
|
|
2
|
+
|
|
3
|
+
## Project overview
|
|
4
|
+
|
|
5
|
+
`pi-python` is an unofficial Python port inspired by [`@earendil-works/pi-agent-core`](https://github.com/earendil-works/pi), with **LangChain replacing the `pi-ai` LLM layer**. It is not affiliated with or endorsed by the official `pi` project. Full design: `docs/DESIGN.md`; Phase 2 spec: `docs/superpowers/specs/2026-05-25-phase2-production-enhancements-design.md`; Phase 3 harness spec: `docs/superpowers/specs/2026-07-03-phase3-agent-harness-design.md`; P6 tool-ecosystem spec: `docs/superpowers/specs/2026-07-03-p6-tool-ecosystem-design.md`; audit tracker: `docs/AUDIT-2026-07-02.md`.
|
|
6
|
+
|
|
7
|
+
Guiding principles:
|
|
8
|
+
|
|
9
|
+
- **Faithfully port pi's loop semantics.** The TS sources (`packages/agent/src/agent-loop.ts` / `agent.ts` upstream) are the reference; when in doubt, match their behavior.
|
|
10
|
+
- **LangChain is only a `StreamFn` boundary adapter.** Tool execution, turn management, and the event protocol live in `agent_loop.py` — never delegate them to LangChain agents/ToolNode.
|
|
11
|
+
|
|
12
|
+
### Architecture
|
|
13
|
+
|
|
14
|
+
```
|
|
15
|
+
AgentMessage[] → transform_context() → convert_to_llm() → LangChain BaseMessage[]
|
|
16
|
+
↓
|
|
17
|
+
stream_fn (LangChain astream)
|
|
18
|
+
↓
|
|
19
|
+
AssistantMessageEvent → AgentEvent
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
### Module map
|
|
23
|
+
|
|
24
|
+
| Module | Role | pi (TS) counterpart |
|
|
25
|
+
|--------|------|---------------------|
|
|
26
|
+
| `pi_agent_core/messages.py` | Canonical messages (user/assistant/toolResult), content blocks, `Usage` | `pi-ai` messages |
|
|
27
|
+
| `pi_agent_core/types.py` | `Model`, `AgentTool`, contexts, event types, `AgentLoopConfig` | `packages/agent/src/types.ts` |
|
|
28
|
+
| `pi_agent_core/event_stream.py` | `EventStream` / `AssistantMessageEventStream` | `pi-ai` EventStream |
|
|
29
|
+
| `pi_agent_core/agent_loop.py` | Core loop: turns, tool execution, hooks, event emission | `packages/agent/src/agent-loop.ts` |
|
|
30
|
+
| `pi_agent_core/agent.py` | Stateful `Agent` wrapper: prompt/steer/follow-up queues, abort | `packages/agent/src/agent.ts` |
|
|
31
|
+
| `pi_agent_core/adapters/langchain_convert.py`, `langchain_stream.py` | pi ⇄ LangChain conversion; `StreamFn` over `astream()` | `packages/ai/src/stream.ts` |
|
|
32
|
+
| `pi_agent_core/transform.py` | Cross-provider replay (tool-call id normalization, thinking downgrade, image stripping) | `pi-ai` transforms |
|
|
33
|
+
| `pi_agent_core/tools.py`, `validation.py`, `queues.py` | `SimpleTool` helper, argument validation, steering/follow-up queues | — |
|
|
34
|
+
| `pi_agent_core/coding_tools/`, `adapters/langchain_tools.py` | Built-in coding tools (all 7: `read`/`bash`/`edit`/`write`/`grep`/`find`/`ls`) + LangChain tool adapter | pi coding-agent built-in tools |
|
|
35
|
+
| `packages/pi-agent-harness/pi_agent_harness` | Phase 3 harness package: sessions, AgentHarness, compaction, skills/templates, LocalExecutionEnv | `packages/agent/src/harness/` |
|
|
36
|
+
|
|
37
|
+
### Invariants (do not break)
|
|
38
|
+
|
|
39
|
+
1. **Event contract** — `prompt()` without tools emits exactly: `agent_start → turn_start → message_start(user) → message_end(user) → message_start(assistant) → message_update* → message_end(assistant) → turn_end → agent_end`. With tools, `tool_execution_*` and `toolResult` message events are inserted after `message_end(assistant)`, possibly across multiple turns.
|
|
40
|
+
2. **Parallel tool ordering** — `tool_execution_end` fires in **completion order**; `toolResult` messages persist in tool-call **source order**.
|
|
41
|
+
3. **terminate semantics** — skip the next LLM turn only when **all** finalized tool results in the batch have `terminate=True`.
|
|
42
|
+
4. **StreamFn contract** — never raises to the caller; failures are encoded as an `error` event with `stop_reason=error|aborted`.
|
|
43
|
+
5. **Thinking/reasoning gating** — reasoning params are injected iff `Model.reasoning=True` **and** `thinking_level != "off"`; the same flag drives thinking-history stripping in `transform_messages`, keeping request params and message replay consistent.
|
|
44
|
+
6. **Usage accumulation is per-field max, not sum** — real providers report usage as a single final report, complementary splits (Anthropic), or cumulative per-chunk snapshots (SiliconFlow/vLLM gateways); summing inflates the last shape by orders of magnitude.
|
|
45
|
+
7. **Structured output must not break streaming** — `response_schema` works via prompt injection + native `response_format` (OpenAI-style); never switch to `with_structured_output` (it replaces `AIMessageChunk` streaming and kills the event protocol).
|
|
46
|
+
|
|
47
|
+
### Status
|
|
48
|
+
|
|
49
|
+
Phase 1 (MVP loop), Phase 2 (usage/cost, thinking/reasoning, transform_messages), Phase 2.5 (retries/backoff, `max_turns`/`tool_timeout`, observability, guardrail hooks, `ContextBudget`, structured output, `Model.base_url` + `deepseek` provider), and Phase 3 H1-H4 (`pi-agent-harness`: session tree, AgentHarness runtime, compaction/tree navigation, skills/templates/system prompt/LocalExecutionEnv) are complete. Real-API smoke (`scripts/smoke_real_api.py`) passed against SiliconFlow (OpenAI-compatible). P6 tool ecosystem (`pi_agent_core/coding_tools/` + `adapters/langchain_tools.py`) is complete: all 7 built-in tools (`read`/`bash`/`edit`/`write`/`grep`/`find`/`ls`), group factories (`create_coding_tools` / `create_read_only_tools`), and the LangChain `BaseTool` adapter — see `docs/superpowers/specs/2026-07-03-p6-tool-ecosystem-design.md`. H1 session-layer audit (`docs/AUDIT-H1.md`) is fully closed as of 2026-07-28 (H1-5 `fromId` pi alignment, H1-6 repo list/delete semantics, H1-8 nits incl. hyphenated uuid7 + random-tail short ids). H2 harness audit (`docs/AUDIT-H2.md`) implementation backlog closed as of 2026-07-29. Current test count: 327.
|
|
50
|
+
|
|
51
|
+
## Cursor Cloud specific instructions
|
|
52
|
+
|
|
53
|
+
This is a Python monorepo with `pi-agent-core` and `pi-agent-harness`. There are no services to start — packages are installed in editable mode and tested via `pytest`.
|
|
54
|
+
|
|
55
|
+
### Key commands
|
|
56
|
+
|
|
57
|
+
| Action | Command |
|
|
58
|
+
|--------|---------|
|
|
59
|
+
| Install (dev) | `pip install -e ".[dev]" -e "./packages/pi-agent-harness"` |
|
|
60
|
+
| Lint check | `ruff check .` |
|
|
61
|
+
| Format check | `ruff format --check .` |
|
|
62
|
+
| Auto-fix lint | `ruff check --fix .` |
|
|
63
|
+
| Auto-format | `ruff format .` |
|
|
64
|
+
| Run tests | `pytest` (or `pytest -v` for verbose) |
|
|
65
|
+
| Run example (no API key) | `PI_USE_MOCK=1 python3 examples/minimal_agent.py` |
|
|
66
|
+
|
|
67
|
+
### Notes
|
|
68
|
+
|
|
69
|
+
- **Ruff** is the linter and formatter. Config is in `pyproject.toml` under `[tool.ruff]`. Rules enabled: E, F, I, UP, B, SIM, RUF. Line length: 100. Target: Python 3.11.
|
|
70
|
+
- **`python` is not on PATH** — always use `python3`.
|
|
71
|
+
- `pytest` and other scripts install to `~/.local/bin`. Ensure `PATH` includes this directory (it should already be on PATH in most shells, but if `pytest` is not found, run `export PATH="$HOME/.local/bin:$PATH"`).
|
|
72
|
+
- All tests use a mock stream (`pi_agent_core/tests/mock_stream.py`) — **no API keys are needed** to run the test suite or the mock example.
|
|
73
|
+
- `asyncio_mode = "auto"` is set in `pyproject.toml`, so async test functions are automatically detected by `pytest-asyncio`.
|
|
74
|
+
- On a local Windows machine where the system Python is older than 3.11, create a dedicated venv instead of forcing compatibility: `uv venv --python 3.12 .venv-audit && uv pip install --python .venv-audit -e ".[dev]" -e "./packages/pi-agent-harness"` (the harness package must be installed too, or its tests fail to collect).
|
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## [0.1.0] - 2026-08-05
|
|
9
|
+
|
|
10
|
+
Initial public release.
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
|
|
14
|
+
#### pi-agent-core
|
|
15
|
+
|
|
16
|
+
- **Core runtime (Phase 1)**: `Agent` with steering/follow-up queues, abort, `subscribe()` event barrier; `agent_loop` with pi-compatible event protocol, parallel/sequential tool execution, `terminate` semantics.
|
|
17
|
+
- **LangChain adapter**: `StreamFn` over `astream()` for OpenAI / Anthropic / DeepSeek / any `init_chat_model` provider; mock stream for tests (no API keys needed).
|
|
18
|
+
- **Production hardening (Phase 2/2.5)**:
|
|
19
|
+
- Cross-provider message replay (`transform_messages`: tool-call id normalization, thinking downgrade, image stripping).
|
|
20
|
+
- Usage & cost tracking with `CostCalculator`.
|
|
21
|
+
- Thinking/reasoning: provider param mapping, streamed `thinking_delta` events, Anthropic signature replay, DeepSeek-style `reasoning_content`.
|
|
22
|
+
- Stream-level retries with exponential backoff + jitter, `Retry-After` aware.
|
|
23
|
+
- Runaway protection: `max_turns` / `tool_timeout`.
|
|
24
|
+
- Guardrail hooks: `before_llm_call` (with `ContextBudget`), `after_llm_call`, `on_agent_end`.
|
|
25
|
+
- Observability: `on_payload` / `on_response` hooks; `run_id` / `turn_id` on every event.
|
|
26
|
+
- Granular stream events: `text_start/end`, `thinking_start/end`, `toolcall_start/end`.
|
|
27
|
+
- Structured output: `response_schema` (Pydantic model or JSON schema).
|
|
28
|
+
- Tool-result images: Anthropic native blocks, user-message fallback elsewhere.
|
|
29
|
+
- OpenAI-compatible gateways via `Model.base_url`.
|
|
30
|
+
- **Tool ecosystem (P6)**:
|
|
31
|
+
- 7 built-in coding tools: `read`, `bash`, `edit`, `write`, `grep`, `find`, `ls`.
|
|
32
|
+
- Group factories: `create_coding_tools()` / `create_read_only_tools()`.
|
|
33
|
+
- LangChain `BaseTool` → `AgentTool` adapter (`from_langchain_tool`).
|
|
34
|
+
|
|
35
|
+
#### pi-agent-harness
|
|
36
|
+
|
|
37
|
+
- **Session tree (H1)**: `SessionRepo` with filesystem storage, `uuid7` IDs, branch/fork semantics, message append/list.
|
|
38
|
+
- **AgentHarness runtime (H2)**: orchestration layer over `Agent`, queue rollback, abort aggregation, event-based idle wait.
|
|
39
|
+
- **Compaction & tree navigation (H3)**: token-based compaction with branch summaries, `navigate_tree` for branch exploration.
|
|
40
|
+
- **Skills, templates & env (H4)**: skill discovery, prompt templates, system prompt injection, `LocalExecutionEnv` for sandboxed execution.
|
|
41
|
+
|
|
42
|
+
[0.1.0]: https://github.com/zy1233/pi-python/releases/tag/v0.1.0
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2026 zy1233
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|