emacs-elpa-diffs
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[nongnu] elpa/cider 64819740ef 1/3: Always escape clojure cli command pa


From: ELPA Syncer
Subject: [nongnu] elpa/cider 64819740ef 1/3: Always escape clojure cli command params on MS-win
Date: Thu, 18 May 2023 02:00:11 -0400 (EDT)

branch: elpa/cider
commit 64819740efc952ec3d44a0e6041dca6e8f122611
Author: ikappaki <ikappaki@users.noreply.github.com>
Commit: Bozhidar Batsov <bozhidar@batsov.dev>

    Always escape clojure cli command params on MS-win
    
    even for non powershell invocations
---
 .github/workflows/test.yml            |   7 ++
 CHANGELOG.md                          |   4 +
 cider.el                              |  79 ++++++++--------
 test/integration/integration-tests.el | 165 ++++++++++++++++++----------------
 4 files changed, 142 insertions(+), 113 deletions(-)

diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml
index fb8701862b..8fd31cd774 100644
--- a/.github/workflows/test.yml
+++ b/.github/workflows/test.yml
@@ -43,6 +43,13 @@ jobs:
 
         curl.exe -fsSL 
https://raw.github.com/doublep/eldev/master/webinstall/github-eldev.bat | cmd /Q
 
+    - name: Install deps.clj on MS-Windows
+      if: startsWith (matrix.os, 'windows')
+      run: |
+        iwr -Uri 
https://raw.githubusercontent.com/borkdude/deps.clj/master/install.ps1 -outfile 
install_clojure.ps1
+        .\install_clojure.ps1
+        get-command deps.exe | split-path -parent | Out-File -FilePath 
$env:GITHUB_PATH -Encoding utf8 -Append
+
     - name: Check out the source code
       uses: actions/checkout@v2
 
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 6bf84be361..cd971ccfbc 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -2,6 +2,10 @@
 
 ## master (unreleased)
 
+### Bugs
+
+- [#3341](https://github.com/clojure-emacs/cider/issues/3341): Escape 
clojure-cli args on MS-Windows on non powershell invocations.
+
 ## 1.7.0 (2023-03-23)
 
 ### New features
diff --git a/cider.el b/cider.el
index 13518e13b7..bb39bd3b23 100644
--- a/cider.el
+++ b/cider.el
@@ -744,12 +744,19 @@ removed, LEIN-PLUGINS, LEIN-MIDDLEWARES and finally 
PARAMS."
   "Removes the duplicates in DEPS."
   (cl-delete-duplicates deps :test 'equal))
 
-(defun cider-clojure-cli-jack-in-dependencies (global-options params 
dependencies)
+(defun cider--powershell-encode-command (cmd-params)
+  "Base64 encode the powershell command and jack-in CMD-PARAMS for 
clojure-cli."
+  (let* ((quoted-params (replace-regexp-in-string "\"" "\"\"" cmd-params))
+         (command (format "clojure %s" quoted-params))
+         (utf-16le-command (encode-coding-string command 'utf-16le)))
+    (format "-encodedCommand %s" (base64-encode-string utf-16le-command t))))
+
+(defun cider-clojure-cli-jack-in-dependencies (global-options params 
dependencies command)
   "Create Clojure tools.deps jack-in dependencies.
-Does so by concatenating DEPENDENCIES, PARAMS and GLOBAL-OPTIONS into a 
suitable
-`clojure` invocation.  The main is placed in an inline alias :cider/nrepl
-so that if your aliases contain any mains, the cider/nrepl one will be the
-one used."
+Does so by concatenating DEPENDENCIES, PARAMS and GLOBAL-OPTIONS into a
+suitable `clojure` invocation and quoting it based on COMMAND if necessary.
+The main is placed in an inline alias :cider/nrepl so that if your aliases
+contain any mains, the cider/nrepl one will be the one used."
   (let* ((all-deps (thread-last
                      dependencies
                      (append (cider--jack-in-required-dependencies))
@@ -770,18 +777,26 @@ one used."
                       (apply-partially #'format "%s")
                       (cider-jack-in-normalized-nrepl-middlewares)
                       ","))
-         (main-opts (format "\"-m\" \"nrepl.cmdline\" \"--middleware\" 
\"[%s]\"" middleware)))
-    (format "%s-Sdeps '{:deps {%s} :aliases {:cider/nrepl {:main-opts [%s]}}}' 
-M%s:cider/nrepl%s"
-            ;; TODO: global-options are deprecated and should be removed in 
CIDER 2.0
-            (if global-options (format "%s " global-options) "")
-            (string-join all-deps " ")
-            main-opts
-            (if cider-clojure-cli-aliases
-                ;; remove exec-opts flags -A -M -T or -X from 
cider-clojure-cli-aliases
-                ;; concatenated with :cider/nrepl to ensure :cider/nrepl comes 
last
-                (format "%s" (replace-regexp-in-string "^-\\(A\\|M\\|T\\|X\\)" 
"" cider-clojure-cli-aliases))
-              "")
-            (if params (format " %s" params) ""))))
+         (main-opts (format "\"-m\" \"nrepl.cmdline\" \"--middleware\" 
\"[%s]\"" middleware))
+         (deps (format "%s-Sdeps '{:deps {%s} :aliases {:cider/nrepl 
{:main-opts [%s]}}}' -M%s:cider/nrepl%s"
+                       ;; TODO: global-options are deprecated and should be 
removed in CIDER 2.0
+                       (if global-options (format "%s " global-options) "")
+                       (string-join all-deps " ")
+                       main-opts
+                       (if cider-clojure-cli-aliases
+                           ;; remove exec-opts flags -A -M -T or -X from 
cider-clojure-cli-aliases
+                           ;; concatenated with :cider/nrepl to ensure 
:cider/nrepl comes last
+                           (format "%s" (replace-regexp-in-string 
"^-\\(A\\|M\\|T\\|X\\)" "" cider-clojure-cli-aliases))
+                         "")
+                       (if params (format " %s" params) "")))
+         (quoted (if (eq system-type 'windows-nt)
+                     (if (or (string-equal command "powershell")
+                             (string-equal command "pwsh"))
+                         (cider--powershell-encode-command deps)
+                       (thread-last (replace-regexp-in-string "\"" "\"\"" deps)
+                                    (replace-regexp-in-string "'" "\"")))
+                   deps)))
+    quoted))
 
 (defun cider-shadow-cljs-jack-in-dependencies (global-opts params dependencies)
   "Create shadow-cljs jack-in deps.
@@ -813,13 +828,13 @@ See also `cider-jack-in-auto-inject-clojure'."
               dependencies))
     dependencies))
 
-(defun cider-inject-jack-in-dependencies (global-opts params project-type)
+(defun cider-inject-jack-in-dependencies (global-opts params project-type 
command)
   "Return GLOBAL-OPTS and PARAMS with injected REPL dependencies.
-These are set in `cider-jack-in-dependencies', `cider-jack-in-lein-plugins' and
-`cider-jack-in-nrepl-middlewares' are injected from the CLI according to
-the used PROJECT-TYPE.  Eliminates the need for hacking profiles.clj or the
-boot script for supporting CIDER with its nREPL middleware and
-dependencies."
+These are set in `cider-jack-in-dependencies', `cider-jack-in-lein-plugins'
+and `cider-jack-in-nrepl-middlewares' are injected from the CLI according
+to the used PROJECT-TYPE and COMMAND. Eliminates the need for hacking
+profiles.clj or the boot script for supporting CIDER with its nREPL
+middleware and dependencies."
   (pcase project-type
     ('lein (cider-lein-jack-in-dependencies
             global-opts
@@ -842,7 +857,8 @@ dependencies."
                    global-opts
                    params
                    (cider-add-clojure-dependencies-maybe
-                    cider-jack-in-dependencies)))
+                    cider-jack-in-dependencies)
+                   command))
     ('babashka (concat
                 global-opts
                 (unless (seq-empty-p global-opts) " ")
@@ -1510,13 +1526,6 @@ Params is a plist with the following keys 
(non-exhaustive)
 (defvar cider--jack-in-cmd-history nil
   "History list for user-specified jack-in commands.")
 
-(defun cider--powershell-encode-command (cmd-params)
-  "Base64 encode the powershell command and jack-in CMD-PARAMS for 
clojure-cli."
-  (let* ((quoted-params (replace-regexp-in-string "\"" "\"\"" cmd-params))
-         (command (format "clojure %s" quoted-params))
-         (utf-16le-command (encode-coding-string command 'utf-16le)))
-    (format "-encodedCommand %s" (base64-encode-string utf-16le-command t))))
-
 (defun cider--update-jack-in-cmd (params)
   "Update :jack-in-cmd key in PARAMS.
 
@@ -1546,7 +1555,8 @@ PARAMS is a plist with the following keys (non-exhaustive 
list)
                                                       
'cider--jack-in-nrepl-params-history)
                                        command-params))
                      (cmd-params (if cider-inject-dependencies-at-jack-in
-                                     (cider-inject-jack-in-dependencies 
command-global-opts command-params project-type)
+                                     (cider-inject-jack-in-dependencies 
command-global-opts command-params
+                                                                        
project-type command)
                                    command-params)))
                 (if (or project-dir cider-allow-jack-in-without-project)
                     (when (or project-dir
@@ -1555,10 +1565,7 @@ PARAMS is a plist with the following keys 
(non-exhaustive list)
                                    (eq cider-allow-jack-in-without-project 
'warn)
                                    (or params-project-type
                                        (y-or-n-p "Are you sure you want to run 
`cider-jack-in' without a Clojure project? "))))
-                      (let ((cmd (format "%s %s" command-resolved (if (or 
(string-equal command "powershell")
-                                                                          
(string-equal command "pwsh"))
-                                                                      
(cider--powershell-encode-command cmd-params)
-                                                                    
cmd-params))))
+                      (let ((cmd (format "%s %s" command-resolved cmd-params)))
                         (plist-put params :jack-in-cmd (if (or 
cider-edit-jack-in-command
                                                                (plist-get 
params :edit-jack-in-command))
                                                            (read-string 
"jack-in command: " cmd 'cider--jack-in-cmd-history)
diff --git a/test/integration/integration-tests.el 
b/test/integration/integration-tests.el
index dd4907a86a..fe3c853a78 100644
--- a/test/integration/integration-tests.el
+++ b/test/integration/integration-tests.el
@@ -31,72 +31,11 @@
 (require 'nrepl-tests-utils "test/utils/nrepl-tests-utils")
 (require 'integration-test-utils)
 
-(describe "jack in"
-  ;; For each project tool, create a project in a temp directory,
-  ;; jack-in to it, send an eval command to the REPL server specific to the
-  ;; project to ensure it works, and finally exit the REPL.
+(defun jack-in-clojure-cli-test (cli-command)
+  "Run clojure cli jack in test using given CLI-COMMAND.
 
-  (it "to babashka"
-    (with-cider-test-sandbox
-      (with-temp-dir temp-dir
-        ;; Create a project in temp dir
-        (let* ((project-dir temp-dir)
-               (bb-edn (expand-file-name "bb.edn" project-dir)))
-          (write-region "{}" nil bb-edn)
-
-          (with-temp-buffer
-            ;; set default directory to temp project
-            (setq-local default-directory project-dir)
-
-            (let* (;; Get a gv reference so as to poll if the client has
-                   ;; connected to the nREPL server.
-                   (client-is-connected* 
(cider-itu-nrepl-client-connected-ref-make!))
-
-                   ;; jack in and get repl buffer
-                   (nrepl-proc (cider-jack-in-clj '()))
-                   (nrepl-buf (process-buffer nrepl-proc)))
-
-              ;; wait until the client has successfully connected to the
-              ;; nREPL server.
-              (cider-itu-poll-until (eq (gv-deref client-is-connected*) 
'connected) 5)
-
-              ;; give it some time to setup the clj REPL
-              (cider-itu-poll-until (cider-repls 'clj nil) 5)
-
-              ;; send command to the REPL, and push stdout/stderr to
-              ;; corresponding eval-xxx variables.
-              (let ((repl-buffer (cider-current-repl))
-                    (eval-err '())
-                    (eval-out '()))
-                (expect repl-buffer :not :to-be nil)
-
-                ;; send command to the REPL
-                (cider-interactive-eval
-                 ;; ask REPL to return a string that uniquely identifies it.
-                 "(print :bb? (some? (System/getProperty 
\"babashka.version\")))"
-                 (lambda (return)
-                   (nrepl-dbind-response
-                       return
-                       (out err)
-                     (when err (push err eval-err))
-                     (when out (push out eval-out)))) )
-
-                ;; wait for a response to come back.
-                (cider-itu-poll-until (or eval-err eval-out) 5)
-
-                ;; ensure there are no errors and response is as expected.
-                (expect eval-err :to-equal '())
-                (expect eval-out :to-equal '(":bb? true"))
-
-                ;; exit the REPL.
-                (cider-quit repl-buffer)
-
-                ;; wait for the REPL to exit
-                (cider-itu-poll-until (not (eq (process-status nrepl-proc) 
'run)) 5)
-                (expect (member (process-status nrepl-proc) '(exit 
signal))))))))))
-
-  (it "to clojure tools cli"
-    (with-cider-test-sandbox
+If CLI-COMMAND is nil, then use the default."
+  (with-cider-test-sandbox
       (with-temp-dir temp-dir
         ;; Create a project in temp dir
         (let* ((project-dir temp-dir)
@@ -109,6 +48,7 @@
                 ;; than the default timeout period to complete.
                 (nrepl-sync-request-timeout 30)
 
+                (cider-clojure-cli-command (or cli-command 
cider-clojure-cli-command))
                 (cider-jack-in-nrepl-middlewares
                  (append '("ikappaki.nrepl-mdlw-log/middleware") 
cider-jack-in-nrepl-middlewares)))
 
@@ -177,15 +117,18 @@
                       (message ":ikappaki/nrepl-mdlw-log-dump\n%s\n" 
(buffer-string)))
                   (message ":!nrepl-mdlw-log-found")))))))))
 
-  (it "to leiningen"
+(describe "jack in"
+  ;; For each project tool, create a project in a temp directory,
+  ;; jack-in to it, send an eval command to the REPL server specific to the
+  ;; project to ensure it works, and finally exit the REPL.
+
+  (it "to babashka"
     (with-cider-test-sandbox
       (with-temp-dir temp-dir
         ;; Create a project in temp dir
         (let* ((project-dir temp-dir)
-               (project-clj (expand-file-name "project.clj" project-dir)))
-          (write-region "(defproject cider/integration \"test\"
-                           :dependencies [[org.clojure/clojure \"1.10.3\"]])"
-                        nil project-clj)
+               (bb-edn (expand-file-name "bb.edn" project-dir)))
+          (write-region "{}" nil bb-edn)
 
           (with-temp-buffer
             ;; set default directory to temp project
@@ -196,15 +139,15 @@
                    (client-is-connected* 
(cider-itu-nrepl-client-connected-ref-make!))
 
                    ;; jack in and get repl buffer
-                   (nrepl-proc (cider-jack-in-clj `()))
+                   (nrepl-proc (cider-jack-in-clj '()))
                    (nrepl-buf (process-buffer nrepl-proc)))
 
               ;; wait until the client has successfully connected to the
               ;; nREPL server.
-              (cider-itu-poll-until (eq (gv-deref client-is-connected*) 
'connected) 90)
+              (cider-itu-poll-until (eq (gv-deref client-is-connected*) 
'connected) 5)
 
               ;; give it some time to setup the clj REPL
-              (cider-itu-poll-until (cider-repls 'clj nil) 90)
+              (cider-itu-poll-until (cider-repls 'clj nil) 5)
 
               ;; send command to the REPL, and push stdout/stderr to
               ;; corresponding eval-xxx variables.
@@ -216,7 +159,7 @@
                 ;; send command to the REPL
                 (cider-interactive-eval
                  ;; ask REPL to return a string that uniquely identifies it.
-                 "(print :clojure? (some? (clojure-version)))"
+                 "(print :bb? (some? (System/getProperty 
\"babashka.version\")))"
                  (lambda (return)
                    (nrepl-dbind-response
                        return
@@ -225,19 +168,87 @@
                      (when out (push out eval-out)))) )
 
                 ;; wait for a response to come back.
-                (cider-itu-poll-until (or eval-err eval-out) 10)
+                (cider-itu-poll-until (or eval-err eval-out) 5)
 
                 ;; ensure there are no errors and response is as expected.
                 (expect eval-err :to-equal '())
-                (expect eval-out :to-equal '(":clojure? true"))
+                (expect eval-out :to-equal '(":bb? true"))
 
                 ;; exit the REPL.
                 (cider-quit repl-buffer)
 
                 ;; wait for the REPL to exit
-                (cider-itu-poll-until (not (eq (process-status nrepl-proc) 
'run)) 15)
+                (cider-itu-poll-until (not (eq (process-status nrepl-proc) 
'run)) 5)
                 (expect (member (process-status nrepl-proc) '(exit 
signal))))))))))
 
+  (it "to clojure tools cli"
+    (jack-in-clojure-cli-test nil))
+
+  (when (eq system-type 'windows-nt)
+    (it "to clojure tools cli (alternative deps.exe)"
+      (jack-in-clojure-cli-test "deps.exe")))
+
+  (it "to leiningen"
+    (with-cider-test-sandbox
+     (with-temp-dir temp-dir
+                    ;; Create a project in temp dir
+                    (let* ((project-dir temp-dir)
+                           (project-clj (expand-file-name "project.clj" 
project-dir)))
+                      (write-region "(defproject cider/integration \"test\"
+                           :dependencies [[org.clojure/clojure \"1.10.3\"]])"
+                                    nil project-clj)
+
+                      (with-temp-buffer
+                        ;; set default directory to temp project
+                        (setq-local default-directory project-dir)
+
+                        (let* (;; Get a gv reference so as to poll if the 
client has
+                               ;; connected to the nREPL server.
+                               (client-is-connected* 
(cider-itu-nrepl-client-connected-ref-make!))
+
+                               ;; jack in and get repl buffer
+                               (nrepl-proc (cider-jack-in-clj `()))
+                               (nrepl-buf (process-buffer nrepl-proc)))
+
+                          ;; wait until the client has successfully connected 
to the
+                          ;; nREPL server.
+                          (cider-itu-poll-until (eq (gv-deref 
client-is-connected*) 'connected) 90)
+
+                          ;; give it some time to setup the clj REPL
+                          (cider-itu-poll-until (cider-repls 'clj nil) 90)
+
+                          ;; send command to the REPL, and push stdout/stderr 
to
+                          ;; corresponding eval-xxx variables.
+                          (let ((repl-buffer (cider-current-repl))
+                                (eval-err '())
+                                (eval-out '()))
+                            (expect repl-buffer :not :to-be nil)
+
+                            ;; send command to the REPL
+                            (cider-interactive-eval
+                             ;; ask REPL to return a string that uniquely 
identifies it.
+                             "(print :clojure? (some? (clojure-version)))"
+                             (lambda (return)
+                               (nrepl-dbind-response
+                                   return
+                                   (out err)
+                                 (when err (push err eval-err))
+                                 (when out (push out eval-out)))) )
+
+                            ;; wait for a response to come back.
+                            (cider-itu-poll-until (or eval-err eval-out) 10)
+
+                            ;; ensure there are no errors and response is as 
expected.
+                            (expect eval-err :to-equal '())
+                            (expect eval-out :to-equal '(":clojure? true"))
+
+                            ;; exit the REPL.
+                            (cider-quit repl-buffer)
+
+                            ;; wait for the REPL to exit
+                            (cider-itu-poll-until (not (eq (process-status 
nrepl-proc) 'run)) 15)
+                            (expect (member (process-status nrepl-proc) '(exit 
signal))))))))))
+
   (it "to nbb"
     (with-cider-test-sandbox
       (with-temp-dir temp-dir



reply via email to

[Prev in Thread] Current Thread [Next in Thread]