From: stardiviner <numbchild@gmail.com>
To: org-mode-email <emacs-orgmode@gnu.org>
Subject: [PATCH] ob-clojure.el and ob-clojure-literate.el support new header argument :ns
Date: Fri, 13 Apr 2018 20:55:25 +0800 [thread overview]
Message-ID: <87zi272rlu.fsf@gmail.com> (raw)
[-- Attachment #1.1: Type: text/plain, Size: 1767 bytes --]
After about 5 times test, And about 4 times review. I decide to PR.
About new header argument :ns, I don't know how to write the test for it
with loading CIDER in ERT. So have not write test. But I load my patch
code, and run test on the following examples works fine.
#+begin_src clojure :results pp
;; (def greeting "hi there!")
*ns*
#+end_src
#+RESULTS[<2018-04-13 20:37:16> f6f68aecdefcfd1be88fb144d47f5881f47b95db]:
: #namespace[user]
#+begin_src clojure :results pp
(ns kk.test)
(def he "hi")
#+end_src
#+RESULTS[<2018-04-13 20:37:24> 0b564a90ba588ba72b622a217834057600ac6d07]:
: #'kk.test/he
Deeper testing:
#+begin_src emacs-lisp :results pp
(nrepl-sync-request:eval
"(clojure.pprint/pprint (do (ns user)\n (ns kk.test)\n (def he 2)))"
(cider-current-connection)
"user"
)
#+end_src
#+RESULTS[<2018-04-13 20:37:39> a05d9349d3b991a7fd47fb4ed268bf7e40f53e7a]:
: (dict "status"
: ("done" "state")
: "id" "20" "out" "#'user/he\n" "session" "72ab6c95-08d4-4873-b83b-31c66aa26d62" "ns" "kk.test" "value" "nil" "changed-namespaces"
: (dict)
: "repl-type" "clj")
#+begin_src clojure :results value :ns kk2
(def he "hi")
*ns*
#+end_src
#+RESULTS[<2018-04-13 20:38:09> 89b32544ad50101e9f6f529a9e87a7bb86235cd9]:
: nil#'kk2/he#namespace[kk2]
What about another src block without ~:ns~ specified after previous specified src block?
#+begin_src clojure :results value
(def he "hi")
*ns*
#+end_src
#+RESULTS[<2018-04-13 20:38:14> 85a2890ea59d198e2d1c771e2b80b1ae6335c416]:
: nil#'user/he#namespace[user]
More complex example:
#+begin_src clojure :results output :var he="hi" :ns kk
;; (def he "hi")
(prn he)
(prn *ns*)
#+end_src
#+RESULTS[<2018-04-13 20:38:19> 9f6d74be8c54e2bc1b5047b569ddc6514c789cf0]:
: "hi"
: #namespace[kk]
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.2: 0001-ob-clojure-literate.el-CIDER-jack-in-outside-of-proj.patch --]
[-- Type: text/x-patch, Size: 4403 bytes --]
From 1a0d80c000384b929b84a3755669e0d44c662558 Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Thu, 22 Mar 2018 01:21:22 +0800
Subject: [PATCH 1/6] * ob-clojure-literate.el: CIDER jack-in outside of
project by default.
---
contrib/lisp/ob-clojure-literate.el | 50 +++++++++++++++++------------
1 file changed, 30 insertions(+), 20 deletions(-)
diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el
index a7ab1894d..8d419b0b4 100644
--- a/contrib/lisp/ob-clojure-literate.el
+++ b/contrib/lisp/ob-clojure-literate.el
@@ -35,8 +35,10 @@ Don't auto jack in by default for not rude."
:type 'boolean
:group 'ob-clojure-literate)
-(defcustom ob-clojure-literate-project-location (concat user-emacs-directory "Org-mode/")
- "The location for `ob-clojure-literate' scaffold project."
+(defcustom ob-clojure-literate-project-location nil
+ "The location for `ob-clojure-literate' scaffold project.
+If it is nil, then `cider-jack-in' will jack-in outside of Clojure project.
+If it is a directory, `ob-clojure-literate' will try to create Clojure project automatically."
:type 'string
:group 'ob-clojure-literate)
@@ -45,7 +47,7 @@ Don't auto jack in by default for not rude."
(defvar ob-clojure-literate-session-ns nil)
(defvar ob-clojure-literate-cider-connections nil)
-(defcustom ob-clojure-literate-default-session "*cider-repl ob-clojure*"
+(defcustom ob-clojure-literate-default-session "*cider-repl localhost*"
"The default session name for `ob-clojure-literate'."
:type 'string
:group 'ob-clojure-literate)
@@ -104,23 +106,31 @@ Don't auto jack in by default for not rude."
(defun ob-clojure-literate-auto-jackin ()
"Auto setup ob-clojure-literate scaffold and jack-in Clojure project."
(interactive)
- (unless (file-directory-p (expand-file-name ob-clojure-literate-project-location))
- (make-directory ob-clojure-literate-project-location t)
- (let ((default-directory ob-clojure-literate-project-location))
- (shell-command "lein new ob-clojure")))
- (unless (or
- (and (cider-connected-p)
- (if (not (null ob-clojure-literate-session))
- (seq-contains cider-connections (get-buffer ob-clojure-literate-session))))
- cider-connections
- (not (null ob-clojure-literate-session)))
- ;; return back to original file.
- (if (not (and (= (length (ob-clojure-literate-get-session-list)) 1)
- (-contains-p (ob-clojure-literate-get-session-list) ob-clojure-literate-default-session)))
- (save-window-excursion
- (find-file (expand-file-name (concat ob-clojure-literate-project-location "ob-clojure/src/ob_clojure/core.clj")))
- (with-current-buffer "core.clj"
- (cider-jack-in))))))
+ (cond
+ ;; jack-in outside of Clojure project.
+ ((null ob-clojure-literate-project-location)
+ (if (member (get-buffer "*cider-repl localhost*") cider-connections)
+ (message "CIDER default session already launched.")
+ (cider-jack-in nil)))
+ ((not (null ob-clojure-literate-project-location))
+ (unless (file-directory-p (expand-file-name ob-clojure-literate-project-location))
+ (make-directory ob-clojure-literate-project-location t)
+ (let ((default-directory ob-clojure-literate-project-location))
+ (shell-command "lein new ob-clojure")))
+ (unless (or
+ (and (cider-connected-p)
+ (if (not (null ob-clojure-literate-session))
+ (seq-contains cider-connections (get-buffer ob-clojure-literate-session))))
+ cider-connections
+ (not (null ob-clojure-literate-session)))
+ ;; return back to original file.
+ (if (not (and (= (length (ob-clojure-literate-get-session-list)) 1)
+ (-contains-p (ob-clojure-literate-get-session-list) ob-clojure-literate-default-session)))
+ (save-window-excursion
+ (find-file (expand-file-name (concat ob-clojure-literate-project-location "ob-clojure/src/ob_clojure/core.clj")))
+ (with-current-buffer "core.clj"
+ (cider-jack-in))))))
+ ))
(defun ob-clojure-literate-set-local-cider-connections (toggle?)
"Set buffer local `cider-connections' for `ob-clojure-literate-mode' `TOGGLE?'."
--
2.17.0
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.3: 0002-ob-clojure-literate.el-support-use-ns-header-argumen.patch --]
[-- Type: text/x-patch, Size: 2952 bytes --]
From 5f14edb8ff3e8b1aaa14338753103c5bd961c014 Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Thu, 22 Mar 2018 01:43:18 +0800
Subject: [PATCH 2/6] * ob-clojure-literate.el: support use :ns header
argument.
- rename ob-clojure-literate-cider-do-not-find-ns to ob-clojure-literate-set-ns
---
contrib/lisp/ob-clojure-literate.el | 9 +++++----
1 file changed, 5 insertions(+), 4 deletions(-)
diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el
index 8d419b0b4..71ea909ba 100644
--- a/contrib/lisp/ob-clojure-literate.el
+++ b/contrib/lisp/ob-clojure-literate.el
@@ -151,14 +151,15 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a
;; (setq-local cider-connections '())
))
-(defun ob-clojure-literate-cider-do-not-find-ns (body params)
+(defun ob-clojure-literate-set-ns (body params)
"Fix the issue that `cider-current-ns' try to invoke `clojure-find-ns' to extract ns from buffer."
;; TODO: Is it possible to find ns in `body'?
(when (ob-clojure-literate-any-connection-p)
(setq ob-clojure-literate-original-ns (cider-current-ns))
(with-current-buffer ob-clojure-literate-session
(setq ob-clojure-literate-session-ns cider-buffer-ns))
- (setq-local cider-buffer-ns ob-clojure-literate-session-ns))
+ (setq-local cider-buffer-ns (or (cdr (assq :ns params))
+ ob-clojure-literate-session-ns)))
(message (format "ob-clojure-literate: current CIDER ns is [%s]." cider-buffer-ns)))
(defun ob-clojure-literate-set-local-session (toggle?)
@@ -302,7 +303,7 @@ reset `RESULT' to `nil'."
(equal major-mode 'org-mode)) ; `ob-clojure-literate-mode' only works in `org-mode'.
(ob-clojure-literate-set-local-cider-connections ob-clojure-literate-mode)
(ob-clojure-literate-set-local-session ob-clojure-literate-mode)
- (advice-add 'org-babel-execute:clojure :before #'ob-clojure-literate-cider-do-not-find-ns)
+ (advice-add 'org-babel-execute:clojure :before #'ob-clojure-literate-set-ns)
(advice-add 'org-babel-expand-body:clojure :filter-args #'ob-clojure-literate-inject-code)
(advice-add 'org-babel-execute:clojure :filter-return #'ob-clojure-literate-support-graphics-result)
(message "ob-clojure-literate minor mode enabled.")))
@@ -310,7 +311,7 @@ reset `RESULT' to `nil'."
;;;###autoload
(defun ob-clojure-literate-disable ()
"Disable Org-mode buffer locally for `ob-clojure-literate'."
- (advice-remove 'org-babel-execute:clojure #'ob-clojure-literate-cider-do-not-find-ns)
+ (advice-remove 'org-babel-execute:clojure #'ob-clojure-literate-set-ns)
(advice-remove 'org-babel-expand-body:clojure #'ob-clojure-literate-inject-code)
(advice-remove 'org-babel-execute:clojure #'ob-clojure-literate-support-graphics-result)
(setq-local cider-buffer-ns ob-clojure-literate-original-ns)
--
2.17.0
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.4: 0003-ob-clojure-literate.el-support-vars-initialization-w.patch --]
[-- Type: text/x-patch, Size: 1672 bytes --]
From 2676754c4f616d023efae75d7de7e0621a681616 Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Mon, 26 Mar 2018 09:47:54 +0800
Subject: [PATCH 3/6] * ob-clojure-literate.el: support vars initialization
when prepare session.
- org-babel-clojure-var-to-clojure
---
contrib/lisp/ob-clojure-literate.el | 12 +++++++++---
1 file changed, 9 insertions(+), 3 deletions(-)
diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el
index 71ea909ba..2d1d30db8 100644
--- a/contrib/lisp/ob-clojure-literate.el
+++ b/contrib/lisp/ob-clojure-literate.el
@@ -221,7 +221,14 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a
(defun org-babel-clojure-var-to-clojure (var)
"Convert src block's `VAR' to Clojure variable."
- ;; TODO: reference `org-babel-python-var-to-python'
+ (if (listp var)
+ (replace-regexp-in-string "(" "'(" var)
+ (cond
+ ((stringp var)
+ ;; wrap org-babel passed in header argument value with quote in Clojure.
+ (format "\"%s\"" var))
+ (t
+ (format "%s" var))))
)
(defun org-babel-variable-assignments:clojure (params)
@@ -230,8 +237,7 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a
(lambda (pair)
(format "(def %s %s)"
(car pair)
- ;; (org-babel-clojure-var-to-clojure (cdr pair))
- (cdr pair)))
+ (org-babel-clojure-var-to-clojure (cdr pair))))
(org-babel--get-vars params)))
;;; Support header arguments :results graphics :file "image.png" by inject Clojure code.
--
2.17.0
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.5: 0004-ob-clojure.el-org-babel-execute-clojure-support-ns-h.patch --]
[-- Type: text/x-patch, Size: 4306 bytes --]
From d59a789dd86359f3907163125389decf51d8da5d Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Mon, 26 Mar 2018 11:35:21 +0800
Subject: [PATCH 4/6] * ob-clojure.el (org-babel-execute:clojure) support :ns
header argument.
Remove optional parameter (cider-current-ns) to better handling namespace.
---
lisp/ob-clojure.el | 54 ++++++++++++++++++++++++++++++++++------------
1 file changed, 40 insertions(+), 14 deletions(-)
diff --git a/lisp/ob-clojure.el b/lisp/ob-clojure.el
index 890f60ada..35b4c3fe5 100644
--- a/lisp/ob-clojure.el
+++ b/lisp/ob-clojure.el
@@ -41,6 +41,7 @@
;;; Code:
(require 'cl-lib)
(require 'ob)
+(require 'subr-x)
(declare-function cider-current-connection "ext:cider-client" (&optional type))
(declare-function cider-current-ns "ext:cider-client" ())
@@ -55,6 +56,7 @@
(declare-function slime-eval "ext:slime" (sexp &optional package))
(defvar nrepl-sync-request-timeout)
+(defvar cider-buffer-ns)
(defvar org-babel-tangle-lang-exts)
(add-to-list 'org-babel-tangle-lang-exts '("clojure" . "clj"))
@@ -80,19 +82,43 @@ If the value is nil, timeout is disabled."
(const :tag "cider" cider)
(const :tag "SLIME" slime)))
+(defcustom org-babel-clojure-default-ns "user"
+ "Default Clojure namespace for src block when all find ns ways failed."
+ :type 'string
+ :group 'org-babel)
+
+(defun org-babel-clojure-cider-current-ns ()
+ "Like `cider-current-ns' except `cider-find-ns'."
+ (or cider-buffer-ns
+ (when-let* ((repl-buf (cider-current-connection)))
+ (buffer-local-value 'cider-buffer-ns repl-buf))
+ org-babel-clojure-default-ns))
+
(defun org-babel-expand-body:clojure (body params)
"Expand BODY according to PARAMS, return the expanded body."
(let* ((vars (org-babel--get-vars params))
+ (ns (cdr (assq :ns params)))
+ (ns-fallback (org-babel-clojure-cider-current-ns))
(result-params (cdr (assq :result-params params)))
(print-level nil) (print-length nil)
+ (bind-vars (lambda (body)
+ (if (null vars) (org-trim body)
+ (concat
+ "(let ["
+ (mapconcat
+ (lambda (var)
+ (format "%S (quote %S)" (car var) (cdr var)))
+ vars "\n ")
+ "]\n" body ")"))))
+ (specify-namespace (lambda (body)
+ (concat
+ "(ns " (if (null ns) ns-fallback ns) ")\n" body)))
(body (org-trim
- (if (null vars) (org-trim body)
- (concat "(let ["
- (mapconcat
- (lambda (var)
- (format "%S (quote %S)" (car var) (cdr var)))
- vars "\n ")
- "]\n" body ")")))))
+ (thread-last body
+ ;; variables binding
+ (funcall bind-vars)
+ ;; src block specified namespace :ns
+ (funcall specify-namespace)))))
(if (or (member "code" result-params)
(member "pp" result-params))
(format "(clojure.pprint/pprint (do %s))" body)
@@ -102,9 +128,11 @@ If the value is nil, timeout is disabled."
"Execute a block of Clojure code with Babel.
The underlying process performed by the code block can be output
using the :show-process parameter."
- (let ((expanded (org-babel-expand-body:clojure body params))
- (response (list 'dict))
- result)
+ (let* ((expanded (org-babel-expand-body:clojure body params))
+ (ns (cdr (assq :ns params)))
+ (ns-fallback (org-babel-clojure-cider-current-ns))
+ (response (list 'dict))
+ result)
(cl-case org-babel-clojure-backend
(cider
(require 'cider)
@@ -117,8 +145,7 @@ using the :show-process parameter."
(let ((nrepl-sync-request-timeout
org-babel-clojure-sync-nrepl-timeout))
(nrepl-sync-request:eval expanded
- (cider-current-connection)
- (cider-current-ns))))
+ (cider-current-connection))))
(setq result
(concat
(nrepl-dict-get response
@@ -152,8 +179,7 @@ using the :show-process parameter."
(nrepl--merge response resp)
;; Update the status of the nREPL output session.
(setq status (nrepl-dict-get response "status")))
- (cider-current-connection)
- (cider-current-ns))
+ (cider-current-connection))
;; Wait until the nREPL code finished to be processed.
(while (not (member "done" status))
--
2.17.0
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.6: 0005-ob-clojure-literate.el-ob-clojure-literate-get-sessi.patch --]
[-- Type: text/x-patch, Size: 2017 bytes --]
From 78948e652621f0e46ce52761aa6f372c5a919ece Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Mon, 2 Apr 2018 11:58:28 +0800
Subject: [PATCH 5/6] * ob-clojure-literate.el
(ob-clojure-literate-get-session-list)
get session from global connections list.
---
contrib/lisp/ob-clojure-literate.el | 10 +++++++---
1 file changed, 7 insertions(+), 3 deletions(-)
diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el
index 2d1d30db8..0c928572b 100644
--- a/contrib/lisp/ob-clojure-literate.el
+++ b/contrib/lisp/ob-clojure-literate.el
@@ -63,7 +63,11 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a
(defun ob-clojure-literate-get-session-list ()
"Return a list of available started CIDER REPL sessions list."
- (-map 'buffer-name cider-connections))
+ (-map 'buffer-name
+ ;; for multiple connections case.
+ ;; get global value instead of buffer local.
+ (default-value 'cider-connections)
+ ))
(defun ob-clojure-literate-set-session ()
"Set session name for buffer local."
@@ -82,7 +86,7 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a
))
;;;###autoload
-(defun ob-clojure-literate-specify-session-header-argument ()
+(defun ob-clojure-literate-specify-session ()
"Specify ob-clojure header argument :session with value selected from a list of available sessions."
(interactive)
(let ((lang (nth 0 (org-babel-get-src-block-info))))
@@ -297,7 +301,7 @@ reset `RESULT' to `nil'."
map)
"Keymap for `ob-clojure-literate-mode'.")
-(define-key org-babel-map (kbd "M-s") 'ob-clojure-literate-specify-session-header-argument)
+(define-key org-babel-map (kbd "M-s") 'ob-clojure-literate-specify-session)
(define-key org-babel-map (kbd "M-j") 'ob-clojure-literate-auto-jackin)
;; (define-key org-babel-map (kbd "M-e") 'cider-eval-last-sexp)
;; (define-key org-babel-map (kbd "M-d") 'cider-doc)
--
2.17.0
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #1.7: 0006-ob-clojure-literate.el-ob-clojure-literate-inject-co.patch --]
[-- Type: text/x-patch, Size: 1143 bytes --]
From 7eeecfe2e0009c99f197c2e4eedb68d92bb58e89 Mon Sep 17 00:00:00 2001
From: stardiviner <numbchild@gmail.com>
Date: Mon, 2 Apr 2018 13:47:28 +0800
Subject: [PATCH 6/6] * ob-clojure-literate.el
(ob-clojure-literate-inject-code)
Handle no :file specified file is nil case.
---
contrib/lisp/ob-clojure-literate.el | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el
index 0c928572b..5dec2ad9b 100644
--- a/contrib/lisp/ob-clojure-literate.el
+++ b/contrib/lisp/ob-clojure-literate.el
@@ -265,7 +265,7 @@ Then you need to assign image variable to this :file value like:
(directory (and dir (file-name-as-directory (expand-file-name dir))))
(result-type (cdr (assq :results params)))
(file (cdr (assq :file params)))
- (file-name (file-name-base file))
+ (file-name (and file (file-name-base file)))
;; TODO: future support `:graphics-file' to avoid collision.
(graphics-result (member "graphics" (cdr (assq :result-params params))))
;; (graphics-file (cdr (assq :graphics-file params)))
--
2.17.0
[-- Attachment #1.8: Type: text/plain, Size: 187 bytes --]
--
[ stardiviner ] don't need to convince with trends.
Blog: https://stardiviner.github.io/
IRC(freenode): stardiviner
GPG: F09F650D7D674819892591401B5DF1C95AE89AC3
[-- Attachment #2: signature.asc --]
[-- Type: application/pgp-signature, Size: 487 bytes --]
next reply other threads:[~2018-04-13 13:33 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-04-13 12:55 stardiviner [this message]
2018-04-14 16:31 ` [PATCH] ob-clojure.el and ob-clojure-literate.el support new header argument :ns Nicolas Goaziou
2018-04-15 1:54 ` stardiviner
2018-04-15 7:32 ` Nicolas Goaziou
2018-04-23 8:30 ` Bastien
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://www.orgmode.org/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=87zi272rlu.fsf@gmail.com \
--to=numbchild@gmail.com \
--cc=emacs-orgmode@gnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/emacs/org-mode.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).