Hello friends! I am currently learning Emacs and Elisp, and I'm trying to use Org-mode for literate programming. Recently, I wrote a convenient function that extracts the content of a code block into a file and calls an asynchronous command to run the code. I'm not sure if there is already a package in the community that implements similar functionality; if there is, please let me know. Below is my version—what do you all think? Please leave a comment, thank you!
;;; -*- lexical-binding: t; -*-
(require 'org)
(require 'ob-core)
(defvar org-src-languages
'(("C" . "runclang")
("C++" . "runclang")
("bash" . "bash")
("clojure" . "clojure")
("elixir" . "elixir")
("fish" . "fish")
("go" . "go run")
("haskell" . "runghc -dynamic")
("html" . "open")
("java" . "java")
("js" . "deno run")
("racket" . "racket")
("rust" . "cargo run --bin")
("scheme" . "guile")
("ts" . "deno run")))
(defun org-babel-tangle-and-run-src-block ()
(interactive)
(let* ((info (org-babel-get-src-block-info t))
(params (nth 2 info))
(lang (nth 0 info))
(command (cdr (assoc lang org-src-languages)))
(tangled-file (cdr (assq :tangle params))))
(unless command
(user-error "Unknown language: %s" lang))
(unless (and tangled-file
(not (equal tangled-file "no")))
(user-error "Source block has no :tangle"))
(if (equal lang "rust")
(let ((cargo-dir "rsb")
(bin (file-name-base tangled-file)))
(unless (file-directory-p (format "./src/%s" cargo-dir))
(call-process "cargo" nil nil nil
"new" (format "./src/%s" cargo-dir)))
(org-babel-tangle)
(async-shell-command
(format "cd ./src/%s && %s %s"
(shell-quote-argument cargo-dir)
command
(shell-quote-argument bin))))
(org-babel-tangle)
(async-shell-command
(format "%s %s"
command
(shell-quote-argument tangled-file))))))
(defun org-babel-tangle-and-run-other-src-block (direction)
(save-excursion
(pcase direction
('next (org-babel-next-src-block))
('prev (org-babel-previous-src-block))
(_ (user-error "Unknown direction: %s" direction)))
(let ((org-babel-current-src-block-location
(org-babel-where-is-src-block-head)))
(org-babel-tangle-and-run-src-block))))
(org-link-set-parameters
"nrun"
:follow
(lambda (_lang _arg)
(org-babel-tangle-and-run-other-src-block 'next)))
(org-link-set-parameters
"prun"
:follow
(lambda (_lang _arg)
(org-babel-tangle-and-run-other-src-block 'prev)))
(provide 'tangle-and-run)
;;; tangle-and-run.el ends here
https://redd.it/1wo1som
@r_emacs