Repository navigation
Make dev mode robust: daemon output, Lambda log reads and levels, no dev alarms, MCP take-back, stop/start - #343
Merged
Conversation
…, MCP sessions, stop [skip ci] Fixes findings 3, 4, 5, 7, 9 and 10 of the third dev-mode dogfood run (r2p) and the dev network deletion message: - The dev agent daemon writes its stdout and stderr to files instead of pipes whose reader exits, so rebuilds no longer fail with EPIPE. A rebuild that fails for a reason other than the build is tried once more. - Lambda log lines get their level from Node, Python (logging format and unhandled errors), JVM, .NET and JSON log formats, and from REPORT/INIT_REPORT status. - One rate-limited poller per process reads every function's log group (FilterLogEvents on the whole group, adaptive interval, backoff on throttling). Throttling is reported once as a warning, never as an app error. `stacktape logs` follow mode uses the same poller. - Dev stacks leave out alarms and their notification rules; dev schedule rules name their function by ARN so CloudFormation creates them in parallel with the function. - MCP: a session this server started after a take-over answers instead of the replaced one; args.stage chooses among one directory's sessions; stop waits until the agent has exited. - Stop closes the relay presence and waits until the relay lets go before it ends the SSM session; a start replaces a holder from the same user and directory whose process is gone. - `dev network delete` says it can take up to about 20 minutes and reports progress. Co-Authored-By: Claude Opus 5.5 <[email protected]>
… s, honest deletion progress [skip ci] Live run in us-west-2 showed three things to adjust: - MCP stop returned once the agent's HTTP server closed, while the process still ran its cleanup; it now waits for the agent's process ID. - CloudWatch made the lines visible 11-14 s after a request; polling quiet groups every 5 s added up to 6 s more. Quiet groups are now read every 2 s, still within 2 requests/s. - The deletion progress claimed a wait for Lambda network interfaces 6 s into a normal 92 s deletion; it now says so only after 2 minutes. Node's console.error and Python's [ERROR] lines no longer print "ERROR: ERROR". The dev and dev network pages say that dev stacks have no alarms and how long a deletion can take. Co-Authored-By: Claude Opus 5.5 <[email protected]>
matuscongrady
added a commit
that referenced
this pull request
Oct 27, 2026
Combines #343 (dev runtime robustness) with this branch. A failed function rebuild now also hands the files it read to the watcher, through each attempt of #343's retry, and the not-ready MCP start result works with session selection by stage. Co-Authored-By: Claude Opus 5.5 <[email protected]>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
This fixes findings 3, 4, 5, 7, 9 and 10 of the third dev-mode dogfood run (r2p) and the misleading
dev network deletemessage.Daemon output (finding 4). The dev agent daemon wrote to pipes whose reader, the process that started it, had exited. A Python rebuild pipes Docker's output into the daemon's stdout, so it failed with
EPIPE. The daemon now gets two files in the user-only token directory as stdout and stderr; the starting process tails them untilAGENT_READY. After ready, the daemon drops its own console output (the agent log has it), so the files stay small, while child processes still write to the files. A rebuild that fails with something other than a Stacktape error (CliError), or with a failed AWS request, is tried once more. A new process test runs a stand-in daemon that pipes a child's output into its stdout after ready; it records EPIPE on the old code and passes on the new.Log levels (finding 3). A new parser (
utils/lambda-log-lines.ts) reads Node and .NET tab lines, Python's logging format and unhandled errors ([ERROR] ..., tracebacks,LAMBDA_WARNING: Unhandled exception), JVM exceptions, the JSON log format, andStatus: error|timeouton REPORT and INIT_REPORT. The table test uses real lines I captured from throwaway nodejs22.x, python3.12, java21 and dotnet8 functions. Java's stack traces contain tabs and were misread as Node lines before.Log polling (finding 5). One scheduler per process reads every function's log group: a group with new events about every second, a quiet one every 2 s, never more than 2 requests per second in total, with backoff and jitter on throttling. Throttling is reported once as a warning, never among the app's error logs. Each read is one
FilterLogEventsover the whole group; the old printer followed only the first log stream, so it missed concurrent execution environments.stacktape logsfollow mode uses the same scheduler and no longer gives up on throttling. I did not useStartLiveTail: it costs $0.01 per session minute after 1,800 free minutes a month, which a dev session left running all day turns into real money.Dev stacks (finding 7). Dev stacks no longer get alarms, their EventBridge notification rules or alarm-triggered function events. A dev schedule rule names its function by ARN instead of
GetAtt, so CloudFormation creates it while it creates the function. EventBridge accepts a target that does not exist yet (probed). Production stacks are unchanged. The dev fingerprint version moves to 6, so each existing dev stage updates once and loses its alarms.MCP (finding 9). A replaced session's take-over answer no longer shadows a session this server started later in the same directory, and
args.stagepicks among one directory's sessions. A newer session found by discovery still does not override the answer (the existing test for a holder in the same directory still passes).Stop and start (finding 10).
DevBoxConnection.stopcloses the relay presence and waits up to 5 s until the relay no longer lists the session before it ends the SSM session. A start replaces, instead of refusing, a holder from the same user and directory whose process has exited; the relay session ID now starts with the process ID. MCPstopwaits until the agent process has exited.dev network deletenow says it can take up to about 20 minutes when dev functions were just deleted, reports progress once a minute, and waits up to 45 minutes instead of 20.Live run in us-west-2 (stacktape-e2e,
STACKTAPE_DEV_NETWORK_SUFFIX=r2r, copy of the r2p app). Cold start with network creation took 296 s; the dev stack has no alarms and its schedule rule ran in parallel with the functions. A new stage on the existing network took 134 s (r2p: 203 s), with a dev stack update of 73 s (r2p: 167 s). Three Python rebuilds and arebuild_allafter the MCP parent had exited returned OK with no EPIPE. A Python edit right after "ready" under--watchwas live in 8.6 s. A planted Python error came back from MCPlogs {level: "error"}as two error entries (r2p: none). Account-wideFilterLogEventscalls for three functions went from about 360/min (old code, computed) to about 65–117/min (measured with theAWS/Usagemetric). Floods of 25 and 100 requests per second (298 and 1,750 throttled) produced no warning or error lines in the session, and logs kept arriving. Across two MCP servers, the r2p take-over sequence now reaches the newest session without an ID. Stop followed by an immediate start succeeded (stop 1.3 s, start 19.3 s). The network deletion took 92 s. Everything I created was deleted and verified.Checks:
test:local-dev210/210,test:mcp-docs81/81,test:src3,058 pass and 0 fail,test:characterization371/371,test:synthesis-families32/32,test:operations:rules65/65,test:tools85/85, CLI typecheck, oxlint and oxfmt on the touched files, andgenerate:checkafter regenerating the LLM docs for the two doc edits.What remains uncertain:
~/.stacktape/dev-agent-tokens/after the agent stops; the next agent on the same port overwrites them.