Skip to content

Commit cbe97e2

Browse files
authored
Merge pull request #3 from Agent-Field/feature/e65cddc0-swe-fast-reasoner
feat: add swe-fast lightweight speed-optimized reasoner agent
2 parents 15342a0 + 9202adc commit cbe97e2

29 files changed

+9030
-0
lines changed

.gitignore

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -39,3 +39,12 @@ Thumbs.db
3939

4040
# Claude Code
4141
.claude/
42+
43+
# Python packaging / dist
44+
dist/
45+
build/
46+
*.egg-info/
47+
*.egg
48+
49+
# Pipeline output files
50+
.claude_output_*.json

docker-compose.yml

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,30 @@ services:
3535
deploy:
3636
replicas: 1 # Scale with: docker compose up --scale swe-agent=3
3737

38+
swe-fast:
39+
build:
40+
context: .
41+
dockerfile: Dockerfile
42+
command: ["python", "-m", "swe_af.fast"]
43+
environment:
44+
- AGENTFIELD_SERVER=http://control-plane:8080
45+
- NODE_ID=swe-fast
46+
- PORT=8004
47+
- AGENT_CALLBACK_URL=http://swe-fast:8004
48+
- ANTHROPIC_API_KEY=${ANTHROPIC_API_KEY}
49+
- CLAUDE_CODE_OAUTH_TOKEN=${CLAUDE_CODE_OAUTH_TOKEN}
50+
- GH_TOKEN=${GH_TOKEN}
51+
- OPENROUTER_API_KEY=${OPENROUTER_API_KEY:-}
52+
- OPENAI_API_KEY=${OPENAI_API_KEY:-}
53+
- GOOGLE_API_KEY=${GOOGLE_API_KEY:-}
54+
- OPENCODE_MODEL=${OPENCODE_MODEL:-}
55+
ports:
56+
- "8004:8004"
57+
volumes:
58+
- workspaces:/workspaces
59+
depends_on:
60+
- control-plane
61+
3862
volumes:
3963
agentfield-data:
4064
workspaces:

pyproject.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ dev = ["pytest", "ruff"]
1414

1515
[project.scripts]
1616
swe-af = "swe_af.app:main"
17+
swe-fast = "swe_af.fast.app:main"
1718

1819
[tool.setuptools.packages.find]
1920
include = ["swe_af*"]

swe_af/fast/__init__.py

Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,150 @@
1+
"""swe_af.fast — speed-optimised single-pass build node.
2+
3+
Exports
4+
-------
5+
fast_router : AgentRouter
6+
Router tagged ``'swe-fast'`` with the five execution-phase thin wrappers
7+
registered: run_git_init, run_coder, run_verifier, run_repo_finalize,
8+
run_github_pr.
9+
10+
Intentionally does NOT import ``swe_af.reasoners.pipeline`` (nor trigger it
11+
via ``swe_af.reasoners.__init__``) so that planning agents (run_architect,
12+
run_tech_lead, run_sprint_planner, run_product_manager, run_issue_writer) are
13+
never loaded into this process. The execution_agents module is imported lazily
14+
inside each wrapper to honour this contract.
15+
"""
16+
17+
from __future__ import annotations
18+
19+
from agentfield import AgentRouter
20+
21+
fast_router = AgentRouter(tags=["swe-fast"])
22+
23+
24+
# ---------------------------------------------------------------------------
25+
# Thin wrappers — each uses a lazy import to avoid loading
26+
# swe_af.reasoners.__init__ (which would pull in pipeline.py).
27+
# ---------------------------------------------------------------------------
28+
29+
30+
@fast_router.reasoner()
31+
async def run_git_init(
32+
repo_path: str,
33+
goal: str,
34+
artifacts_dir: str = "",
35+
model: str = "sonnet",
36+
permission_mode: str = "",
37+
ai_provider: str = "claude",
38+
previous_error: str | None = None,
39+
build_id: str = "",
40+
) -> dict:
41+
"""Thin wrapper around execution_agents.run_git_init."""
42+
import swe_af.reasoners.execution_agents as _ea # noqa: PLC0415
43+
return await _ea.run_git_init(
44+
repo_path=repo_path, goal=goal, artifacts_dir=artifacts_dir,
45+
model=model, permission_mode=permission_mode, ai_provider=ai_provider,
46+
previous_error=previous_error, build_id=build_id,
47+
)
48+
49+
50+
@fast_router.reasoner()
51+
async def run_coder(
52+
issue: dict,
53+
worktree_path: str,
54+
feedback: str = "",
55+
iteration: int = 1,
56+
iteration_id: str = "",
57+
project_context: dict | None = None,
58+
memory_context: dict | None = None,
59+
model: str = "sonnet",
60+
permission_mode: str = "",
61+
ai_provider: str = "claude",
62+
) -> dict:
63+
"""Thin wrapper around execution_agents.run_coder."""
64+
import swe_af.reasoners.execution_agents as _ea # noqa: PLC0415
65+
return await _ea.run_coder(
66+
issue=issue, worktree_path=worktree_path, feedback=feedback,
67+
iteration=iteration, iteration_id=iteration_id,
68+
project_context=project_context, memory_context=memory_context,
69+
model=model, permission_mode=permission_mode, ai_provider=ai_provider,
70+
)
71+
72+
73+
@fast_router.reasoner()
74+
async def run_verifier(
75+
prd: dict,
76+
repo_path: str,
77+
artifacts_dir: str,
78+
completed_issues: list[dict] | None = None,
79+
failed_issues: list[dict] | None = None,
80+
skipped_issues: list[str] | None = None,
81+
model: str = "sonnet",
82+
permission_mode: str = "",
83+
ai_provider: str = "claude",
84+
) -> dict:
85+
"""Thin wrapper around execution_agents.run_verifier."""
86+
import swe_af.reasoners.execution_agents as _ea # noqa: PLC0415
87+
return await _ea.run_verifier(
88+
prd=prd, repo_path=repo_path, artifacts_dir=artifacts_dir,
89+
completed_issues=completed_issues or [], failed_issues=failed_issues or [],
90+
skipped_issues=skipped_issues or [],
91+
model=model, permission_mode=permission_mode, ai_provider=ai_provider,
92+
)
93+
94+
95+
@fast_router.reasoner()
96+
async def run_repo_finalize(
97+
repo_path: str,
98+
artifacts_dir: str = "",
99+
model: str = "sonnet",
100+
permission_mode: str = "",
101+
ai_provider: str = "claude",
102+
) -> dict:
103+
"""Thin wrapper around execution_agents.run_repo_finalize."""
104+
import swe_af.reasoners.execution_agents as _ea # noqa: PLC0415
105+
return await _ea.run_repo_finalize(
106+
repo_path=repo_path, artifacts_dir=artifacts_dir,
107+
model=model, permission_mode=permission_mode, ai_provider=ai_provider,
108+
)
109+
110+
111+
@fast_router.reasoner()
112+
async def run_github_pr(
113+
repo_path: str,
114+
integration_branch: str,
115+
base_branch: str,
116+
goal: str,
117+
build_summary: str = "",
118+
completed_issues: list[dict] | None = None,
119+
accumulated_debt: list[dict] | None = None,
120+
artifacts_dir: str = "",
121+
model: str = "sonnet",
122+
permission_mode: str = "",
123+
ai_provider: str = "claude",
124+
) -> dict:
125+
"""Thin wrapper around execution_agents.run_github_pr."""
126+
import swe_af.reasoners.execution_agents as _ea # noqa: PLC0415
127+
return await _ea.run_github_pr(
128+
repo_path=repo_path, integration_branch=integration_branch,
129+
base_branch=base_branch, goal=goal, build_summary=build_summary,
130+
completed_issues=completed_issues, accumulated_debt=accumulated_debt,
131+
artifacts_dir=artifacts_dir, model=model,
132+
permission_mode=permission_mode, ai_provider=ai_provider,
133+
)
134+
135+
136+
from . import executor # noqa: E402, F401 — registers fast_execute_tasks
137+
from . import planner # noqa: E402, F401 — registers fast_plan_tasks
138+
from . import verifier # noqa: E402, F401 — registers fast_verify
139+
140+
__all__ = [
141+
"fast_router",
142+
"run_git_init",
143+
"run_coder",
144+
"run_verifier",
145+
"run_repo_finalize",
146+
"run_github_pr",
147+
"executor",
148+
"planner",
149+
"verifier",
150+
]

swe_af/fast/__main__.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
"""Allow: python -m swe_af.fast"""
2+
from swe_af.fast.app import main
3+
4+
main()

0 commit comments

Comments
 (0)