Update rollup, minimatch, ajv, and lodash to patched versions
via npm audit fix (2 high, 2 moderate → 0 vulnerabilities).
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add a new scaffold system that lets users choose a project template
(blank or agentic starter) during project creation. This inserts a
template selection step between folder selection and spec method choice.
Backend:
- New server/routers/scaffold.py with SSE streaming endpoint for
running hardcoded scaffold commands (npx create-agentic-app)
- Path validation, security checks, and cross-platform npx resolution
- Registered scaffold_router in server/main.py and routers/__init__.py
Frontend (NewProjectModal.tsx):
- New "template" step with Blank Project and Agentic Starter cards
- Real-time scaffold output streaming with auto-scroll log viewer
- Success, error, and retry states with proper back-navigation
- Updated step flow: name → folder → template → method → chat/complete
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The Claude Code CLI v2.1.45+ emits a `rate_limit_event` message type that
the Python SDK v0.1.19 cannot parse, raising MessageParseError. Two bugs
resulted:
1. **False-positive rate limit**: check_rate_limit_error() matched
"rate_limit" in the exception string "Unknown message type:
rate_limit_event" via both an explicit type check and a regex fallback,
triggering 15-19s backoff + query re-send on every session.
2. **One-message-behind**: The MessageParseError killed the
receive_response() async generator, but the CLI subprocess was still
alive with buffered response data. Catching and returning meant the
response was never consumed. The next send_message() would read the
previous response first, creating a one-behind offset.
Changes:
- chat_constants.py: check_rate_limit_error() now returns (False, None)
for any MessageParseError, blocking both false-positive paths. Added
safe_receive_response() helper that retries receive_response() on
MessageParseError — the SDK's decoupled producer/consumer architecture
(anyio memory channel) allows the new generator to continue reading
remaining messages without data loss. Removed calculate_rate_limit_backoff
re-export and MAX_CHAT_RATE_LIMIT_RETRIES constant.
- spec_chat_session.py, assistant_chat_session.py, expand_chat_session.py:
Replaced retry-with-backoff loops with safe_receive_response() wrapper.
Removed asyncio.sleep backoff, query re-send, and rate_limited yield.
Cleaned up unused imports (asyncio, calculate_rate_limit_backoff,
MAX_CHAT_RATE_LIMIT_RETRIES).
- agent.py: Added inner retry loop around receive_response() with same
MessageParseError skip-and-restart pattern. Removed early-return that
truncated responses.
- types.ts: Removed SpecChatRateLimitedMessage,
AssistantChatRateLimitedMessage, and their union entries.
- useSpecChat.ts, useAssistantChat.ts, useExpandChat.ts: Removed dead
'rate_limited' case handlers.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
The Claude CLI sends `rate_limit_event` messages that the SDK's
`parse_message()` doesn't recognize, raising `MessageParseError` and
crashing all three chat session types (spec, assistant, expand).
Changes:
- Bump claude-agent-sdk minimum from 0.1.0 to 0.1.39
- Add `check_rate_limit_error()` helper in chat_constants.py that
detects rate limits from both MessageParseError data payloads and
error message text patterns
- Wrap `receive_response()` loops in all three `_query_claude()` methods
with retry-on-rate-limit logic (up to 3 retries with backoff)
- Gracefully log and skip non-rate-limit MessageParseError instead of
crashing the session
- Add `rate_limited` message type to frontend TypeScript types and
handle it in useSpecChat, useAssistantChat, useExpandChat hooks to
show "Rate limited. Retrying in Xs..." system messages
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Create VISION.md establishing AutoForge as a Claude Agent SDK wrapper
exclusively, rejecting integrations with other AI SDKs/CLIs/platforms
- Update review-pr.md step 6 to make vision deviation a merge blocker
(previously informational only) and auto-reject PRs modifying VISION.md
- Add .claude/launch.json with backend (uvicorn) and frontend (Vite)
dev server configurations
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Validate select option structure (value/label keys, non-empty strings)
and reject options on non-select field types.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add merge conflict detection as step 2 in PR review command, surfacing
conflicts early before the rest of the review proceeds
- Refine merge recommendations: always fix issues on the PR branch before
merging rather than merging first and fixing on main afterward
- Update verdict definitions (MERGE / MERGE after fixes / DON'T MERGE)
with clearer action guidance for each outcome
- Add GLM 5 model to the GLM API provider in registry
- Clean up ui/package-lock.json (remove unnecessary peer flags)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
A) Graph view: add needs_human_input bucket to handleGraphNodeClick so
clicking blocked nodes opens the feature modal
B) MCP validation: validate field type enum, require options for select,
enforce unique non-empty field IDs and labels
C) Progress fallback: include needs_human_input in non-WebSocket total
D) WebSocket: track needs_human_input count in progress state
E) Cleanup guard: remove unnecessary needs_human_input check in
_cleanup_stale_features (resolved via merge conflict)
F) Defensive SQL: require in_progress=1 in feature_request_human_input
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Follow-up fixes after merging PR #183 (graceful pause/drain mode):
- process_manager: _stream_output finally block now transitions from
pausing/paused_graceful to crashed/stopped (not just running), and
cleans up the drain signal file on process exit
- App.tsx: block Reset button and R shortcut during pausing/paused_graceful
- AgentThought/ProgressDashboard: keep thought bubble visible while pausing
- OrchestratorAvatar: add draining/paused cases to animation, glow, and
description switch statements
- AgentMissionControl: show Draining/Paused badge text for new states
- registry.py: remove redundant type annotation to fix mypy no-redef
- process_manager.py: add type:ignore for SQLAlchemy Column assignment
- websocket.py: reclassify test-pass lines as 'testing' not 'success'
- review-pr.md: add post-review recommended action guidance
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Set unique PLAYWRIGHT_CLI_SESSION environment variable for each spawned
agent subprocess to prevent concurrent agents from sharing a single
browser instance and interfering with each other's navigation.
- _spawn_coding_agent: session named "coding-{feature_id}"
- _spawn_coding_agent_batch: session named "coding-{primary_id}"
- _spawn_testing_agent: session named "testing-{counter}" using an
incrementing counter (since multiple testing agents can test
overlapping features, feature ID alone isn't sufficient)
Previously, after migrating from Playwright MCP to CLI, all parallel
agents shared the default browser session, causing them to navigate
away from each other's pages.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add feature_get_ready, feature_get_blocked, and feature_get_graph to
CODING_AGENT_TOOLS, TESTING_AGENT_TOOLS, and INITIALIZER_AGENT_TOOLS.
These read-only tools were available on the MCP server but blocked by
the allowed_tools lists, causing "blocked/not allowed" errors when
agents tried to query project state.
Fix SettingsModal custom base URL input:
- Remove fallback to current settings value when saving, so empty input
is not silently replaced with the existing URL
- Remove .trim() on the input value to prevent cursor jumping while typing
- Fix "Change" button pre-fill using empty string instead of space
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Major changes across 21 files (755 additions, 196 deletions):
Browser Automation Migration:
- Add versioned project migration system (prompts.py) with content-based
detection and section-level regex replacement for coding/testing prompts
- Migrate STEP 5 (browser verification) and BROWSER AUTOMATION sections
in coding prompt template to use playwright-cli commands
- Migrate STEP 2 and AVAILABLE TOOLS sections in testing prompt template
- Migration auto-runs at agent startup (autonomous_agent_demo.py), copies
playwright-cli skill, scaffolds .playwright/cli.config.json, updates
.gitignore, and stamps .migration_version file
- Add playwright-cli command validation to security allowlist (security.py)
with tests for allowed subcommands and blocked eval/run-code
Headless Browser Setting Fix:
- Add _apply_playwright_headless() to process_manager.py that reads/updates
.playwright/cli.config.json before agent subprocess launch
- Remove dead PLAYWRIGHT_HEADLESS env var that was never consumed
- Settings UI toggle now correctly controls visible browser window
Playwright CLI Auto-Install:
- Add ensurePlaywrightCli() to lib/cli.js for npm global entry point
- Add playwright-cli detection + npm install to start.bat, start.sh,
start_ui.bat, start_ui.sh for all startup paths
Other Improvements:
- Add project folder path tooltip to ProjectSelector.tsx dropdown items
- Remove legacy Playwright MCP server configuration from client.py
- Update CLAUDE.md with playwright-cli skill documentation
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
- Add "Azure Anthropic (Claude)" to API_PROVIDERS in registry.py
with ANTHROPIC_API_KEY auth (required for Claude CLI to route
through custom base URL instead of default Anthropic endpoint)
- Add Azure env var template to .env.example
- Show Base URL input field for Azure provider in Settings UI
with "Configured" state and Azure-specific placeholder
- Widen Settings modal for better readability with long URLs
- Add Azure endpoint detection and "Azure Mode" log label
- Rename misleading "GLM Mode" fallback label to "Alternative API"
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Address three issues reported after overnight AutoForge runs:
1. ~193GB of .node files in %TEMP% from V8 compile caching
2. Stale npm artifact folders on drive root when %TEMP% fills up
3. PNG screenshot files left in project root by Playwright
Changes:
- Widen .node cleanup glob from ".78912*.node" to ".[0-9a-f]*.node"
to match all V8 compile cache hex prefixes
- Add "node-compile-cache" directory to temp cleanup patterns
- Set NODE_COMPILE_CACHE="" in all subprocess environments (client.py,
parallel_orchestrator.py, process_manager.py) to disable V8 compile
caching at the source
- Add cleanup_project_screenshots() to remove stale .png files from
project directories (feature*-*.png, screenshot-*.png, step-*.png)
- Run cleanup_stale_temp() at server startup in lifespan()
- Add _run_inter_session_cleanup() to orchestrator, called after each
agent completes (both coding and testing paths)
- Update coding and testing prompt templates to instruct agents to use
inline (base64) screenshots only, never saving files to disk
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Agents can now request structured human input when they encounter
genuine blockers (API keys, design choices, external configs). The
request is displayed in the UI with a dynamic form, and the human's
response is stored and made available when the agent resumes.
Changes span 21 files + 1 new component:
- Database: 3 new columns (needs_human_input, human_input_request,
human_input_response) with migration
- MCP: new feature_request_human_input tool + guards on existing tools
- API: new resolve-human-input endpoint, 4th feature bucket
- Orchestrator: skip needs_human_input features in scheduling
- Progress: 4-tuple return from count_passing_tests
- WebSocket: needs_human_input count in progress messages
- UI: conditional 4th Kanban column, HumanInputForm component,
amber status indicators, dependency graph support
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
File-based signal (.pause_drain) lets the orchestrator finish current
work before pausing instead of hard-freezing the process tree. New
status states pausing/paused_graceful flow through WebSocket to the UI
where a Pause button, draining indicator, and Resume button are shown.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add a draggable resize handle on the left edge of the AI assistant
panel, allowing users to adjust the panel width by clicking and
dragging. Width is persisted to localStorage across sessions.
- Drag handle with hover highlight (border -> primary color)
- Min width 300px, max width 90vw
- Width saved to localStorage under 'assistant-panel-width'
- Cursor changes to col-resize and text selection disabled during drag
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Redesign the header from a single overflowing row into a clean two-row
layout that prevents content from overlapping the logo and bleeding
outside the navbar on smaller screens.
Row 1: Logo + project selector + spacer + mode badges + utility icons
Row 2: Agent controls + dev server + spacer + settings + reset
(only rendered when a project is selected, with a subtle border divider)
Changes:
- App.tsx: Split header into two logical rows with flex spacers for
right-alignment; hide title text below md breakpoint; move mode
badges (Ollama/GLM) to row 1 with sm:hidden for small screens
- ProjectSelector: Responsive min-width (140px mobile, 200px desktop);
truncate long project names instead of pushing icons off-screen
- AgentControl: Responsive gap (gap-2 mobile, gap-4 desktop)
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Tooltip fixes (PR #177 follow-up):
- Remove duplicate title attr on Settings button that caused double-tooltip
- Restore keyboard shortcut hints in tooltip text: Settings (,), Reset (R)
- Clean up spurious peer markers in package-lock.json
Dev server config dialog:
- Add DevServerConfigDialog component for custom dev commands
- Open config dialog automatically when start fails with "no dev command"
- Add useDevServerConfig/useUpdateDevServerConfig hooks
- Add updateDevServerConfig API function
- Add config gear button next to dev server start
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add interactive multiple-choice question support to the project assistant,
allowing it to present clickable options when clarification is needed.
Backend changes:
- Add ask_user MCP tool to feature_mcp.py with input validation
- Add mcp__features__ask_user to assistant allowed tools list
- Intercept ask_user tool calls in _query_claude() to yield question messages
- Add answer WebSocket message handler in assistant_chat router
- Document ask_user tool in assistant system prompt
Frontend changes:
- Add AssistantChatQuestionMessage type and update server message union
- Add currentQuestions state and sendAnswer() to useAssistantChat hook
- Handle question WebSocket messages by attaching to last assistant message
- Render QuestionOptions component between messages and input area
- Disable text input while structured questions are active
Flow: Claude calls ask_user → backend intercepts → WebSocket question message →
frontend renders QuestionOptions → user clicks options → answer sent back →
Claude receives formatted answer and continues conversation.
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>