Fix MCP serve: remove stdin conflict and premature ProjectContext call

Two bugs caused immediate connection close:
1. ProjectContext.find() at startup crashed if cwd wasn't a project root;
   it's not needed here — each tool handler calls it on demand.
2. io.stdin.drain() added a second listener to stdin after stdioChannel
   already subscribed, throwing StateError and killing the process.

The Dart event loop keeps the process alive while stdin has a listener.

Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
This commit is contained in:
Chris Hendrickson 2026-04-23 16:09:30 -04:00
parent 260d291b0f
commit bb93f7570e

View file

@ -21,21 +21,17 @@ class ServeCommand extends DewCommand {
@override @override
Future<void> run() async { Future<void> run() async {
final context = await ProjectContext.find();
final tools = _toolRegistry.allTools; final tools = _toolRegistry.allTools;
io.stderr.writeln( io.stderr.writeln(
'Dew MCP server starting — ' 'Dew MCP server starting — ${tools.length} tool(s) registered.',
'${tools.length} tool(s) registered, '
'project root: ${context.root}',
); );
// stdioChannel subscribes to stdin; do not touch stdin after this point.
// The Dart event loop keeps the process alive until the client disconnects.
DewMcpServer( DewMcpServer(
stdioChannel(input: io.stdin, output: io.stdout), stdioChannel(input: io.stdin, output: io.stdout),
tools, tools,
); );
// Keep the process alive until the MCP client closes the connection.
await io.stdin.drain<void>();
} }
} }