@tduncan / Cortana / commits / 6df4784

feat(tooling): add Marionette MCP server and flutter driver integration

- Add marionette_flutter and marionette_logger packages - Wire MarionetteBinding and MarionetteConfiguration into main.dart - Connect AppLogger to Marionette log collector for get_logs support - Add .mcp.json and .cursor/mcp.json configurations - Update .gitignore to cover build directories across packages and .config/

abdulmominsakib committed Sep 24, 2026 at 20:46 UTC 6df47845e259a5cc59166f53fbad6950de32b801
7 files changed +71 -12
.cursor/mcp.json new
+8
@@ -0,0 +1,8 @@
1 +{
2 + "mcpServers": {
3 + "marionette": {
4 + "command": "marionette_mcp",
5 + "args": []
6 + }
7 + }
8 +}
.gitignore
+9 -11
@@ -5,11 +5,9 @@
5 *.swp
6 .DS_Store
7 .atom/
8 -.build/
8 .buildlog/
9 .history
10 .svn/
12 -.swiftpm/
11 migrate_working_dir/
12
13 # IntelliJ related
@@ -18,25 +16,24 @@ migrate_working_dir/
16 *.iws
17 .idea/
18
21 -# The .vscode folder contains launch configuration and tasks you configure in
22 -# VS Code which you may wish to be included in version control, so this line
23 -# is commented out by default.
24 -#.vscode/
19 +# The .vscode folder contains codespaces, launch, and tasks configurations, and
20 +# should be included in the repository, however setting.json should not be.
21 +.vscode/settings.json
22
23 # Flutter/Dart/Pub related
24 **/doc/api/
25 **/ios/Flutter/.last_build_id
26 .dart_tool/
27 +.flutter-plugins
28 .flutter-plugins-dependencies
29 +.packages
30 .pub-cache/
31 .pub/
32 build/
34 -/coverage/
33 +**/build/
34
36 -# Symbolication related
35 +# Symbol processing related
36 app.*.symbols
38 -
39 -# Obfuscation related
37 app.*.map.json
38
39 # Android Studio will place build artifacts here
@@ -57,4 +54,5 @@ docs/marketing/
54 .puku-cli/
55 .puku/
56 .opencode/
60 -RELEASE.md
\ No newline at end of file
57 +.config/
58 +RELEASE.md
.mcp.json new
+8
@@ -0,0 +1,8 @@
1 +{
2 + "mcpServers": {
3 + "marionette": {
4 + "command": "marionette_mcp",
5 + "args": []
6 + }
7 + }
8 +}
lib/core/logger/app_logger.dart
+13
@@ -4,10 +4,18 @@ import 'package:logger/logger.dart';
4 class Log {
5 late Logger _logger;
6 static const lineLength = 80;
7 + static LogOutput? _additionalOutput;
8
9 Log._internal() {
10 + _initLogger();
11 + }
12 +
13 + void _initLogger() {
14 if (kDebugMode) {
15 _logger = Logger(
16 + output: _additionalOutput != null
17 + ? MultiOutput([ConsoleOutput(), _additionalOutput!])
18 + : null,
19 printer: PrettyPrinter(
20 methodCount: 2,
21 errorMethodCount: 8,
@@ -32,6 +40,11 @@ class Log {
40 }
41 }
42
43 + static void attachOutput(LogOutput output) {
44 + _additionalOutput = output;
45 + _singleton._initLogger();
46 + }
47 +
48 static final Log _singleton = Log._internal();
49
50 static void fatal({required Object error, required StackTrace stackTrace}) =>
lib/main.dart
+15 -1
@@ -1,18 +1,32 @@
1 import 'dart:async';
2 +import 'dart:io' show Platform;
3
4 import 'package:flutter/foundation.dart';
5 import 'package:flutter/material.dart';
6 import 'package:just_audio_background/just_audio_background.dart';
7 +import 'package:marionette_flutter/marionette_flutter.dart';
8 +import 'package:marionette_logger/marionette_logger.dart';
9 import 'package:pdfrx/pdfrx.dart';
10
11 import 'bootstrap/bootstrap_host.dart';
12 +import 'core/logger/app_logger.dart';
13 import 'core/services/crash_report_service.dart';
14 import 'core/widgets/crash_error_widget.dart';
15
16 Future<void> main() async {
17 await runZonedGuarded<Future<void>>(
18 () async {
15 - WidgetsFlutterBinding.ensureInitialized();
19 + final isFlutterTest =
20 + !kIsWeb && Platform.environment.containsKey('FLUTTER_TEST');
21 + if (!kReleaseMode && !isFlutterTest) {
22 + final logCollector = LoggerLogCollector();
23 + Log.attachOutput(logCollector);
24 + MarionetteBinding.ensureInitialized(
25 + MarionetteConfiguration(logCollector: logCollector),
26 + );
27 + } else {
28 + WidgetsFlutterBinding.ensureInitialized();
29 + }
30 await pdfrxFlutterInitialize();
31 final crashReports = CrashReportService.instance;
32 await crashReports.initialize();
pubspec.lock
+16
@@ -1300,6 +1300,22 @@ packages:
1300 url: "https://pub.dev"
1301 source: hosted
1302 version: "3.1.14+2"
1303 + marionette_flutter:
1304 + dependency: "direct main"
1305 + description:
1306 + name: marionette_flutter
1307 + sha256: "9bf6aa531157edeb3d94f7c4972367240a1d704bbe9f4ac558ef1a125c4d1a6d"
1308 + url: "https://pub.dev"
1309 + source: hosted
1310 + version: "0.6.0"
1311 + marionette_logger:
1312 + dependency: "direct main"
1313 + description:
1314 + name: marionette_logger
1315 + sha256: "6220aaafa8de2bfb23070c2dff2ceafabfe8e43a46259b750db8c10090f702cb"
1316 + url: "https://pub.dev"
1317 + source: hosted
1318 + version: "0.6.0"
1319 matcher:
1320 dependency: transitive
1321 description:
pubspec.yaml
+2
@@ -94,6 +94,8 @@ dependencies:
94 flutter_gemma_builtin_ai: ^0.2.1
95 geolocator: ^14.0.3
96 geocoding: ^5.0.0
97 + marionette_flutter: ^0.6.0
98 + marionette_logger: ^0.6.0
99
100 dev_dependencies:
101 flutter_test: