12

What is the standard method to debug emacs-lisp orgmode source code blocks with input variables as header arguments?

I found the hacky solution to insert the following snipped in front of a source code block.

(when t ;; t: do debug, nil: do not debug
  (org-edit-src-code)
  (let ((parse-sexp-ignore-comments t))
    (goto-char (point-min))
    (forward-sexp 2)
    (edebug-defun)))

Debugging of the source code block can be turned on or off by the boolean on the first line. The org-edit-src-code makes sure that point is in the special source edit buffer when one executes the source code block. The snippet puts point in front of the actual code and enters edebug-defun.

There follows a full working example:

* edebug emacs-lisp source code block with input variables

  Example input data:
  #+TBLNAME: input-table
  | This   | table       | contains |
  | some   | strings     | for      |
  | trying | source code | blocks   |

  Further example input data (strings to be highlighted):
  #+TBLNAME: emph
  | table | strings | blocks |

  The code-block to be debugged:
  #+NAME: emphDebug
  #+BEGIN_SRC emacs-lisp :var input=input-table emph=emph
(when t ;; t: do debug, nil: do not debug
  (org-edit-src-code)
  (let ((parse-sexp-ignore-comments t))
    (goto-char (point-min))
    (forward-sexp 2)
    (edebug-defun)))
;; The actual program starts here.
(let ((re (regexp-opt (car emph))))
  (mapcar (lambda (row)
        (mapcar (lambda (col)
              (if (string-match re col)
              (concat "*" (match-string 0 col) "*")
            col))
            row))
      input))
  #+END_SRC

  #+RESULTS: emphDebug
  | This   | *table*     | contains |
  | some   | *strings*   | for      |
  | trying | source code | *blocks* |

Place point on the #+BEGIN_SRC line and press C-c C-c to start debugging.


If one often needs to debug source code blocks one can define the following function somewhere in his configuration file:

(defun org-src-debug ()
  "Put a call to this function at the beginning of the org source block to debug it."
  (save-excursion
    (let ((pt (let ((case-fold-search t)) (org-babel-where-is-src-block-head))))
      (unless pt (error "Not at source block"))
      (goto-char pt)
      (org-edit-src-code)
      (let ((parse-sexp-ignore-comments t))
        (goto-char (point-min))
        (forward-sexp 2)
        (edebug-defun)))))

This function can then be used at the beginning of source code blocks. Example:

#+BEGIN_SRC emacs-lisp :var test='(1 2 3)
   (org-src-debug)
   (message "arg: %s" test)
#+END_SRC

But, I guess there is some org-standard way for debugging which I am not yet aware of.

Drew
  • 75,699
  • 9
  • 109
  • 225
Tobias
  • 32,569
  • 1
  • 34
  • 75
  • No standard way I know of: I usually write and debug the code outside of org and *then* create the source block. – NickD Jun 22 '19 at 14:54
  • 2
    @NickD `org-src-debug` above is a really handy alternative and worth a try. The most pleasent thing is that the header variables are already defined when the debugger is called. – Tobias Oct 08 '19 at 09:19
  • Thanks! I'll give it a try. – NickD Oct 08 '19 at 12:11
  • 1
    @NickD 1st: I just checked. The elisp code I am currently using is still that one from above. 2nd: Only the first form in the source block is debugged. If you have a sequence of forms in your source block temporarily wrap them by `progn`. – Tobias Oct 08 '19 at 13:39
  • Got it, thanks! – NickD Oct 08 '19 at 14:21

0 Answers0