The general answer consists of two parts: 1) you write a Lisp function that extracts the value of interest and 2) you arrange a command-line invocation that calls that function and gives you the value on its standard output, so that it can be incorporated in a shell script.
The second part is an invocation of emacsclient
with the appropriate arguments. You can capture its stdout by using the $(some_command)
syntax of bash (and other shells, but the exact syntax depends on the shell - I am assuming bash
from now on).
E.g. assuming that you have Emacs running and that you have started a server with (server-start)
, the invocation
$ emacsclient -e "(+ 1 2)"
3
will send the string to the server and ask it to evaluate it. The evaluation results in the value 3
which is sent back to emacsclient
and is printed on its stdout.
So a simple bash program that would make use of that output would be something like
echo The value that emacs returned was $(emacsclient -e "(+ 1 2)")
The first part involves writing a function to retrieve the value of some property that is found under some headline in some file. The function takes the pathname of the file, the headline and the property name as arguments and it should return the value of the property. The following is an initial attempt at that (it does not deal with errors, but it should be good enough to experiment with):
(defun ndk/get-headline-property-from-file (fname headline prop)
"Open the file, search for the headline and retrieve the value
of the property. FNAME is the path of the file to be searched,
HEADLINE is the headline under which the property is looked up
and PROP is the name of the property. The value of the property
is returned. If no value is found, the empty string is
returned (IOW, the function does not distinguish between a
non-existent property and a property whose value is empty)."
(save-excursion
(with-current-buffer (find-file-noselect fname)
(goto-char (point-min))
;; search for the headline
(if (re-search-forward (format org-complex-heading-regexp-format
(regexp-quote headline))
nil t)
(beginning-of-line)
(goto-char (point-max)))
;; try to get the property
(let ((val (org-entry-get (point) prop)))
(if (not val)
""
val)))))
Make sure that your emacs knows about this function before going further: add it to your init file and (re)start emacs. And don't forget to start the emacs server: add (server-start)
to your init file as well.
Now you can put the two parts together:
echo $(emacsclient -e '(ndk/get-headline-property-from-file "./test.org" "My headline" "var1")'
with test.org
(assumed to be in the current directory) containing:
* Some headline
...
* My headline
:PROPERTIES:
:var1: baz
:END:
stuff
* Another headline
...
The echo
should echo baz
.
foo
with a single row and column that containsbar
. So I'm not sure what you mean by "extracting the value of a variable" but maybe you can clarify by showing the method you use when you are inside the Org mode file.