From mboxrd@z Thu Jan 1 00:00:00 1970 From: stardiviner Subject: Re: [PATCH] migrate ob-clojure initiate session code from ob-clojure-literate.el into ob-clojure.el Date: Thu, 25 Oct 2018 13:51:12 +0800 Message-ID: <875zxqr2un.fsf@gmail.com> References: <87a7tza42f.fsf@gmail.com> <87o9iegsn7.fsf@nicolasgoaziou.fr> <877ei8uaz1.fsf@gmail.com> <874ldby3k2.fsf@nicolasgoaziou.fr> Reply-To: numbchild@gmail.com Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="=-=-=" Return-path: Received: from eggs.gnu.org ([2001:4830:134:3::10]:42689) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1gFYYD-0004NJ-E3 for emacs-orgmode@gnu.org; Thu, 25 Oct 2018 01:51:23 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1gFYY7-00052S-N7 for emacs-orgmode@gnu.org; Thu, 25 Oct 2018 01:51:20 -0400 Received: from [61.175.244.13] (port=37959 helo=dark.localdomain) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1gFYY6-000520-Uo for emacs-orgmode@gnu.org; Thu, 25 Oct 2018 01:51:15 -0400 In-reply-to: <874ldby3k2.fsf@nicolasgoaziou.fr> List-Id: "General discussions about Org-mode." List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: emacs-orgmode-bounces+geo-emacs-orgmode=m.gmane.org@gnu.org Sender: "Emacs-orgmode" To: Nicolas Goaziou Cc: org-mode --=-=-= Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: quoted-printable Nicolas Goaziou writes: > Hello, > > stardiviner writes: > >> Nicolas Goaziou writes: >> >> Hi, sorry for late response, because I'm a little lazy on give effort on >> review my patch and improve it again. But now I finished it. Actually I >> corrected my patch as soon as you replied email with mentioned. Today I >> pick up this task again, and add a new improve which support CIDER new >> API which using sesman to manage REPL sessions. > > OK. So does it qualify as a bug fix, i.e., should that go into master > branch, or is it a new feature, for next branch? > > BTW, there are some compilation warning: > > --8<---------------cut here---------------start------------->8--- > Compiling /home/ngz/dev/org-mode/lisp/ob-clojure.el... > > In toplevel form: > ob-clojure.el:215:1:Warning: Unused lexical variable =E2=80=98sesman-syst= em=E2=80=99 > > In org-babel-clojure-initiate-session: > ob-clojure.el:225:47:Warning: reference to free variable =E2=80=98cider-v= ersion=E2=80=99 > > In end of data: > ob-clojure.el:278:1:Warning: the function =E2=80=98cider-repls=E2=80=99 i= s not known to be > defined. > --8<---------------cut here---------------end--------------->8--- > > Could you fix them? > > Thank you. > > Regards, Hi, Nicolas. I fixed those warning. I think this should be a feature. not a= patch. And run `make test`. Here is the result: ``` ... executing Vala source code block Code block evaluation complete. passed 138/814 ob-vala/static-output failed 139/814 org-missing-dependency/test-ob-R failed 140/814 org-missing-dependency/test-ob-clojure failed 141/814 org-missing-dependency/test-ob-lua failed 142/814 org-missing-dependency/test-ob-maxima failed 143/814 org-missing-dependency/test-ob-plantuml failed 144/814 org-missing-dependency/test-ob-ruby failed 145/814 org-missing-dependency/test-ob-scheme failed 146/814 org-missing-dependency/test-org-attach-annex failed 147/814 org-missing-dependency/test-org-protocol passed 148/814 test-ob-exp/org-babel-exp-src-blocks/w-no-file passed 149/814 test-ob-exp/org-babel-exp-src-blocks/w-no-headers passed 150/814 test-ob-exp/org-babel-exp-src-blocks/w-no-headers2 executing Emacs-Lisp code block... ..... ..... 6 unexpected results: FAILED ob-D/inhomogeneous_table FAILED ob-D/list-list-var FAILED ob-D/list-var FAILED ob-D/vector-var FAILED test-org-clock/clocktable/lang FAILED test-org-colview/columns-width ``` Also I added an entry in ORG-NEWS mentioned about this new feature. --=-=-= Content-Type: text/x-patch Content-Disposition: attachment; filename=0001-ob-clojure.el-Support-org-babel-initiate-session-to-.patch >From f495c5b4e65fd8c6a64e8619d974d6eb051fb1f7 Mon Sep 17 00:00:00 2001 From: stardiviner Date: Thu, 19 Apr 2018 18:16:27 +0800 Subject: [PATCH 1/2] ob-clojure.el: Support `org-babel-initiate-session' to initialize. * ob-clojure.el (org-babel-clojure-initiate-session): Initialize session for src block. (org-babel-prep-session:clojure): Prepare Clojure session. (org-babel-clojure-var-to-clojure): Convert header argument :var into clojure variables definitions. (org-babel-variable-assignments:clojure): Support assign variables when initialize session. --- contrib/lisp/ob-clojure-literate.el | 56 --------------------- lisp/ob-clojure.el | 55 +++++++++++++++++++++ testing/lisp/test-ob-clojure.el | 77 +++++++++++++++++++++++++++++ 3 files changed, 132 insertions(+), 56 deletions(-) create mode 100644 testing/lisp/test-ob-clojure.el diff --git a/contrib/lisp/ob-clojure-literate.el b/contrib/lisp/ob-clojure-literate.el index 4c4d38a0f..b1cc386ee 100644 --- a/contrib/lisp/ob-clojure-literate.el +++ b/contrib/lisp/ob-clojure-literate.el @@ -184,62 +184,6 @@ If it is a directory, `ob-clojure-literate' will try to create Clojure project a (lambda (cons) (if (eq (car cons) :session) t cons)) org-babel-default-header-args:clojure))))) -;;; Support `org-babel-initiate-session' / [C-c C-v z] to initialize Clojure session. - -(defun org-babel-clojure-initiate-session (&optional session _params) - "Initiate a session named SESSION according to PARAMS." - (when (and session (not (string= session "none"))) - (save-window-excursion - (unless (org-babel-comint-buffer-livep session) - ;; CIDER jack-in to the Clojure project directory. - (cond - ((eq org-babel-clojure-backend 'cider) - (require 'cider) - (let ((session-buffer (save-window-excursion - (cider-jack-in t) - (current-buffer)))) - (if (org-babel-comint-buffer-livep session-buffer) - (progn (sit-for .25) session-buffer)))) - ((eq org-babel-clojure-backend 'slime) - (error "Session evaluation with SLIME is not supported")) - (t - (error "Session initiate failed"))) - ) - (get-buffer session) - ))) - -(defun org-babel-prep-session:clojure (session params) - "Prepare SESSION according to the header arguments specified in PARAMS." - (let* ((session (org-babel-clojure-initiate-session session)) - (var-lines (org-babel-variable-assignments:clojure params))) - (when session - (org-babel-comint-in-buffer session - (mapc (lambda (var) - (insert var) (comint-send-input nil t) - (org-babel-comint-wait-for-output session) - (sit-for .1) (goto-char (point-max))) var-lines))) - session)) - -(defun org-babel-clojure-var-to-clojure (var) - "Convert src block's `VAR' to Clojure variable." - (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) - "Return a list of Clojure statements assigning the block's variables in `PARAMS'." - (mapcar - (lambda (pair) - (format "(def %s %s)" - (car 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. (defun ob-clojure-literate-inject-code (args) diff --git a/lisp/ob-clojure.el b/lisp/ob-clojure.el index d5b918b01..048ba3735 100644 --- a/lisp/ob-clojure.el +++ b/lisp/ob-clojure.el @@ -43,6 +43,7 @@ (require 'ob) (require 'org-macs) +(declare-function cider-jack-in "ext:cider" (&optional prompt-project cljs-too)) (declare-function cider-current-connection "ext:cider-client" (&optional type)) (declare-function cider-current-ns "ext:cider-client" ()) (declare-function nrepl--merge "ext:nrepl-client" (dict1 dict2)) @@ -211,6 +212,60 @@ using the :show-process parameter." (condition-case nil (org-babel-script-escape result) (error result))))) +(defun org-babel-clojure-initiate-session (&optional session _params) + "Initiate a session named SESSION according to PARAMS." + (when (and session (not (string= session "none"))) + (save-window-excursion + (cond + ((org-babel-comint-buffer-livep session) nil) + ;; CIDER jack-in to the Clojure project directory. + ((eq org-babel-clojure-backend 'cider) + (require 'cider) + (let ((session-buffer (save-window-excursion + (cider-jack-in t) + (current-buffer)))) + (if (org-babel-comint-buffer-livep session-buffer) + (progn (sit-for .25) session-buffer)))) + ((eq org-babel-clojure-backend 'slime) + (error "Session evaluation with SLIME is not supported")) + (t + (error "Session initiate failed"))) + (get-buffer session)))) + +(defun org-babel-prep-session:clojure (session params) + "Prepare SESSION according to the header arguments specified in PARAMS." + (let ((session (org-babel-clojure-initiate-session session)) + (var-lines (org-babel-variable-assignments:clojure params))) + (when session + (org-babel-comint-in-buffer session + (dolist (var var-lines) + (insert var) + (comint-send-input nil t) + (org-babel-comint-wait-for-output session) + (sit-for .1) + (goto-char (point-max))))) + session)) + +(defun org-babel-clojure-var-to-clojure (var) + "Convert src block's VAR to Clojure variable." + (cond + ((listp var) + (replace-regexp-in-string "(" "'(" var)) + ((stringp var) + ;; Wrap Babel passed-in header argument value with quotes in Clojure. + (format "\"%s\"" var)) + (t + (format "%S" var)))) + +(defun org-babel-variable-assignments:clojure (params) + "Return a list of Clojure statements assigning the block's variables in PARAMS." + (mapcar + (lambda (pair) + (format "(def %s %s)" + (car pair) + (org-babel-clojure-var-to-clojure (cdr pair)))) + (org-babel--get-vars params))) + (provide 'ob-clojure) ;;; ob-clojure.el ends here diff --git a/testing/lisp/test-ob-clojure.el b/testing/lisp/test-ob-clojure.el new file mode 100644 index 000000000..f917ca4cc --- /dev/null +++ b/testing/lisp/test-ob-clojure.el @@ -0,0 +1,77 @@ +;;; test-ob-clojure.el + +;; Copyright (c) 2018-2022 Free Software Foundation, Inc. +;; Authors: stardiviner + +;; This file is not part of GNU Emacs. + +;; This program is free software; you can redistribute it and/or modify +;; it under the terms of the GNU General Public License as published by +;; the Free Software Foundation, either version 3 of the License, or +;; (at your option) any later version. + +;; This program is distributed in the hope that it will be useful, +;; but WITHOUT ANY WARRANTY; without even the implied warranty of +;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +;; GNU General Public License for more details. + +;; You should have received a copy of the GNU General Public License +;; along with this program. If not, see . + +;;; Comments: + +;; Org tests for ob-clojure.el live here + +;;; Code: +(org-test-for-executable "cider") +(unless (featurep 'cider) + (signal 'missing-test-dependency "CIDER")) +(unless (featurep 'ob-clojure) + (signal 'missing-test-dependency "Support for Clojure code blocks")) + +(ert-deftest ob-clojure/simple-session () + (org-test-with-temp-text + "#+begin_src clojure :session +(print \"hello, world\") +#+end_src +" + (should (string= "hello, world" (org-babel-execute-src-block))))) + +(ert-deftest ob-clojure/initiate-session () + (org-test-with-temp-text + "#+begin_src clojure :session :var a=1 :results output +(print \"hello, world\") +#+end_src + +#+begin_src clojure :session :results output +(print a) +#+end_src" + (goto-char (point-min)) + (org-babel-switch-to-session) + (sleep-for 2) + (org-babel-execute-maybe) + (org-babel-next-src-block) + (goto-char (org-babel-result-end)) + (forward-line 2) + (should (string= + ": 1" + (buffer-substring-no-properties (point-at-bol) (point-at-eol)))))) + +(ert-deftest ob-clojure/initiate-session-with-var () + (org-test-with-temp-text + "#+begin_src clojure :session :var a=1 :results output +(print a) +#+end_src" + (org-babel-next-src-block) + (org-babel-initiate-session) + (sleep-for 2) + (org-babel-execute-maybe) + (goto-char (org-babel-result-end)) + (forward-line 2) + (should (string= + ": 1" + (buffer-substring-no-properties (point-at-bol) (point-at-eol)))))) + +(provide 'test-ob-clojure) + + ;;; test-ob-clojure.el ends here -- 2.19.1 --=-=-= Content-Type: text/x-patch Content-Disposition: attachment; filename=0002-ob-clojure.el-Support-new-CIDER-using-sesman-to-mana.patch >From 62dc8625005af2e1be9e1e3dde897e294bd56324 Mon Sep 17 00:00:00 2001 From: stardiviner Date: Tue, 23 Oct 2018 19:23:45 +0800 Subject: [PATCH 2/2] ob-clojure.el: Support new CIDER using sesman to manage sessions. * ob-clojure.el (org-babel-clojure-initiate-session): improve ob-clojure initialize session way to support CIDER new API. * etc/ORG-NEWS: add declare for new :session support feature. --- etc/ORG-NEWS | 11 +++++++++++ lisp/ob-clojure.el | 11 ++++++++++- 2 files changed, 21 insertions(+), 1 deletion(-) diff --git a/etc/ORG-NEWS b/etc/ORG-NEWS index 811e98147..100f9fd75 100644 --- a/etc/ORG-NEWS +++ b/etc/ORG-NEWS @@ -170,6 +170,17 @@ This is consistent with the naming of =org-dblock-write:columnview= options, where =:match= is also used as a headlines filter. ** New features +*** Add ~:session~ support of ob-clojure for CIDER +You can initialize source block session with Babel default keybinding +=[C-c C-v C-z]= to use =sesman= session manager to link current +project, directory or buffer with specific Clojure session, or +=cider-jack-in= a new CIDER REPL if no CIDER REPLs available. In older +CIDER version which has not =sesman= integrated, only has +=cider-jack-in= without Clojure project is supported. +#+begin_src clojure :session +(dissoc Clojure 'JVM) +(conj clojurists "stardiviner") +#+end_src *** Add ~:results link~ support for Babel With this output format, create a link to the file specified in diff --git a/lisp/ob-clojure.el b/lisp/ob-clojure.el index 048ba3735..ffac3c149 100644 --- a/lisp/ob-clojure.el +++ b/lisp/ob-clojure.el @@ -46,6 +46,7 @@ (declare-function cider-jack-in "ext:cider" (&optional prompt-project cljs-too)) (declare-function cider-current-connection "ext:cider-client" (&optional type)) (declare-function cider-current-ns "ext:cider-client" ()) +(declare-function cider-repls "ext:cider-connection" (&optional type ensure)) (declare-function nrepl--merge "ext:nrepl-client" (dict1 dict2)) (declare-function nrepl-dict-get "ext:nrepl-client" (dict key)) (declare-function nrepl-dict-put "ext:nrepl-client" (dict key value)) @@ -55,6 +56,8 @@ (defvar nrepl-sync-request-timeout) (defvar cider-buffer-ns) +(defvar sesman-system) +(defvar cider-version) (defvar org-babel-tangle-lang-exts) (add-to-list 'org-babel-tangle-lang-exts '("clojure" . "clj")) @@ -222,7 +225,13 @@ using the :show-process parameter." ((eq org-babel-clojure-backend 'cider) (require 'cider) (let ((session-buffer (save-window-excursion - (cider-jack-in t) + (if (version< cider-version "0.18.0") + ;; older CIDER (without sesman) still need to use old way. + (cider-jack-in nil) ; nil for jack-in without project. + ;; new CIDER (with sesman to manage sessions) + (unless (cider-repls) + (let ((sesman-system 'CIDER)) + (call-interactively 'sesman-link-with-directory)))) (current-buffer)))) (if (org-babel-comint-buffer-livep session-buffer) (progn (sit-for .25) session-buffer)))) -- 2.19.1 --=-=-= Content-Type: text/plain -- [ stardiviner ] I try to make every word tell the meaning what I want to express. Blog: https://stardiviner.github.io/ IRC(freenode): stardiviner GPG: F09F650D7D674819892591401B5DF1C95AE89AC3 --=-=-=--