branch: elpa/aidermacs commit 654d2ab50509029dc844c5e0be3c784de10527b0 Author: Mingde (Matthew) Zeng <matthew...@posteo.net> Commit: Mingde (Matthew) Zeng <matthew...@posteo.net>
Redesign transient menus Signed-off-by: Mingde (Matthew) Zeng <matthew...@posteo.net> --- README.org | 196 +++++++++++++++----------------------- aidermacs-backend-comint.el | 2 +- aidermacs-backend-vterm.el | 2 +- aidermacs-backends.el | 6 +- aidermacs-doom.el | 2 +- aidermacs.el | 226 ++++++++++++++++++++++++++------------------ 6 files changed, 216 insertions(+), 218 deletions(-) diff --git a/README.org b/README.org index d10165f823..c33d8aa1bb 100644 --- a/README.org +++ b/README.org @@ -127,128 +127,88 @@ This key allows you to enter multiple lines without sending the command to Aider This section provides a step-by-step guide on how to use Aidermacs for AI-assisted pair programming in Emacs. -** 1. Start an Aidermacs Session +** Getting Started -Aidermacs automatically determines the best root directory for your session using this priority: +The main interface to Aidermacs is through its transient menu system (similar to Magit). Access it with: -1. =project-current= if available (via project.el) -2. =vc-git-root= if in a Git repository -3. Directory of =buffer-file-name= if visiting a file -4. =default-directory= as fallback +#+BEGIN_SRC +M-x aidermacs-transient-menu +#+END_SRC + +Or bind it to a key in your config: + +#+BEGIN_SRC emacs-lisp +(global-set-key (kbd "C-c a") 'aidermacs-transient-menu) +#+END_SRC -Start a session with these options: +** Core Workflow -- =C-c a a= or =M-x aidermacs-run-aidermacs=: Start with automatic root detection -- =C-c a .= or =M-x aidermacs-run-in-current-dir=: Start in current directory with =--subtree-only=, good for large mono repos -- =M-x aidermacs-change-model= (=o= in transient menu): Select AI model interactively +*** 1. Start a Session +From the transient menu: +- =a= Start/open session (auto-detects project root) +- =.= Start in current directory (good for monorepos) +- =^= Toggle "Start in New Frame" option +- =o= Change AI model The session buffer will be named =*aidermacs:your-repo-name*= where you can interact with the AI. -** 2. Add Files to the Session - -To provide context to the AI, you need to add relevant files to the Aidermacs session: - -- Add current file: =M-x aidermacs-add-current-file= (=f= in transient menu) -- Add current file in read-only mode: =M-x aidermacs-add-current-file-read-only= (=R= in transient menu) -- Add all files in current window: =M-x aidermacs-add-files-in-current-window= (=w= in transient menu) -- Add all files with same suffix in current directory: =M-x aidermacs-add-same-type-files-under-dir= (=d= in transient menu) -- In dired-mode, add marked files: =M-x aidermacs-batch-add-dired-marked-files= (=b= in transient menu) - -** 3. Interact with the AI - -After adding files to the session, switch to the =*aidermacs*= buffer to interact with the AI using these commands: - -*** Code Changes -- Request code changes: =M-x aidermacs-code-change= (=c= in transient menu) -- Refactor function/region: =M-x aidermacs-function-or-region-refactor= (=r= in transient menu) -- Implement TODO comments: =M-x aidermacs-implement-todo= (=i= in transient menu) -- Start architectural discussion: =M-x aidermacs-architect-discussion= (=t= in transient menu) -- Undo last AI change: =M-x aidermacs-undo-last-change= (=u= in transient menu) - -*** Session Control -- Run aidermacs: =M-x aidermacs-run-aidermacs= (=a= in transient menu) -- Run in current directory: =M-x aidermacs-run-in-current-dir= (=.= in transient menu) -- Switch to Buffer: =M-x aidermacs-switch-to-buffer= (=z= in transient menu) -- Select Model: =M-x aidermacs-change-model= (=o= in transient menu) -- Clear Session: =M-x aidermacs-clear= (=l= in transient menu) -- Reset Session: =M-x aidermacs-reset= (=s= in transient menu) -- Exit Session: =M-x aidermacs-exit= (=x= in transient menu) - -*** File Management -- Add Current File: =M-x aidermacs-add-current-file= (=f= in transient menu) -- Add File Read-Only: =M-x aidermacs-add-current-file-read-only= (=R= in transient menu) -- Add Files in Window: =M-x aidermacs-add-files-in-current-window= (=w= in transient menu) -- Add Files by Type: =M-x aidermacs-add-same-type-files-under-dir= (=d= in transient menu) -- Add Marked Files: =M-x aidermacs-batch-add-dired-marked-files= (=b= in transient menu) -- List Added Files: =M-x aidermacs-list-added-files= (=L= in transient menu) -- Drop File from Chat: =M-x aidermacs-drop-file= (=D= in transient menu) -- Drop Current File: =M-x aidermacs-drop-current-file= (=O= in transient menu) - -*** Code Actions -- Code Change: =M-x aidermacs-code-change= (=c= in transient menu) -- Refactor Code: =M-x aidermacs-function-or-region-refactor= (=r= in transient menu) -- Implement TODO: =M-x aidermacs-implement-todo= (=i= in transient menu) -- Architect Discussion: =M-x aidermacs-architect-discussion= (=t= in transient menu) -- Undo Last Change: =M-x aidermacs-undo-last-change= (=u= in transient menu) - -*** Testing -- Write Unit Test: =M-x aidermacs-write-unit-test= (=U= in transient menu) -- Fix Failing Test: =M-x aidermacs-fix-failing-test-under-cursor= (=T= in transient menu) -- Debug Exception: =M-x aidermacs-debug-exception= (=X= in transient menu) - -*** Help & Documentation -- Ask Question: =M-x aidermacs-ask-question= (=q= in transient menu) -- Explain Code: =M-x aidermacs-function-or-region-explain= (=e= in transient menu) -- Explain Symbol: =M-x aidermacs-explain-symbol-under-point= (=p= in transient menu) -- Get Help: =M-x aidermacs-help= (=h= in transient menu) -- General Question: =M-x aidermacs-general-question= (=Q= in transient menu) - -*** History & Output -- Show History: =M-x aidermacs-show-output-history= (=H= in transient menu) -- Copy Last Output: =M-x aidermacs-get-last-output= (=C= in transient menu) -- Show Last Commit: =M-x aidermacs-magit-show-last-commit= (=m= in transient menu) -- Go Ahead: =M-x aidermacs-go-ahead= (=y= in transient menu) -- General Command: =M-x aidermacs-general-command= (=g= in transient menu) -- Open Prompt File: =M-x aidermacs-open-prompt-file= (=P= in transient menu) - -** 4. Send Code Blocks - -When working with code blocks, you can use these commands: - -- Send line or region line-by-line: =C-c C-n= or =C-<return>= -- Send block/region as whole: =C-c C-c= - -These keybindings are available in the minor mode. - -** 5. Manage the Aidermacs Session - -Session management commands: - -- Switch to Aidermacs buffer: =C-c C-z= or =M-x aidermacs-switch-to-buffer= (=z= in transient menu) -- Clear buffer: =M-x aidermacs-clear= (=l= in transient menu) -- Reset session: =M-x aidermacs-reset= (=s= in transient menu) -- Exit session: =M-x aidermacs-exit= (=x= in transient menu) - -** 6. Prompt Files - -- Open/create prompt file: =M-x aidermacs-open-prompt-file= (=p= in transient menu) -- The prompt file (=.aider.prompt.org=) is created in your Git repository root -- Use it to store frequently used prompts -- When the prompt file is open, you can use these keybindings: - - =C-c C-n= or =C-<return>=: Send current line/region line-by-line - - =C-c C-c=: Send current block/region as whole - - =C-c C-z=: Switch to Aidermacs buffer - -** 7. Transient Menu - -- Access all commands through the transient menu: =M-x aidermacs-transient-menu= -- The transient menu is a popup menu that provides a convenient way to access all aidermacs commands. -- The menu groups commands into categories: - - "Session Control": Basic session management (=a=, =.=, =z=, =o=, =l=, =s=, =x=) - - "File Management": File management (=f=, =w=, =d=, =b=, =L=, =D=, =O=) - - "Code Actions": Code modifications (=c=, =r=, =i=, =t=, =u=) - - "Testing": Unit tests and debugging (=U=, =T=, =X=) - - "Help & Documentation": Questions and explanations (=q=, =e=, =p=, =h=, =Q=) - - "History & Output": History and output management (=H=, =C=, =m=, =y=, =g=, =P=) - -Note: The default keybindings in the minor mode map (=C-c C-n=, =C-<return>=, =C-c C-c=, and =C-c C-z=) are always available when the minor mode is active. All other commands can be accessed either through =M-x= or through the transient menu after invoking =M-x aidermacs-transient-menu=. +*** 2. Quick Actions +Most common operations are available directly: +- =f= Add current file to chat +- =c= Request code changes +- =r= Refactor code at point/region +- =d= Drop current file from chat +- =g= Accept AI's proposal ("go ahead") + +*** 3. Specialized Commands +Access more specific commands through submenus: + +**** File Commands (=F=) +- Add files: current (=f=), read-only (=r=), window (=w=), directory (=d=), marked in dired (=m=) +- Drop files: specific (=j=), current (=k=) +- List files in chat (=l=) + +**** Code Commands (=C=) +- Code changes (=c=) +- Refactoring (=r=) +- Implement TODOs (=i=) +- Testing: write (=t=), fix (=T=) +- Debug exceptions (=x=) +- Undo changes (=u=) + +**** Understanding Code (Under "Understanding") +- =m= Show last commit +- =q= Ask questions +- =e= Explain code at point/region +- =p= Explain symbol under point + +**** Other Features +- =H= View session history +- =C= Copy last AI output +- =l= Clear buffer +- =h= Get help + +** Working with Code Blocks + +When editing =.aider.prompt.org= or other files, these keybindings are available: + +- =C-c C-n= or =C-<return>=: Send line/region line-by-line +- =C-c C-c=: Send block/region as whole +- =C-c C-z=: Switch to Aidermacs buffer + +** Prompt Files + +The =.aider.prompt.org= file (created with =M-x aidermacs-open-prompt-file=) is useful for: +- Storing frequently used prompts +- Documenting common workflows +- Quick access to complex instructions + +The file is automatically recognized and enables Aidermacs minor mode with the above keybindings. + +** Tips + +1. Start with Core Actions to begin a session +2. Use Quick Actions for common tasks +3. Explore specialized commands through submenus for more specific needs +4. The transient interface shows all available commands - no need to memorize! +5. Use =C-g= to cancel any transient menu operation diff --git a/aidermacs-backend-comint.el b/aidermacs-backend-comint.el index f9b5e34a60..4b744ea4b9 100644 --- a/aidermacs-backend-comint.el +++ b/aidermacs-backend-comint.el @@ -233,7 +233,7 @@ This allows for multi-line input without sending the command." (aidermacs--store-output aidermacs--comint-output-temp) (setq aidermacs--comint-output-temp "")))) -(defun aidermacs-run-aidermacs-comint (program args buffer-name) +(defun aidermacs-run-comint (program args buffer-name) "Create a comint-based buffer and run aidermacs PROGRAM with ARGS in BUFFER-NAME." (let ((comint-terminfo-terminal "dumb")) (unless (comint-check-proc buffer-name) diff --git a/aidermacs-backend-vterm.el b/aidermacs-backend-vterm.el index ce96cda889..801bb2f5c9 100644 --- a/aidermacs-backend-vterm.el +++ b/aidermacs-backend-vterm.el @@ -68,7 +68,7 @@ to force vterm to update until the expected finish sequence is detected." (apply orig-fun args)) (apply orig-fun args))) -(defun aidermacs-run-aidermacs-vterm (program args buffer-name) +(defun aidermacs-run-vterm (program args buffer-name) "Create a vterm-based buffer and run aidermacs PROGRAM with ARGS in BUFFER-NAME. PROGRAM is the command to run, ARGS is a list of arguments, and BUFFER-NAME is the name of the vterm buffer." diff --git a/aidermacs-backends.el b/aidermacs-backends.el index b583b55902..fbb6fd12de 100644 --- a/aidermacs-backends.el +++ b/aidermacs-backends.el @@ -76,15 +76,15 @@ If there's a callback function, call it with the output." (setq aidermacs--current-callback nil))))) ;; Backend dispatcher functions -(defun aidermacs-run-aidermacs-backend (program args buffer-name) +(defun aidermacs-run-backend (program args buffer-name) "Run aidermacs using the selected backend. PROGRAM is the aidermacs executable path, ARGS are command line arguments, and BUFFER-NAME is the name for the aidermacs buffer." (cond ((eq aidermacs-backend 'vterm) - (aidermacs-run-aidermacs-vterm program args buffer-name)) + (aidermacs-run-vterm program args buffer-name)) (t - (aidermacs-run-aidermacs-comint program args buffer-name)))) + (aidermacs-run-comint program args buffer-name)))) (defun aidermacs--send-command-backend (buffer command &optional callback) "Send COMMAND to BUFFER using the appropriate backend. diff --git a/aidermacs-doom.el b/aidermacs-doom.el index 722793c51c..ed1be9a0f6 100644 --- a/aidermacs-doom.el +++ b/aidermacs-doom.el @@ -58,7 +58,7 @@ :desc "Help" "h" #'aidermacs-help ) - :desc "Open aidermacs" "o" #'aidermacs-run-aidermacs + :desc "Open aidermacs" "o" #'aidermacs-run :desc "Reset aidermacs" "r" #'aidermacs-reset :desc "Exit aidermacs" "x" #'aidermacs-exit )))) diff --git a/aidermacs.el b/aidermacs.el index dabb26a28e..21dd53e326 100644 --- a/aidermacs.el +++ b/aidermacs.el @@ -125,93 +125,133 @@ This function can be customized or redefined by the user." ;; The instruction in the autoload comment is needed, see ;; https://github.com/magit/transient/issues/280. ;;;###autoload (autoload 'aidermacs-transient-menu "aidermacs" "Transient menu for aidermacs commands." t) +;; Define secondary transient menus +(transient-define-prefix aidermacs-transient-file-commands () + "File management commands." + ["File Actions" + ["Add File Actions" + ("f" "Add Current File" aidermacs-add-current-file) + ("r" "Add Read-Only" aidermacs-add-current-file-read-only) + ("w" "Add Window Files" aidermacs-add-files-in-current-window) + ("d" "Add Directory Files" aidermacs-add-same-type-files-under-dir) + ("m" "Add Marked Files" aidermacs-batch-add-dired-marked-files)] + + ["Drop Actions" + ("j" "Drop File" aidermacs-drop-file) + ("k" "Drop Current File" aidermacs-drop-current-file)] + + [("l" "List Files" aidermacs-list-added-files)]]) + +(transient-define-prefix aidermacs-transient-code-commands () + "Code modification commands." + ["Code Actions" + ("c" "Code Change" aidermacs-code-change) + ("r" "Refactor Code" aidermacs-function-or-region-refactor) + ("i" "Implement TODO" aidermacs-implement-todo) + ("t" "Write Tests" aidermacs-write-unit-test) + ("T" "Fix Test" aidermacs-fix-failing-test-under-cursor) + ("x" "Debug Exception" aidermacs-debug-exception) + ("u" "Undo Change" aidermacs-undo-last-change)]) + +;; Main transient menu (transient-define-prefix aidermacs-transient-menu () - "Transient menu for aidermacs commands." - ["aidermacs: AI Pair Programming" - ["Session Control" - (aidermacs--infix-switch-to-buffer-other-frame) - ("a" "Start/Open Aidermacs" aidermacs-run-aidermacs) - ("." "Run in Current Dir" aidermacs-run-in-current-dir) - ("z" "Switch to Buffer" aidermacs-switch-to-buffer) - ("o" "Select Model" aidermacs-change-model) - ("l" "Clear Session" aidermacs-clear) - ("s" "Reset Session" aidermacs-reset) - ("x" "Exit Session" aidermacs-exit)] - - ["File Management" - ("f" "Add Current File" aidermacs-add-current-file) - ("R" "Add File Read-Only" aidermacs-add-current-file-read-only) - ("w" "Add Files in Window" aidermacs-add-files-in-current-window) - ("d" "Add Files by Type" aidermacs-add-same-type-files-under-dir) - ("b" "Add Marked Files" aidermacs-batch-add-dired-marked-files) - ("L" "List Added Files" aidermacs-list-added-files) - ("D" "Drop File from Chat" aidermacs-drop-file) - ("O" "Drop Current File" aidermacs-drop-current-file)] - - ["Code Actions" - ("c" "Code Change" aidermacs-code-change) - ("r" "Refactor Code" aidermacs-function-or-region-refactor) - ("i" "Implement TODO" aidermacs-implement-todo) - ("t" "Architect Discussion" aidermacs-architect-discussion) - ("u" "Undo Last Change" aidermacs-undo-last-change)] - - ["Testing" - ("U" "Write Unit Test" aidermacs-write-unit-test) - ("T" "Fix Failing Test" aidermacs-fix-failing-test-under-cursor) - ("X" "Debug Exception" aidermacs-debug-exception)] - - ["Help & Documentation" - ("q" "Ask Question" aidermacs-ask-question) - ("e" "Explain Code" aidermacs-function-or-region-explain) - ("p" "Explain Symbol" aidermacs-explain-symbol-under-point) - ("h" "Get Help" aidermacs-help) - ("Q" "General Question" aidermacs-general-question)] - - ["History & Output" - ("H" "Show Output History" aidermacs-show-output-history) - ("C" "Copy Last Output" aidermacs-get-last-output) - ("m" "Show Last Commit" aidermacs-magit-show-last-commit) - ("y" "Go Ahead" aidermacs-go-ahead) - ("g" "General Command" aidermacs-general-command) - ("P" "Open Prompt File" aidermacs-open-prompt-file)]]) + "AI Pair Programming Interface" + ["Aidermacs: AI Pair Programming" + ["Core Actions" + ("^" "Start in New Frame" aidermacs--infix-switch-to-buffer-other-frame) + ("a" "Start/Open Session" aidermacs-run) + ("." "Start in Current Dir" aidermacs-run-in-current-dir) + ("o" "Change Model" aidermacs-change-model) + ("s" "Reset Session" aidermacs-reset) + ("x" "Exit Session" aidermacs-exit)] + + ["Quick Actions" + ("f" "Add Current File" aidermacs-add-current-file) + ("c" "Code Change" aidermacs-code-change) + ("r" "Refactor" aidermacs-function-or-region-refactor) + ("d" "Drop Current File" aidermacs-drop-current-file) + ("g" "Go Ahead" aidermacs-go-ahead)] + + ["Code & Files" + ("F" "File Commands" aidermacs-transient-file-commands) + ("C" "Code Commands" aidermacs-transient-code-commands)] + + ["Understanding" + ("m" "Show Last Commit" aidermacs-magit-show-last-commit) + ("q" "Ask Question" aidermacs-ask-question) + ("e" "Explain Code" aidermacs-function-or-region-explain) + ("p" "Explain Symbol" aidermacs-explain-symbol-under-point)] + + ["Others" + ("H" "Session History" aidermacs-show-output-history) + ("C" "Copy Last Aidermacs Output" aidermacs-get-last-output) + ("l" "Clear Buffer" aidermacs-clear) + ("h" "Aider Help" aidermacs-help)]]) (defun aidermacs-buffer-name () - "Generate the aidermacs buffer name based on the git repo or current buffer file path. -If not in a git repository and no buffer file exists, an error is raised." - (let ((git-repo-path (vc-git-root default-directory)) - (current-file (buffer-file-name))) - (cond - ;; Case 1: Valid git repo path - (git-repo-path - (format "*aidermacs:%s*" (file-truename git-repo-path))) - ;; Case 2: Has buffer file - (current-file - (format "*aidermacs:%s*" - (file-truename (file-name-directory current-file)))) - ;; Case 3: No git repo and no buffer file - (t - (error "Not in a git repository and current buffer is not associated with a file. Please open a file or start aidermacs from within a git repository."))))) - -;;;###autoload -(defun aidermacs-run-aidermacs (&optional edit-args directory) + "Generate the aidermacs buffer name based on project root or current directory. +Prefers existing sessions closer to current directory." + (let* ((root (aidermacs-project-root)) + (current-dir (file-truename default-directory)) + ;; Get all existing aidermacs buffers + (aidermacs-buffers + (cl-remove-if-not + (lambda (buf) + (string-match-p "^\\*aidermacs:" (buffer-name buf))) + (buffer-list))) + ;; Extract directory paths and subtree status from buffer names + (buffer-dirs + (mapcar + (lambda (buf) + (when (string-match "^\\*aidermacs:\\(.*?\\)\\*$" + (buffer-name buf)) + (cons (match-string 1 (buffer-name buf)) + (match-string 2 (buffer-name buf))))) + aidermacs-buffers)) + ;; Find closest parent directory that has an aidermacs session + (closest-parent + (car + (car + (sort + (cl-remove-if-not + (lambda (dir-info) + (and (car dir-info) + (string-prefix-p (car dir-info) current-dir) + (file-exists-p (car dir-info)))) + buffer-dirs) + (lambda (a b) + ;; Sort by path length (deeper paths first) + (> (length (car a)) (length (car b)))))))) + (display-root (cond + ;; Use current directory for new subtree session + (aidermacs-subtree-only current-dir) + ;; Use closest parent if it exists + (closest-parent closest-parent) + ;; Fall back to project root for new non-subtree session + (t root)))) + (format "*aidermacs:%s*" + (file-truename display-root)))) + +;;;###autoload +(defun aidermacs-run (&optional edit-args) "Run aidermacs process using the selected backend. -With the universal argument EDIT-ARGS, prompt to edit aidermacs-args before running. -Optional DIRECTORY parameter sets working directory, defaults to project root." +With the universal argument EDIT-ARGS, prompt to edit aidermacs-args before running." (interactive "P") - (let* ((default-directory (or directory (aidermacs-project-root))) - (buffer-name (aidermacs-buffer-name)) + (let* ((buffer-name (aidermacs-buffer-name)) (current-args (if edit-args - (split-string (read-string "Edit aidermacs arguments: " - (mapconcat 'identity aidermacs-args " "))) - aidermacs-args)) + (split-string (read-string "Edit aidermacs arguments: " + (mapconcat 'identity aidermacs-args " "))) + aidermacs-args)) (final-args (append current-args - (when (not aidermacs-auto-commits) - '("--no-auto-commits")) - (when aidermacs-subtree-only - '("--subtree-only"))))) + (when (not aidermacs-auto-commits) + '("--no-auto-commits")) + (when aidermacs-subtree-only + '("--subtree-only"))))) + ;; Check if a matching buffer exists (handled by aidermacs-buffer-name) (if (get-buffer buffer-name) (aidermacs-switch-to-buffer) - (aidermacs-run-aidermacs-backend aidermacs-program final-args buffer-name) + ;; Start new session with proper directory and args + (aidermacs-run-backend aidermacs-program final-args buffer-name) (aidermacs-switch-to-buffer)))) ;;;###autoload @@ -219,8 +259,9 @@ Optional DIRECTORY parameter sets working directory, defaults to project root." "Run aidermacs in the current directory with --subtree-only flag. This is useful for working in monorepos where you want to limit aider's scope." (interactive) - (let ((aidermacs-subtree-only t)) - (aidermacs-run-aidermacs nil default-directory))) + (let ((aidermacs-subtree-only t) + (default-directory (file-truename default-directory))) + (aidermacs-run nil))) (defun aidermacs--send-command (command &optional switch-to-buffer callback) "Send COMMAND to the corresponding aidermacs process. @@ -233,7 +274,7 @@ If CALLBACK is provided, it will be called with the command output when availabl (aidermacs--send-command-backend aidermacs-buffer processed-command callback) (when (and switch-to-buffer (not (string= (buffer-name) (aidermacs-buffer-name)))) (aidermacs-switch-to-buffer))) - (message "Buffer %s does not exist. Please start aidermacs with 'M-x aidermacs-run-aidermacs'." aidermacs-buffer-name))) + (message "Buffer %s does not exist. Please start aidermacs with 'M-x aidermacs-run'." aidermacs-buffer-name))) ;; Function to switch to the aidermacs buffer @@ -455,7 +496,7 @@ If cursor is inside a function, include the function name as context." (when (string= (buffer-name) (aidermacs-buffer-name)) (call-interactively 'aidermacs-general-question) (cl-return-from aidermacs-ask-question)) - + (aidermacs-add-current-file) (let* ((function-name (which-function)) (initial-input (when function-name (format "About function '%s': " function-name))) @@ -465,7 +506,6 @@ If cursor is inside a function, include the function name as context." (command (if region-text (format "/ask %s: %s" question region-text) (format "/ask %s" question)))) - (aidermacs-add-current-file) (aidermacs--send-command command t))) ;;;###autoload @@ -525,6 +565,7 @@ If Magit is not installed, report that it is required." If region is active, refactor that region. If point is in a function, refactor that function." (interactive) + (aidermacs-add-current-file) (if (use-region-p) (let* ((region-text (buffer-substring-no-properties (region-beginning) (region-end))) (function-name (which-function)) @@ -534,13 +575,11 @@ If point is in a function, refactor that function." function-name user-command region-text) (format "/architect \"for the following code block, %s: %s\"\n" user-command region-text)))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (if-let ((function-name (which-function))) (let* ((initial-input (format "refactor %s: " function-name)) (user-command (aidermacs-read-string "Enter refactor instruction: " initial-input)) (command (format "/architect %s" user-command))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (message "No region selected and no function found at point.")))) @@ -549,6 +588,7 @@ If point is in a function, refactor that function." "Get a command from the user and send it to the corresponding aidermacs comint buffer based on the selected region. The command will be formatted as \"/ask \" followed by the text from the selected region." (interactive) + (aidermacs-add-current-file) (if (use-region-p) (let* ((region-text (buffer-substring-no-properties (region-beginning) (region-end))) (function-name (which-function)) @@ -559,7 +599,6 @@ The command will be formatted as \"/ask \" followed by the text from the selecte processed-region-text) (format "/ask explain the following code block: %s" processed-region-text)))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (message "No region selected."))) @@ -568,11 +607,11 @@ The command will be formatted as \"/ask \" followed by the text from the selecte "Ask aidermacs to explain the function under the cursor. Prompts user for specific questions about the function." (interactive) + (aidermacs-add-current-file) (if-let ((function-name (which-function))) (let* ((initial-input (format "explain %s: " function-name)) (user-question (aidermacs-read-string "Enter your question about the function: " initial-input)) (command (format "/ask %s" user-question))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (message "No function found at cursor position."))) @@ -588,13 +627,13 @@ Prompts user for specific questions about the function." (defun aidermacs-explain-symbol-under-point () "Ask aidermacs to explain symbol under point, given the code line as background info." (interactive) + (aidermacs-add-current-file) (let* ((symbol (thing-at-point 'symbol)) (line (buffer-substring-no-properties (line-beginning-position) (line-end-position))) (prompt (format "/ask Please explain what '%s' means in the context of this code line: %s" symbol line))) - (aidermacs-add-current-file) (aidermacs--send-command prompt t))) (defun aidermacs-send-command-with-prefix (prefix command) @@ -608,7 +647,7 @@ Prompts user for specific questions about the function." (interactive) (let ((files (dired-get-marked-files))) (if files - (let ((command (concat (aidermacs--get-add-command-prefix) " " (mapconcat 'expand-file-name files " ")))) + (let ((command (concat "/add " (mapconcat 'expand-file-name files " ")))) (aidermacs--send-command command t)) (message "No files marked in Dired.")))) @@ -628,7 +667,7 @@ If there are more than 40 files, refuse to add and show warning message." (if (> (length files) max-files) (message "Too many files (%d, > %d) found with suffix .%s. Aborting." (length files) max-files current-suffix) - (let ((command (concat (aidermacs--get-add-command-prefix) " " (mapconcat 'identity files " ")))) + (let ((command (concat "/add " (mapconcat 'identity files " ")))) (aidermacs--send-command command t)) (message "Added %d files with suffix .%s" (length files) current-suffix))))) @@ -644,6 +683,7 @@ Otherwise: - If cursor is on a function, generate unit test for that function - Otherwise generate unit tests for the entire file" (interactive) + (aidermacs-add-current-file) (if (not buffer-file-name) (message "Current buffer is not visiting a file.") (let ((is-test-file (string-match-p "test" (file-name-nondirectory buffer-file-name))) @@ -658,7 +698,6 @@ Otherwise: function-name)) (user-command (aidermacs-read-string "Test implementation instruction: " initial-input)) (command (format "/architect %s" user-command))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (message "Current function '%s' does not appear to be a test function." function-name)) (message "Please place cursor inside a test function to implement."))) @@ -673,7 +712,6 @@ Otherwise: (file-name-nondirectory buffer-file-name) common-instructions))) (user-command (aidermacs-read-string "Unit test generation instruction: " initial-input)) (command (format "/architect %s" user-command))) - (aidermacs-add-current-file) (aidermacs--send-command command t))))))) ;;;###autoload @@ -681,12 +719,12 @@ Otherwise: "Report the current test failure to aidermacs and ask it to fix the code. This function assumes the cursor is on or inside a test function." (interactive) + (aidermacs-add-current-file) (if-let ((test-function-name (which-function))) (let* ((initial-input (format "The test '%s' is failing. Please analyze and fix the code to make the test pass. Don't break any other test" test-function-name)) (test-output (aidermacs-read-string "Architect question: " initial-input)) (command (format "/architect %s" test-output))) - (aidermacs-add-current-file) (aidermacs--send-command command t)) (message "No test function found at cursor position."))) @@ -711,6 +749,7 @@ Otherwise implement TODOs for the entire current file." (interactive) (if (not buffer-file-name) (message "Current buffer is not visiting a file.") + (aidermacs-add-current-file) (let* ((current-line (string-trim (thing-at-point 'line t))) (is-comment (aidermacs--is-comment-line current-line)) (function-name (which-function)) @@ -734,7 +773,6 @@ Otherwise implement TODOs for the entire current file." (file-name-nondirectory buffer-file-name))))) (user-command (aidermacs-read-string "TODO implementation instruction: " initial-input)) (command (format "/architect %s" user-command))) - (aidermacs-add-current-file) (aidermacs--send-command command t))))