Skip to content

Commit c1f1656

Browse files
authored
fix analyze command roots validation (#315)
Fixes #282 Previously we were doing a non-null assertion on the wrong variable 🤦‍♂️ . This is now tested as well.
1 parent 71a0b00 commit c1f1656

File tree

3 files changed

+42
-2
lines changed

3 files changed

+42
-2
lines changed

pkgs/dart_mcp_server/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
- Add `--tools=dart|all` argument to allow enabling only vanilla Dart tools for
44
non-flutter projects.
55
- Include the device name and target platform in the list_devices tool.
6+
- Fix analyze tool handling of invalid roots.
67
- Fix erroneous SDK version error messages when connecting to a VM Service
78
instead of DTD URI.
89

pkgs/dart_mcp_server/lib/src/mixins/analyzer.dart

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -275,8 +275,8 @@ base mixin DartAnalyzerSupport
275275
fileSystem: fileSystem,
276276
);
277277

278-
if (validated.errorResult != null) {
279-
return errorResult!;
278+
if (validated.errorResult case final error?) {
279+
return error;
280280
}
281281

282282
final rootUri = Uri.parse(validated.root!.uri);

pkgs/dart_mcp_server/test/tools/analyzer_test.dart

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -277,6 +277,45 @@ void main() {
277277
);
278278
});
279279

280+
test('handles invalid roots list', () async {
281+
// We still need a root registered with the server so that the
282+
// prerequisites check passes.
283+
final example = d.dir('example', [
284+
d.file('main.dart', 'void main() => 1;'),
285+
]);
286+
await example.create();
287+
final exampleRoot = testHarness.rootForPath(example.io.path);
288+
testHarness.mcpClient.addRoot(exampleRoot);
289+
await pumpEventQueue();
290+
291+
final request = CallToolRequest(
292+
name: analyzeTool.name,
293+
arguments: {
294+
ParameterNames.roots: [
295+
{'root': 'file:///invalid/root'},
296+
],
297+
},
298+
);
299+
final result = await testHarness.callToolWithRetry(
300+
request,
301+
expectError: true,
302+
);
303+
expect(result.isError, isTrue);
304+
expect(
305+
result.content.single,
306+
isA<TextContent>().having(
307+
(t) => t.text,
308+
'text',
309+
allOf(
310+
contains(
311+
'Invalid root file:///invalid/root, must be under one of the registered project roots:',
312+
),
313+
contains(example.io.uri.toString()),
314+
),
315+
),
316+
);
317+
});
318+
280319
test('can analyze files in multiple roots', () async {
281320
final projectA = d.dir('project_a', [
282321
d.file('main.dart', 'void main() => 1 + "a";'),

0 commit comments

Comments
 (0)