coding-agent-adapters 0.2.13 → 0.2.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +137 -85
- package/dist/index.cjs +406 -23
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +45 -4
- package/dist/index.d.ts +45 -4
- package/dist/index.js +406 -23
- package/dist/index.js.map +1 -1
- package/package.json +4 -4
package/dist/index.cjs
CHANGED
|
@@ -339,6 +339,43 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
339
339
|
],
|
|
340
340
|
docsUrl: "https://github.com/anthropics/gemini-cli#installation"
|
|
341
341
|
};
|
|
342
|
+
/**
|
|
343
|
+
* Auto-response rules for Gemini CLI.
|
|
344
|
+
* Gemini uses Ink/React TUI with arrow-key radio menus.
|
|
345
|
+
* Source: FolderTrustDialog.tsx, MultiFolderTrustDialog.tsx, CloudFreePrivacyNotice.tsx
|
|
346
|
+
*/
|
|
347
|
+
autoResponseRules = [
|
|
348
|
+
{
|
|
349
|
+
pattern: /do.?you.?trust.?this.?folder|trust.?folder|trust.?parent.?folder/i,
|
|
350
|
+
type: "permission",
|
|
351
|
+
response: "",
|
|
352
|
+
responseType: "keys",
|
|
353
|
+
keys: ["enter"],
|
|
354
|
+
description: "Trust current folder (default selection in radio menu)",
|
|
355
|
+
safe: true,
|
|
356
|
+
once: true
|
|
357
|
+
},
|
|
358
|
+
{
|
|
359
|
+
pattern: /trust.?the.?following.?folders.*(added|workspace)/i,
|
|
360
|
+
type: "permission",
|
|
361
|
+
response: "",
|
|
362
|
+
responseType: "keys",
|
|
363
|
+
keys: ["enter"],
|
|
364
|
+
description: "Trust multiple folders being added to workspace",
|
|
365
|
+
safe: true,
|
|
366
|
+
once: true
|
|
367
|
+
},
|
|
368
|
+
{
|
|
369
|
+
pattern: /allow.?google.?to.?use.?this.?data/i,
|
|
370
|
+
type: "config",
|
|
371
|
+
response: "",
|
|
372
|
+
responseType: "keys",
|
|
373
|
+
keys: ["down", "enter"],
|
|
374
|
+
description: 'Decline Google data collection (select "No")',
|
|
375
|
+
safe: true,
|
|
376
|
+
once: true
|
|
377
|
+
}
|
|
378
|
+
];
|
|
342
379
|
getRecommendedModels(_credentials) {
|
|
343
380
|
return {
|
|
344
381
|
powerful: "gemini-3-pro",
|
|
@@ -383,6 +420,27 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
383
420
|
instructions: "Set GOOGLE_API_KEY or GEMINI_API_KEY environment variable"
|
|
384
421
|
};
|
|
385
422
|
}
|
|
423
|
+
if (/enter.?gemini.?api.?key/i.test(stripped)) {
|
|
424
|
+
return {
|
|
425
|
+
required: true,
|
|
426
|
+
type: "api_key",
|
|
427
|
+
instructions: "Enter a Gemini API key or set GEMINI_API_KEY environment variable"
|
|
428
|
+
};
|
|
429
|
+
}
|
|
430
|
+
if (/how.?would.?you.?like.?to.?authenticate/i.test(stripped) || /get.?started/i.test(stripped) && /login.?with.?google|use.?gemini.?api.?key|vertex/i.test(stripped)) {
|
|
431
|
+
return {
|
|
432
|
+
required: true,
|
|
433
|
+
type: "oauth",
|
|
434
|
+
instructions: "Gemini CLI authentication required \u2014 select an auth method"
|
|
435
|
+
};
|
|
436
|
+
}
|
|
437
|
+
if (/waiting.?for.?auth/i.test(stripped)) {
|
|
438
|
+
return {
|
|
439
|
+
required: true,
|
|
440
|
+
type: "oauth",
|
|
441
|
+
instructions: "Waiting for browser authentication to complete"
|
|
442
|
+
};
|
|
443
|
+
}
|
|
386
444
|
if (stripped.includes("Sign in with Google") || stripped.includes("OAuth") || stripped.includes("accounts.google.com")) {
|
|
387
445
|
const urlMatch = stripped.match(/https?:\/\/[^\s]+/);
|
|
388
446
|
return {
|
|
@@ -403,7 +461,7 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
403
461
|
}
|
|
404
462
|
detectBlockingPrompt(output) {
|
|
405
463
|
const stripped = this.stripAnsi(output);
|
|
406
|
-
if (/
|
|
464
|
+
if (/apply.?this.?change\??/i.test(stripped) || /allow.?execution.?of/i.test(stripped) || /do.?you.?want.?to.?proceed\??/i.test(stripped) || /waiting.?for.?user.?confirmation/i.test(stripped)) {
|
|
407
465
|
return {
|
|
408
466
|
detected: true,
|
|
409
467
|
type: "permission",
|
|
@@ -424,6 +482,15 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
424
482
|
instructions: loginDetection.instructions
|
|
425
483
|
};
|
|
426
484
|
}
|
|
485
|
+
if (/further.?action.?is.?required/i.test(stripped) || /verify.?your.?account/i.test(stripped) || /waiting.?for.?verification/i.test(stripped)) {
|
|
486
|
+
return {
|
|
487
|
+
detected: true,
|
|
488
|
+
type: "config",
|
|
489
|
+
prompt: "Account verification required",
|
|
490
|
+
canAutoRespond: false,
|
|
491
|
+
instructions: "Your Gemini account requires verification before continuing"
|
|
492
|
+
};
|
|
493
|
+
}
|
|
427
494
|
if (/select.*model|choose.*model|gemini-/i.test(stripped) && /\d+\)/i.test(stripped)) {
|
|
428
495
|
return {
|
|
429
496
|
detected: true,
|
|
@@ -455,7 +522,16 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
455
522
|
}
|
|
456
523
|
detectReady(output) {
|
|
457
524
|
const stripped = this.stripAnsi(output);
|
|
458
|
-
|
|
525
|
+
if (/do.?you.?trust.?this.?folder/i.test(stripped) || /how.?would.?you.?like.?to.?authenticate/i.test(stripped) || /waiting.?for.?auth/i.test(stripped) || /allow.?google.?to.?use.?this.?data/i.test(stripped)) {
|
|
526
|
+
return false;
|
|
527
|
+
}
|
|
528
|
+
if (/type.?your.?message/i.test(stripped)) {
|
|
529
|
+
return true;
|
|
530
|
+
}
|
|
531
|
+
if (/^\s*[>!*]\s+/m.test(stripped) || /\(r:\)/.test(stripped)) {
|
|
532
|
+
return true;
|
|
533
|
+
}
|
|
534
|
+
return stripped.includes("How can I help") || stripped.includes("What would you like") || // Match "gemini> " prompt specifically, not bare ">"
|
|
459
535
|
/gemini>\s*$/i.test(stripped);
|
|
460
536
|
}
|
|
461
537
|
parseOutput(output) {
|
|
@@ -477,6 +553,27 @@ var GeminiAdapter = class extends BaseCodingAdapter {
|
|
|
477
553
|
}
|
|
478
554
|
};
|
|
479
555
|
}
|
|
556
|
+
/**
|
|
557
|
+
* Detect exit conditions specific to Gemini CLI.
|
|
558
|
+
* Source: FolderTrustDialog.tsx:127, LogoutConfirmationDialog.tsx:64
|
|
559
|
+
*/
|
|
560
|
+
detectExit(output) {
|
|
561
|
+
const stripped = this.stripAnsi(output);
|
|
562
|
+
if (/folder.?trust.?level.?must.?be.?selected.*exiting/i.test(stripped)) {
|
|
563
|
+
return {
|
|
564
|
+
exited: true,
|
|
565
|
+
code: 1,
|
|
566
|
+
error: "Gemini CLI exited because no folder trust level was selected"
|
|
567
|
+
};
|
|
568
|
+
}
|
|
569
|
+
if (/you are now logged out/i.test(stripped)) {
|
|
570
|
+
return {
|
|
571
|
+
exited: true,
|
|
572
|
+
code: 0
|
|
573
|
+
};
|
|
574
|
+
}
|
|
575
|
+
return super.detectExit(output);
|
|
576
|
+
}
|
|
480
577
|
getPromptPattern() {
|
|
481
578
|
return /gemini>\s*$/i;
|
|
482
579
|
}
|
|
@@ -498,11 +595,12 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
498
595
|
};
|
|
499
596
|
/**
|
|
500
597
|
* Auto-response rules for OpenAI Codex CLI.
|
|
501
|
-
* Codex uses
|
|
598
|
+
* Codex uses ratatui/crossterm full-screen TUI with arrow-key menus.
|
|
599
|
+
* Source: trust_directory.rs, update_prompt.rs, model_migration.rs, cwd_prompt.rs, chatwidget.rs, main.rs
|
|
502
600
|
*/
|
|
503
601
|
autoResponseRules = [
|
|
504
602
|
{
|
|
505
|
-
pattern: /
|
|
603
|
+
pattern: /update.?available.*->|update.?now|skip.?until.?next.?version/i,
|
|
506
604
|
type: "config",
|
|
507
605
|
response: "",
|
|
508
606
|
responseType: "keys",
|
|
@@ -511,14 +609,51 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
511
609
|
safe: true
|
|
512
610
|
},
|
|
513
611
|
{
|
|
514
|
-
pattern: /trust
|
|
612
|
+
pattern: /do.?you.?trust.?the.?contents|trust.?this.?directory|yes,?.?continue|prompt.?injection/i,
|
|
515
613
|
type: "permission",
|
|
516
614
|
response: "",
|
|
517
615
|
responseType: "keys",
|
|
518
616
|
keys: ["enter"],
|
|
519
|
-
description:
|
|
617
|
+
description: 'Trust directory contents (default: "Yes, continue")',
|
|
520
618
|
safe: true,
|
|
521
619
|
once: true
|
|
620
|
+
},
|
|
621
|
+
{
|
|
622
|
+
pattern: /choose.?how.?you.?d.?like.?codex.?to.?proceed|try.?new.?model|use.?existing.?model/i,
|
|
623
|
+
type: "config",
|
|
624
|
+
response: "",
|
|
625
|
+
responseType: "keys",
|
|
626
|
+
keys: ["enter"],
|
|
627
|
+
description: 'Accept model migration (default: "Try new model")',
|
|
628
|
+
safe: true,
|
|
629
|
+
once: true
|
|
630
|
+
},
|
|
631
|
+
{
|
|
632
|
+
pattern: /choose.?working.?directory.?to.?(resume|fork)/i,
|
|
633
|
+
type: "config",
|
|
634
|
+
response: "",
|
|
635
|
+
responseType: "keys",
|
|
636
|
+
keys: ["enter"],
|
|
637
|
+
description: "Accept default working directory for session resume",
|
|
638
|
+
safe: true
|
|
639
|
+
},
|
|
640
|
+
{
|
|
641
|
+
pattern: /enable.?full.?access\??/i,
|
|
642
|
+
type: "permission",
|
|
643
|
+
response: "",
|
|
644
|
+
responseType: "keys",
|
|
645
|
+
keys: ["enter"],
|
|
646
|
+
description: 'Confirm full access mode (default: "Yes, continue anyway")',
|
|
647
|
+
safe: true,
|
|
648
|
+
once: true
|
|
649
|
+
},
|
|
650
|
+
{
|
|
651
|
+
pattern: /continue.?anyway\?\s*\[y\/N\]/i,
|
|
652
|
+
type: "config",
|
|
653
|
+
response: "y",
|
|
654
|
+
responseType: "text",
|
|
655
|
+
description: "Confirm dumb terminal continuation",
|
|
656
|
+
safe: true
|
|
522
657
|
}
|
|
523
658
|
];
|
|
524
659
|
getRecommendedModels(_credentials) {
|
|
@@ -563,6 +698,23 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
563
698
|
instructions: "Set OPENAI_API_KEY environment variable or provide credentials in adapterConfig"
|
|
564
699
|
};
|
|
565
700
|
}
|
|
701
|
+
if (/sign.?in.?with.?chatgpt/i.test(stripped) || /sign.?in.?with.?device.?code/i.test(stripped) && !/open.?this.?link/i.test(stripped) || /provide.?your.?own.?api.?key/i.test(stripped)) {
|
|
702
|
+
return {
|
|
703
|
+
required: true,
|
|
704
|
+
type: "oauth",
|
|
705
|
+
instructions: "Codex authentication required \u2014 select a sign-in method or provide an API key"
|
|
706
|
+
};
|
|
707
|
+
}
|
|
708
|
+
if (/preparing.?device.?code.?login/i.test(stripped) || /open.?this.?link.?in.?your.?browser/i.test(stripped) || /enter.?this.?one-time.?code/i.test(stripped)) {
|
|
709
|
+
const codeMatch = stripped.match(/code[:\s]+([A-Z0-9-]+)/i);
|
|
710
|
+
const urlMatch = stripped.match(/https?:\/\/[^\s]+/);
|
|
711
|
+
return {
|
|
712
|
+
required: true,
|
|
713
|
+
type: "device_code",
|
|
714
|
+
url: urlMatch ? urlMatch[0] : void 0,
|
|
715
|
+
instructions: codeMatch ? `Enter code ${codeMatch[1]} at the URL` : "Device code authentication in progress \u2014 complete in browser"
|
|
716
|
+
};
|
|
717
|
+
}
|
|
566
718
|
if (stripped.includes("device code") || stripped.includes("Enter the code")) {
|
|
567
719
|
const codeMatch = stripped.match(/code[:\s]+([A-Z0-9-]+)/i);
|
|
568
720
|
const urlMatch = stripped.match(/https?:\/\/[^\s]+/);
|
|
@@ -576,10 +728,21 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
576
728
|
return { required: false };
|
|
577
729
|
}
|
|
578
730
|
/**
|
|
579
|
-
* Detect blocking prompts specific to OpenAI Codex CLI
|
|
731
|
+
* Detect blocking prompts specific to OpenAI Codex CLI.
|
|
732
|
+
* Source: approval_overlay.rs, chatwidget.rs, request_user_input/mod.rs
|
|
580
733
|
*/
|
|
581
734
|
detectBlockingPrompt(output) {
|
|
582
735
|
const stripped = this.stripAnsi(output);
|
|
736
|
+
if (/would.?you.?like.?to.?run.?the.?following.?command/i.test(stripped) || /do.?you.?want.?to.?approve.?access/i.test(stripped) || /would.?you.?like.?to.?make.?the.?following.?edits/i.test(stripped) || /press.?enter.?to.?confirm/i.test(stripped) && /esc.?to.?cancel/i.test(stripped)) {
|
|
737
|
+
return {
|
|
738
|
+
detected: true,
|
|
739
|
+
type: "permission",
|
|
740
|
+
prompt: "Codex tool approval",
|
|
741
|
+
suggestedResponse: "keys:enter",
|
|
742
|
+
canAutoRespond: true,
|
|
743
|
+
instructions: "Codex is asking permission to execute a command, approve access, or apply edits"
|
|
744
|
+
};
|
|
745
|
+
}
|
|
583
746
|
const loginDetection = this.detectLogin(output);
|
|
584
747
|
if (loginDetection.required) {
|
|
585
748
|
return {
|
|
@@ -591,6 +754,24 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
591
754
|
instructions: loginDetection.instructions
|
|
592
755
|
};
|
|
593
756
|
}
|
|
757
|
+
if (/set.?up.?default.?sandbox/i.test(stripped) || /use.?non-admin.?sandbox/i.test(stripped)) {
|
|
758
|
+
return {
|
|
759
|
+
detected: true,
|
|
760
|
+
type: "config",
|
|
761
|
+
prompt: "Windows sandbox setup",
|
|
762
|
+
canAutoRespond: false,
|
|
763
|
+
instructions: "Codex needs a sandbox configuration on Windows"
|
|
764
|
+
};
|
|
765
|
+
}
|
|
766
|
+
if (/type.?your.?answer/i.test(stripped) && /select.?an.?option/i.test(stripped)) {
|
|
767
|
+
return {
|
|
768
|
+
detected: true,
|
|
769
|
+
type: "unknown",
|
|
770
|
+
prompt: "Codex requesting structured user input",
|
|
771
|
+
canAutoRespond: false,
|
|
772
|
+
instructions: "Codex model is asking multi-step questions that require user input"
|
|
773
|
+
};
|
|
774
|
+
}
|
|
594
775
|
if (/select.*model|choose.*model|gpt-4|gpt-3\.5/i.test(stripped) && /\d+\)/i.test(stripped)) {
|
|
595
776
|
return {
|
|
596
777
|
detected: true,
|
|
@@ -622,7 +803,16 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
622
803
|
}
|
|
623
804
|
detectReady(output) {
|
|
624
805
|
const stripped = this.stripAnsi(output);
|
|
625
|
-
|
|
806
|
+
if (/do.?you.?trust.?the.?contents/i.test(stripped) || /sign.?in.?with.?chatgpt/i.test(stripped) || /update.?available/i.test(stripped) || /enable.?full.?access/i.test(stripped) || /choose.?working.?directory/i.test(stripped)) {
|
|
807
|
+
return false;
|
|
808
|
+
}
|
|
809
|
+
if (/›\s+/m.test(stripped)) {
|
|
810
|
+
return true;
|
|
811
|
+
}
|
|
812
|
+
if (/explain this codebase|summarize recent commits|find and fix a bug/i.test(stripped)) {
|
|
813
|
+
return true;
|
|
814
|
+
}
|
|
815
|
+
return stripped.includes("How can I help") || /(?:codex|>)\s*$/i.test(stripped);
|
|
626
816
|
}
|
|
627
817
|
parseOutput(output) {
|
|
628
818
|
const stripped = this.stripAnsi(output);
|
|
@@ -642,6 +832,24 @@ var CodexAdapter = class extends BaseCodingAdapter {
|
|
|
642
832
|
}
|
|
643
833
|
};
|
|
644
834
|
}
|
|
835
|
+
/**
|
|
836
|
+
* Detect exit conditions specific to Codex CLI.
|
|
837
|
+
* Source: main.rs:404, main.rs:414, main.rs:461
|
|
838
|
+
*/
|
|
839
|
+
detectExit(output) {
|
|
840
|
+
const stripped = this.stripAnsi(output);
|
|
841
|
+
if (/to.?continue.?this.?session,?.?run/i.test(stripped)) {
|
|
842
|
+
return { exited: true, code: 0 };
|
|
843
|
+
}
|
|
844
|
+
if (/update.?ran.?successfully.*restart.?codex/i.test(stripped)) {
|
|
845
|
+
return {
|
|
846
|
+
exited: true,
|
|
847
|
+
code: 0,
|
|
848
|
+
error: "Codex updated successfully \u2014 restart required"
|
|
849
|
+
};
|
|
850
|
+
}
|
|
851
|
+
return super.detectExit(output);
|
|
852
|
+
}
|
|
645
853
|
getPromptPattern() {
|
|
646
854
|
return /(?:codex|>)\s*$/i;
|
|
647
855
|
}
|
|
@@ -669,12 +877,42 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
669
877
|
};
|
|
670
878
|
/**
|
|
671
879
|
* Auto-response rules for Aider CLI.
|
|
672
|
-
* Aider uses plain text
|
|
673
|
-
*
|
|
880
|
+
* Aider uses plain text prompts via io.py:832 with (Y)es/(N)o format.
|
|
881
|
+
* All rules are responseType: 'text' — Aider never uses TUI menus.
|
|
882
|
+
*
|
|
883
|
+
* Decline rules come first to override the generic accept patterns.
|
|
674
884
|
*/
|
|
675
885
|
autoResponseRules = [
|
|
886
|
+
// ── Decline rules (specific, checked first) ────────────────────────
|
|
887
|
+
{
|
|
888
|
+
pattern: /allow collection of anonymous analytics/i,
|
|
889
|
+
type: "config",
|
|
890
|
+
response: "n",
|
|
891
|
+
responseType: "text",
|
|
892
|
+
description: "Decline Aider telemetry opt-in",
|
|
893
|
+
safe: true,
|
|
894
|
+
once: true
|
|
895
|
+
},
|
|
676
896
|
{
|
|
677
|
-
pattern: /
|
|
897
|
+
pattern: /would you like to see what.?s new in this version/i,
|
|
898
|
+
type: "config",
|
|
899
|
+
response: "n",
|
|
900
|
+
responseType: "text",
|
|
901
|
+
description: "Decline release notes offer",
|
|
902
|
+
safe: true,
|
|
903
|
+
once: true
|
|
904
|
+
},
|
|
905
|
+
{
|
|
906
|
+
pattern: /open a github issue pre-filled/i,
|
|
907
|
+
type: "config",
|
|
908
|
+
response: "n",
|
|
909
|
+
responseType: "text",
|
|
910
|
+
description: "Decline automatic bug report",
|
|
911
|
+
safe: true
|
|
912
|
+
},
|
|
913
|
+
// ── File / edit operations ──────────────────────────────────────────
|
|
914
|
+
{
|
|
915
|
+
pattern: /add .+ to the chat\?/i,
|
|
678
916
|
type: "permission",
|
|
679
917
|
response: "y",
|
|
680
918
|
responseType: "text",
|
|
@@ -682,7 +920,15 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
682
920
|
safe: true
|
|
683
921
|
},
|
|
684
922
|
{
|
|
685
|
-
pattern: /
|
|
923
|
+
pattern: /add url to the chat\?/i,
|
|
924
|
+
type: "permission",
|
|
925
|
+
response: "y",
|
|
926
|
+
responseType: "text",
|
|
927
|
+
description: "Allow Aider to add URL content to chat",
|
|
928
|
+
safe: true
|
|
929
|
+
},
|
|
930
|
+
{
|
|
931
|
+
pattern: /create new file\?/i,
|
|
686
932
|
type: "permission",
|
|
687
933
|
response: "y",
|
|
688
934
|
responseType: "text",
|
|
@@ -690,11 +936,96 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
690
936
|
safe: true
|
|
691
937
|
},
|
|
692
938
|
{
|
|
693
|
-
pattern: /
|
|
939
|
+
pattern: /allow edits to file/i,
|
|
940
|
+
type: "permission",
|
|
941
|
+
response: "y",
|
|
942
|
+
responseType: "text",
|
|
943
|
+
description: "Allow edits to file not yet in chat",
|
|
944
|
+
safe: true
|
|
945
|
+
},
|
|
946
|
+
{
|
|
947
|
+
pattern: /edit the files\?/i,
|
|
694
948
|
type: "permission",
|
|
695
949
|
response: "y",
|
|
696
950
|
responseType: "text",
|
|
697
|
-
description: "
|
|
951
|
+
description: "Accept architect mode edits",
|
|
952
|
+
safe: true
|
|
953
|
+
},
|
|
954
|
+
// ── Shell operations ────────────────────────────────────────────────
|
|
955
|
+
{
|
|
956
|
+
pattern: /run shell commands?\?/i,
|
|
957
|
+
type: "permission",
|
|
958
|
+
response: "y",
|
|
959
|
+
responseType: "text",
|
|
960
|
+
description: "Allow Aider to run shell commands",
|
|
961
|
+
safe: true
|
|
962
|
+
},
|
|
963
|
+
{
|
|
964
|
+
pattern: /add command output to the chat\?/i,
|
|
965
|
+
type: "permission",
|
|
966
|
+
response: "y",
|
|
967
|
+
responseType: "text",
|
|
968
|
+
description: "Add shell command output to chat context",
|
|
969
|
+
safe: true
|
|
970
|
+
},
|
|
971
|
+
{
|
|
972
|
+
pattern: /add \d+.*tokens of command output to the chat\?/i,
|
|
973
|
+
type: "permission",
|
|
974
|
+
response: "y",
|
|
975
|
+
responseType: "text",
|
|
976
|
+
description: "Add /run command output to chat context",
|
|
977
|
+
safe: true
|
|
978
|
+
},
|
|
979
|
+
// ── Setup / maintenance ─────────────────────────────────────────────
|
|
980
|
+
{
|
|
981
|
+
pattern: /no git repo found.*create one/i,
|
|
982
|
+
type: "config",
|
|
983
|
+
response: "y",
|
|
984
|
+
responseType: "text",
|
|
985
|
+
description: "Create git repo for change tracking",
|
|
986
|
+
safe: true,
|
|
987
|
+
once: true
|
|
988
|
+
},
|
|
989
|
+
{
|
|
990
|
+
pattern: /add .+ to \.gitignore/i,
|
|
991
|
+
type: "config",
|
|
992
|
+
response: "y",
|
|
993
|
+
responseType: "text",
|
|
994
|
+
description: "Update .gitignore with Aider patterns",
|
|
995
|
+
safe: true,
|
|
996
|
+
once: true
|
|
997
|
+
},
|
|
998
|
+
{
|
|
999
|
+
pattern: /run pip install\?/i,
|
|
1000
|
+
type: "config",
|
|
1001
|
+
response: "y",
|
|
1002
|
+
responseType: "text",
|
|
1003
|
+
description: "Install missing Python dependencies",
|
|
1004
|
+
safe: true
|
|
1005
|
+
},
|
|
1006
|
+
{
|
|
1007
|
+
pattern: /install playwright\?/i,
|
|
1008
|
+
type: "config",
|
|
1009
|
+
response: "y",
|
|
1010
|
+
responseType: "text",
|
|
1011
|
+
description: "Install Playwright for web scraping",
|
|
1012
|
+
safe: true
|
|
1013
|
+
},
|
|
1014
|
+
// ── Other safe confirmations ────────────────────────────────────────
|
|
1015
|
+
{
|
|
1016
|
+
pattern: /fix lint errors in/i,
|
|
1017
|
+
type: "permission",
|
|
1018
|
+
response: "y",
|
|
1019
|
+
responseType: "text",
|
|
1020
|
+
description: "Accept lint error fix suggestion",
|
|
1021
|
+
safe: true
|
|
1022
|
+
},
|
|
1023
|
+
{
|
|
1024
|
+
pattern: /try to proceed anyway\?/i,
|
|
1025
|
+
type: "config",
|
|
1026
|
+
response: "y",
|
|
1027
|
+
responseType: "text",
|
|
1028
|
+
description: "Continue despite context limit warning",
|
|
698
1029
|
safe: true
|
|
699
1030
|
}
|
|
700
1031
|
];
|
|
@@ -774,8 +1105,28 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
774
1105
|
instructions: "API key is invalid - please check your credentials"
|
|
775
1106
|
};
|
|
776
1107
|
}
|
|
1108
|
+
if (/login to openrouter or create a free account/i.test(stripped)) {
|
|
1109
|
+
return {
|
|
1110
|
+
required: true,
|
|
1111
|
+
type: "oauth",
|
|
1112
|
+
instructions: "Aider offering OpenRouter OAuth login \u2014 provide API keys to skip"
|
|
1113
|
+
};
|
|
1114
|
+
}
|
|
1115
|
+
if (/please open this url in your browser to connect aider with openrouter/i.test(stripped) || /waiting up to 5 minutes for you to finish in the browser/i.test(stripped)) {
|
|
1116
|
+
const urlMatch = stripped.match(/https?:\/\/[^\s]+/);
|
|
1117
|
+
return {
|
|
1118
|
+
required: true,
|
|
1119
|
+
type: "browser",
|
|
1120
|
+
url: urlMatch ? urlMatch[0] : void 0,
|
|
1121
|
+
instructions: "Complete OpenRouter authentication in browser"
|
|
1122
|
+
};
|
|
1123
|
+
}
|
|
777
1124
|
return { required: false };
|
|
778
1125
|
}
|
|
1126
|
+
/**
|
|
1127
|
+
* Detect blocking prompts specific to Aider CLI.
|
|
1128
|
+
* Source: io.py, onboarding.py, base_coder.py, report.py
|
|
1129
|
+
*/
|
|
779
1130
|
detectBlockingPrompt(output) {
|
|
780
1131
|
const stripped = this.stripAnsi(output);
|
|
781
1132
|
const loginDetection = this.detectLogin(output);
|
|
@@ -784,6 +1135,7 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
784
1135
|
detected: true,
|
|
785
1136
|
type: "login",
|
|
786
1137
|
prompt: loginDetection.instructions,
|
|
1138
|
+
url: loginDetection.url,
|
|
787
1139
|
canAutoRespond: false,
|
|
788
1140
|
instructions: loginDetection.instructions
|
|
789
1141
|
};
|
|
@@ -797,16 +1149,16 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
797
1149
|
instructions: "Please select a model or set AIDER_MODEL env var"
|
|
798
1150
|
};
|
|
799
1151
|
}
|
|
800
|
-
if (/
|
|
1152
|
+
if (/please answer with one of:/i.test(stripped)) {
|
|
801
1153
|
return {
|
|
802
1154
|
detected: true,
|
|
803
|
-
type: "
|
|
804
|
-
prompt: "
|
|
1155
|
+
type: "unknown",
|
|
1156
|
+
prompt: "Invalid confirmation input",
|
|
805
1157
|
canAutoRespond: false,
|
|
806
|
-
instructions: "Aider
|
|
1158
|
+
instructions: "Aider received an invalid response to a confirmation prompt"
|
|
807
1159
|
};
|
|
808
1160
|
}
|
|
809
|
-
if (/delete|remove|overwrite/i.test(stripped) && /\[y\/n\]/i.test(stripped)) {
|
|
1161
|
+
if (/delete|remove|overwrite/i.test(stripped) && (/\[y\/n\]/i.test(stripped) || /\(Y\)es\/\(N\)o/i.test(stripped))) {
|
|
810
1162
|
return {
|
|
811
1163
|
detected: true,
|
|
812
1164
|
type: "permission",
|
|
@@ -820,9 +1172,22 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
820
1172
|
}
|
|
821
1173
|
detectReady(output) {
|
|
822
1174
|
const stripped = this.stripAnsi(output);
|
|
823
|
-
|
|
824
|
-
|
|
825
|
-
|
|
1175
|
+
if (/login to openrouter/i.test(stripped) || /open this url in your browser/i.test(stripped) || /waiting up to 5 minutes/i.test(stripped)) {
|
|
1176
|
+
return false;
|
|
1177
|
+
}
|
|
1178
|
+
if (/(?:ask|code|architect|help)(?:\s+multi)?>\s*$/m.test(stripped) || /^multi>\s*$/m.test(stripped)) {
|
|
1179
|
+
return true;
|
|
1180
|
+
}
|
|
1181
|
+
if (/^Aider v\d+/m.test(stripped)) {
|
|
1182
|
+
return true;
|
|
1183
|
+
}
|
|
1184
|
+
if (/^(?:Readonly|Editable):/m.test(stripped)) {
|
|
1185
|
+
return true;
|
|
1186
|
+
}
|
|
1187
|
+
return (
|
|
1188
|
+
// Legacy prompt patterns
|
|
1189
|
+
stripped.includes("aider>") || /Added.*to the chat/i.test(stripped) || />\s*$/.test(stripped)
|
|
1190
|
+
);
|
|
826
1191
|
}
|
|
827
1192
|
parseOutput(output) {
|
|
828
1193
|
const stripped = this.stripAnsi(output);
|
|
@@ -843,8 +1208,26 @@ var AiderAdapter = class extends BaseCodingAdapter {
|
|
|
843
1208
|
}
|
|
844
1209
|
};
|
|
845
1210
|
}
|
|
1211
|
+
/**
|
|
1212
|
+
* Detect exit conditions specific to Aider.
|
|
1213
|
+
* Source: base_coder.py:994, base_coder.py:998, report.py:77, versioncheck.py:58
|
|
1214
|
+
*/
|
|
1215
|
+
detectExit(output) {
|
|
1216
|
+
const stripped = this.stripAnsi(output);
|
|
1217
|
+
if (/\^C again to exit/i.test(stripped) || /\^C KeyboardInterrupt/i.test(stripped)) {
|
|
1218
|
+
return { exited: true, code: 130 };
|
|
1219
|
+
}
|
|
1220
|
+
if (/re-run aider to use new version/i.test(stripped)) {
|
|
1221
|
+
return {
|
|
1222
|
+
exited: true,
|
|
1223
|
+
code: 0,
|
|
1224
|
+
error: "Aider updated \u2014 restart required"
|
|
1225
|
+
};
|
|
1226
|
+
}
|
|
1227
|
+
return super.detectExit(output);
|
|
1228
|
+
}
|
|
846
1229
|
getPromptPattern() {
|
|
847
|
-
return /(?:aider
|
|
1230
|
+
return /(?:ask|code|architect|help|aider|multi)(?:\s+multi)?>\s*$/i;
|
|
848
1231
|
}
|
|
849
1232
|
getHealthCheckCommand() {
|
|
850
1233
|
return "aider --version";
|