During the compilation of sources, I would like GNU Make to call an emacs defun.
For this I have 2 options:
Start a new emacs instance, and load the desired function and call it.
Call the defun from the emacsclient like:
emacsclient --eval "(my-emacs-defun)"
The latter has the advantage, it is faster, because the emacs server is already running and has the desired defun loaded.
But this also has a disadvantage, if (message ...) is called from (my-emacs-defun), it interrupts my active emacs session.
I could try to modify (my-emacs-defun) so (message ...) isn't called, but is really hard when using emacs built-in functions.
Therefore I would like to know how to suppress the (message ...) from (my-emacs-defun).
Is it possible to alter the (message ...) behavior when being called (my-emacs-defun)? Can I use(defadvice)` for this?
EDIT
The real problem is, the message is displayed the minibuffer. It is irritating when using the minibuffer at that time (e.g. during (find-file)).
Just redefine the message function for your call (temporarily):
(flet ((message (msg) ))
(my-emacs-defun)))
Because of dynamic scoping for global functions, the name message will be redefined while the execution is inside the flet-expression, and it will return it's original sense after it exits the flet.
Example:
(defun verbose ()
(message "hi"))
(let ()
(message "one")
(flet ((message (msg) ))
(verbose))
(message "two"))
; ->
; one
; two
You could've also temporarily rebind s Messages buffer, but I don't know where is it stored.
You can restore the message displayed in the echo area before the function call like this:
(let ((msg (current-message)))
(do-something-that-calls-message)
(message "%s" (or msg "")))
(with-temp-message "" (my-emacs-func))
I've looked in the emacs source code and I found this hack:
(let ((message-log-max nil)
(executing-kbd-macro t))
(my-emacs-defun))
This does suppress all message, but still while (find-file) the focus of the minibuffer is lost.
I decided to go for the first option: without emacsclient.
To be more precise I now use:
emacs --batch --eval "(my-emacs-defun)"
In my Makefile it looks like this:
sometarget:
#emacs --batch --eval "$${elisp_code}"
define elisp_code
(require 'something)
(my-emacs-defun)
endif
This also seems to be fast.
Even better:
define emacs_script_content=
(require 'something)
(my-emacs-defun)
endef
export emacs_script_content
emacs-script:
#echo $${emacs_script_content} > $#
.INTERMEDIATE: emacs-script
some-target: emacs-script
#emacs --script $<
This way you won't get errors when calling make functions or when having quoted "text" in the script.
Related
I've defined a major mode for my language.
I'm trying to redefine C-x C-e so that when I'm in my major mode, it'd evaluate the expression using "my" custom interpreter.
Suppose my interpreter is just a command-line program that could be invoked like this:
$my-interpreter <some expression>
I imagine, all I need to do is to do a system call, passing the expression "before point" as argument and print the return value in the echo area.
How hard could it be, right?
Problem: I have no idea where to start!
Any hint?
Thanks.
You can take a look at shell-command and its relatives, along with thing-at-point. Here's a really simple example that uses an "interpreter" (just the shell echo command) to echo the word at point:
(defun my-interpreter ()
(interactive)
(let ((arg (thing-at-point 'word)))
(when arg
(shell-command (concat "echo " arg)))))
(Edit in response to comment.)
If you have defined a keymap for your major mode, you can bind C-x C-e in you major mode with a call to define-key. Otherwise, you can just bind it locally with (local-set-key (kbd "C-x C-e") 'my-interpreter).
It occurred to me that you might be interested in building in interactive functionality like a REPL. To do so, you might consider comint-mode; see the EmacsWiki and this post from Mastering Emacs to get inspired.
I had to run the command revert-buffer many times recently and really frustrated to say yes whenever emacs prompts this message Revert buffer from file abc.txt? (yes or no).
Is there anyway to auto say yes in this case?
If it's just for interactive usage, I'd define an alternative function:
(defun my-revert-buffer-noconfirm ()
"Call `revert-buffer' with the NOCONFIRM argument set."
(interactive)
(revert-buffer nil t))
Alternatively, as the revert-buffer docstring tells you, take a look at the revert-without-query variable, in case that's a nicer solution for you.
On a related side note, many people have the following line in their .emacs that will make confirmations just a single keypress (just y or n):
(defalias 'yes-or-no-p 'y-or-n-p)
I use this, similar to what #phils proposed, but with non-nil IGNORE-AUTO arg:
(defun revert-buffer-no-confirm ()
"Revert buffer without confirmation."
(interactive) (revert-buffer t t))
And I bind it to <f5>, since that's what that key does generally, in MS Windows.
In any case, I agree (strongly) with those who have advised to define a separate command for this. I would not bother with revert-without-query, unless you are very sure wrt certain files (always) etc. It's best to let revert-buffer continue to act normally, and provide (and perhaps bind) your own command for interactive use. You know best when to not be bothered by a confirmation prompt.
Customizing revert-without-query might be an option.
While it is, as pointed out by other answers, preferred to redefine the revert-buffer function or the key binding, it is possible to auto-reply "yes" to any function using yes-or-no-p or for that matter y-or-n-p by something like the following:
(defalias 'yes-or-no-p '(lambda (a &rest b) t))
This may be very destructive to your data, so use at your own discretion.
I use the following to turn all ‘yes/no’ confirmations to ‘y/n’ confirmations,
and default to yes for certain prompts. i add prompts to default-yes-sometimes as needed. note i don’t have to list the entire prompt, just a regexp that matches it.
(setq original-y-or-n-p 'y-or-n-p)
(defalias 'original-y-or-n-p (symbol-function 'y-or-n-p))
(defun default-yes-sometimes (prompt)
(if (or
(string-match "has a running process" prompt)
(string-match "does not exist; create" prompt)
(string-match "modified; kill anyway" prompt)
(string-match "Delete buffer using" prompt)
(string-match "Kill buffer of" prompt)
(string-match "Kill Dired buffer of" prompt)
(string-match "delete buffer using" prompt))
t
(original-y-or-n-p prompt)))
(defalias 'yes-or-no-p 'default-yes-sometimes)
(defalias 'y-or-n-p 'default-yes-sometimes)
My ~/.emacs contains the following settings for opening certain files with certain applications (Ubuntu 12.10; Emacs 24):
(setq dired-guess-shell-alist-user
'(("\\.pdf\\'" "okular ? &")
("\\.djvu\\'" "okular ? &")
("\\.mp3\\'" "vlc ? &")
("\\.mp4\\'" "vlc ? &")
))
When I navigate to a .pdf in dired-mode and hit !, it opens the .pdf in Okular, but the dired-buffer is split into two parts, the second one now being a useless *Async Shell Command* buffer containing content like
okular(25393)/kdecore (KConfigSkeleton) KCoreConfigSkeleton::writeConfig:
okular(25393)/kdecore (KConfigSkeleton) KCoreConfigSkeleton::writeConfig:
okular(25393)/kdecore (KConfigSkeleton) KCoreConfigSkeleton::writeConfig:
okular(25393)/kdecore (KConfigSkeleton) KCoreConfigSkeleton::writeConfig:
How can I prevent this buffer from being opened? (except for, maybe, if there was an error and this information is useful).
I found related questions here and here, but they seem to deal with specific commands executed asynchronously, instead of the *Async Shell Command* in general (if possible, I would like to change the behaviour in general for asynchronous processes, not only for certain file types)
Found this here:
(call-process-shell-command "okular&" nil 0)
Works for me. No stderr gobbledygook.
The question was asked in 2012, and at the time of my writing, the most recent answer is dated 2015. Now, in 2017, I can say that the answer is simple:
(add-to-list 'display-buffer-alist
(cons "\\*Async Shell Command\\*.*" (cons #'display-buffer-no-window nil)))
I am piggybacking off of user1404316's answer, but here is another generic way to achieve the desired outcome.
(defun async-shell-command-no-window
(command)
(interactive)
(let
((display-buffer-alist
(list
(cons
"\\*Async Shell Command\\*.*"
(cons #'display-buffer-no-window nil)))))
(async-shell-command
command)))
I'm not entirely sure about doing it for asynchronous processes in general, but for anything that goes through async-shell-command, this should work:
(defadvice async-shell-command (around hide-async-windows activate)
(save-window-excursion
ad-do-it))
Sadly there is no good way to avoid this buffer as it's called directly by 'shell-command' function ('async-shell-command' is just a wrapper).
So, a much better way is to replace 'async-shell-command' with 'start-process'.
You should start process with 'set-process-sentinel' to detect the moment when process emits 'exit signal. Then kill process.
A slightly more complicated incantation should get you what you want. Just use a shell command like: (okular ? >& /dev/null &).
I haven't tested this with okular, but I can do M-! ((echo foo; sleep 10; echo bar) >& /dev/null &) and Emacs returns immediately without creating a new buffer.
I solved the problem, using this method:
;list of programs, corresponding to extensions
(setq alist-programs
'(("pdf" ."okular")
("djvu" . "okular")
("mp3" . "xmms")))
(defun my-run-async-command (command file)
"Run a command COMMAND on the file asynchronously.
No buffers are created"
(interactive
(let ((file (car (dired-get-marked-files t current-prefix-arg))))
(list
;last element of alist-programs, contains COMMAND
(cdr
(assoc
(file-name-extension file)
alist-programs))
file)))
;begin of function body
(if command ;command if not nil?
(start-process "command" nil command file)
)
)
;attach function to <f2> key
(add-hook 'dired-mode-hook
(lambda ()
(define-key dired-mode-map (kbd "<f2>") 'my-run-async-command)))
The suggestions to use start-process are ok if he is running a distinct program on the path of course. But if you want run some shell command in a specific directory (eg your project directory) then simply quell the popup - you frequently want the buffer but just dont want it jumping up in your face. eg I run a webserver and I want to see the output, just not now...
(use-package php-mode
:config
(add-to-list 'display-buffer-alist
(cons "\\*Symfony Web Server\\*.*" (cons #'display-buffer-no-window nil)))
(defun php-mode-webserver-hook ()
(if (projectile-project-root) (let ((default-directory (projectile-project-root)))
(unless (get-buffer "*Symfony Web Server*" )
(async-shell-command "bin/console server:run" "*Symfony Web Server*")))))
:hook (php-mode . php-mode-webserver-hook))
[I apologize for the poor title, but couldn't come up with a better one.]
bin chen asked on Google+:
How to input relative path of (buffer-file-name) in minibuffer after M-! in #emacs?
I thought if the buffer-file-name is saved in a register, it should be accessible by invoking insert-register (C-x r i) while at the shell-command prompt.
(defun save-buffer-file-name-in-register ()
(set-register ?F (buffer-file-name))
(set-register ?D (file-name-directory buffer-file-name)))
(defadvice shell-command (before save-buffer-file-name)
"Save buffer-file-name to register F before running shell-command"
(save-buffer-file-name-in-register))
(ad-activate 'shell-command)
When I invoke shell-command (M-!) followed by insert-register (C-x r i), I get the error message: Register does not contain any text.
But when I run list-registers I do see that the registers F and D are set with the appropriate values. If I run the shell-command again, I can access the values from the registers previously saved.
Is it possible that the registers are being set too late for the first time? How can I fix the code to do what I want?
Edit: Changed around to before (Thanks to #phils)
n.b. You have defined around advice, not before advice.
Around advice acts as a wrapper, and must include the token ad-do-it to execute the code of the function it is wrapping.
You have effectively replaced the body of the shell-command function with a call to save-buffer-file-name-in-register
As to your main question, I'd need to check the documentation, but I suspect that because the arguments to the advised function are available to advice, the original function's interactive declaration probably executes before the advice does, which would explain why your register values are not visible at the interactive shell-command prompt.
(If the around in the above code is indeed what you were using, the fact that you were still being prompted for a shell command would seem to verify this sequence.)
When the interactive form runs, your advice hasn't executed yet. See: this question
You need to specify an interactive form in your advice that redefines the original if you want to stick with this approach. However, this approach is a little fancy-pants for the sake of fancy-pants-ness.
Just define your own interactive function which does what you want without registers.
(defun insert-cur-dir ()
(interactive)
(let ((dir-name (file-name-directory (buffer-file-name (window-buffer (minibuffer-selected-window))))))
(insert (or dir-name ""))))
(define-key minibuffer-local-map (kbd "C-c i") 'insert-cur-dir)
An alternative, but way awesomer approach is to use yasnippet.
As an Emacs beginner, I am working on writing a minor mode. My current (naive) method of programming elisp consists of making a change, closing out Emacs, restarting Emacs, and observing the change. How can I streamline this process? Is there a command to refresh everything?
You might try using M-C-x (eval-defun), which will re-evaluate the top-level form around point. Unlike M-x eval-buffer or C-x C-e (exal-last-sexp), this will reset variables declared with defvar and defcustom to their initial values, which might be what's tripping you up.
Also try out C-u C-M-x which evaluates the definition at point and sets a breakpoint there, so you get dropped into the debugger when you hit that function.
M-x ielm is also very useful as a more feature-rich Lisp REPL when developing Emacs code.
M-x eval-buffer should do it.
What Sean said. In addition, I have (eval-defun) bound to a key, along with a test. The development loop then becomes: 1) edit function, 2) press eval-and-test key, 3) observe results, 4) repeat. This is extremely fast.
During development I write a test, bind it to jmc-test, then use the above key to run it on my just-edited function. I edit more, then press key again, testing it again. When the function works, I zap jmc-test, edit another function, and write another jmc-test function. They're nearly always one line of code, so easy to just bang out.
(defun jmc-eval-and-test ()
(interactive)
(eval-defun nil)
(jmc-test))
(define-key emacs-lisp-mode-map (kbd "<kp-enter>") 'jmc-eval-and-test)
(when t
(defun myfunc (beer yum)
(+ beer yum))
(defun jmc-test () (message "out: %s" (myfunc 1 2))))
When editing "myfunc", if I hit keypad enter, it prints "out: 3".
It all depends on what you're writing and how you've written it. Toggling the mode should get you the new behavior. If you're using [define-minor-mode][1], you can add code in the body of the macro that keys off the mode variable:
(define-minor-mode my-minor-mode
"doc string"
nil
""
nil
(if my-minor-mode
(progn
;; do something when minor mode is on
)
;; do something when minor mode is off
)
But, another way to check it quickly would be to spawn a new Emacs from your existing one:
M-x shell-command emacs&
I just define a function called ldf (short for load-file) in my .emacs file,
like this:
(defun ldf (arg) (interactive "P") (load-file (buffer-file-name)))
As you can see, this little function looks up the filename of the current buffer and then loads the file. Whenever I need to reload the current buffer elisp file, just type "M-x ldf"