org-babel: New babel backend API function org-babel-session-buffer:<lang>

* lisp/ob-core.el (org-babel-session-buffer): New API function that
return session buffer, if such buffer exists and is live.
(org-babel-execute-src-block): Use `org-babel-session-buffer'.
* lisp/ob-lua.el (org-babel-session-buffer:lua):
* lisp/ob-python.el (org-babel-session-buffer:python): Provide API to
retrieve session buffer name.
(org-babel-python-initiate-session-by-key): Use
`org-babel-session-buffer:python'.
* etc/ORG-NEWS (Org babel backends are now expected to define an
additional API function ~org-babel-session-buffer:<lang>~): Declare
the API addition.

Link: https://orgmode.org/list/87r0hr9f3b.fsf@localhost
This commit is contained in:
Ihor Radchenko 2024-02-06 15:02:48 +01:00
parent 644bf846d6
commit 8c7313d397
No known key found for this signature in database
GPG Key ID: 6470762A7DA11D8B
4 changed files with 48 additions and 7 deletions

View File

@ -13,6 +13,17 @@ Please send Org bug reports to mailto:emacs-orgmode@gnu.org.
* Version 9.7 (not released yet)
** Important announcements and breaking changes
*** Org babel backends are now expected to define an additional API function ~org-babel-session-buffer:<lang>~
Org babel now uses session buffer (if it exists) to retrieve
~default-directory~ environment during src block evaluation.
By default, buffer named like session is checked. All the backends
that create sessions inside buffers named differently should provide a
function ~org-babel-session-buffer:<lang>~. The function must accept
two arguments - session name and info list (as returned by
~org-babel-get-src-block-info~); and return the session buffer name.
*** ~org-insert-subheading~ no longer inserts a sub-heading above current when point is at the beginning of line
Previously, calling ~org-insert-subheading~ on

View File

@ -767,8 +767,30 @@ When `:file-desc' is missing, return nil."
(`(:file-desc) result)
(`(:file-desc . ,(and (pred stringp) val)) val)))
(defvar *this*) ; Dynamically bound in `org-babel-execute-src-block'
; and `org-babel-read'
(defvar *this*)
;; Dynamically bound in `org-babel-execute-src-block'
;; and `org-babel-read'
(defun org-babel-session-buffer (&optional info)
"Return buffer name for session associated with current code block.
Return nil when no such live buffer with process exists.
When INFO is non-nil, it should be a list returned by
`org-babel-get-src-block-info'.
This function uses org-babel-session-buffer:<lang> function to
retrieve backend-specific session buffer name."
(declare-function org-babel-comint-buffer-livep "ob-comint" (buffer))
(when-let* ((info (or info (org-babel-get-src-block-info 'no-eval)))
(lang (nth 0 info))
(session (cdr (assq :session (nth 2 info))))
(cmd (intern (concat "org-babel-session-buffer:" lang)))
(buffer-name
(if (fboundp cmd)
(funcall cmd session info)
;; Use session name as buffer name by default.
session)))
(require 'ob-comint)
(when (org-babel-comint-buffer-livep buffer-name)
buffer-name)))
;;;###autoload
(defun org-babel-execute-src-block (&optional arg info params executor-type)
@ -842,9 +864,8 @@ guess will be made."
(default-directory
(cond
((not dir) default-directory)
((when-let ((session (cdr (assq :session params))))
(when (org-babel-comint-buffer-livep session)
(buffer-local-value 'default-directory (get-buffer session)))))
((when-let ((session (org-babel-session-buffer info)))
(buffer-local-value 'default-directory (get-buffer session))))
((member mkdirp '("no" "nil" nil))
(file-name-as-directory (expand-file-name dir)))
(t

View File

@ -184,6 +184,11 @@ Emacs-lisp table, otherwise return the results as a string."
name
(format "*%s*" name))))
(defun org-babel-session-buffer:lua (session &optional _)
"Return session buffer name for SESSION."
(or (org-babel-lua-session-buffer session)
(org-babel-lua-with-earmuffs session)))
(defun org-babel-lua-without-earmuffs (session)
"Remove stars around *SESSION*, leaving SESSION."
(let ((name (if (stringp session) session (format "%s" session))))

View File

@ -260,6 +260,11 @@ results as a string."
(substring name 1 (- (length name) 1))
name)))
(defun org-babel-session-buffer:python (session &optional _)
"Return session buffer name for SESSION."
(or (org-babel-python-session-buffer session)
(org-babel-python-with-earmuffs session)))
(defun org-babel-python--python-util-comint-end-of-output-p ()
"Return non-nil if the last prompt matches input prompt.
Backport of `python-util-comint-end-of-output-p' to emacs28. To
@ -302,8 +307,7 @@ already been configured as such, do nothing. Return the
initialized session."
(save-window-excursion
(let* ((session (if session (intern session) :default))
(py-buffer (or (org-babel-python-session-buffer session)
(org-babel-python-with-earmuffs session)))
(py-buffer (org-babel-session-buffer:python session))
(python-shell-buffer-name
(org-babel-python-without-earmuffs py-buffer))
(existing-session-p (comint-check-proc py-buffer))