branch: elpa/cider
commit c621bace94e29127320ca6bc5a8819e1e8e71a7c
Author: Bozhidar Batsov <[email protected]>
Commit: Bozhidar Batsov <[email protected]>

    Resolve unqualified core vars against cljs.core in cljs REPLs
    
    `cider-resolve--var' hardcoded a `clojure.core' fallback for unqualified,
    non-referred vars, so ClojureScript core vars (e.g. their indentation
    metadata) never resolved in a cljs buffer.  Fall back to the connection's
    actual core namespace, mirroring `cider-resolve-core-ns'.
---
 lisp/cider-resolve.el       | 25 ++++++++++++++++++-------
 test/cider-resolve-tests.el | 21 ++++++++++++++++++++-
 2 files changed, 38 insertions(+), 8 deletions(-)

diff --git a/lisp/cider-resolve.el b/lisp/cider-resolve.el
index 1ba1dc16fe..7f70bd62eb 100644
--- a/lisp/cider-resolve.el
+++ b/lisp/cider-resolve.el
@@ -90,10 +90,21 @@ If it doesn't point anywhere, returns ALIAS."
 
 (defconst cider-resolve--prefix-regexp "\\`\\(?:#'\\)?\\([^/]+\\)/")
 
-(defun cider-resolve--var (cache ns var)
+(defun cider-resolve--core-ns-name ()
+  "Return the core namespace name for the current connection.
+Either \"cljs.core\" or \"clojure.core\", depending on the value of
+`cider-repl-type' in the connected REPL."
+  (if-let* ((repl (cider-current-repl)))
+      (with-current-buffer repl
+        (if (eq cider-repl-type 'cljs) "cljs.core" "clojure.core"))
+    "clojure.core"))
+
+(defun cider-resolve--var (cache ns var core-ns)
   "Resolve VAR in namespace NS against the namespace CACHE dict.
-Helper for `cider-resolve-var'; recurses on CACHE instead of re-resolving
-the connection on every lookup.  See `cider-resolve-var' for the contract."
+CORE-NS is the core namespace (\"clojure.core\" or \"cljs.core\") that an
+unqualified, non-referred VAR falls back to.  Helper for `cider-resolve-var';
+recurses on CACHE instead of re-resolving the connection on every lookup.
+See `cider-resolve-var' for the contract."
   (let* ((var-ns (when (string-match cider-resolve--prefix-regexp var)
                    (let ((alias (match-string 1 var)))
                      (or (nrepl-dict-get-in cache (list ns "aliases" alias))
@@ -104,17 +115,17 @@ the connection on every lookup.  See `cider-resolve-var' 
for the contract."
      (unless var-ns
        ;; If the var had no prefix, it might be referred.
        (if-let* ((referral (nrepl-dict-get-in cache (list ns "refers" name))))
-           (cider-resolve--var cache ns referral)
+           (cider-resolve--var cache ns referral core-ns)
          ;; Or it might be from core.
-         (unless (equal ns "clojure.core")
-           (cider-resolve--var cache "clojure.core" name)))))))
+         (unless (equal ns core-ns)
+           (cider-resolve--var cache core-ns name core-ns)))))))
 
 (defun cider-resolve-var (ns var)
   "Return a dict of the metadata of a clojure var VAR in namespace NS.
 VAR is a string.
 Return nil only if VAR cannot be resolved."
   (when-let* ((cache (cider-resolve--ns-cache)))
-    (cider-resolve--var cache ns var)))
+    (cider-resolve--var cache ns var (cider-resolve--core-ns-name))))
 
 (defun cider-resolve-core-ns ()
   "Return a dict of the core namespace for current connection.
diff --git a/test/cider-resolve-tests.el b/test/cider-resolve-tests.el
index 0959a36ae0..9111315e21 100644
--- a/test/cider-resolve-tests.el
+++ b/test/cider-resolve-tests.el
@@ -58,6 +58,12 @@
           "interns"
           (dict "map" (dict "arglists" "([f] [f coll])")
                 "filter" (dict "arglists" "([pred] [pred coll])"))
+          "refers" (dict))
+    "cljs.core"
+    (dict "aliases" (dict)
+          "interns"
+          (dict "map" (dict "arglists" "([f] [f coll])")
+                "js-obj" (dict "arglists" "([& keyvals])"))
           "refers" (dict))))
 
 (defmacro with-mock-ns-cache (&rest body)
@@ -142,7 +148,20 @@
   (it "returns nil for completely unknown vars"
     (with-mock-ns-cache
       (expect (cider-resolve-var "myapp.core" "totally-unknown")
-              :to-be nil))))
+              :to-be nil)))
+
+  (it "falls back to cljs.core in a ClojureScript REPL"
+    (with-mock-ns-cache
+      (with-current-buffer repl-buf (setq-local cider-repl-type 'cljs))
+      ;; A cljs.core-only var resolves in a cljs REPL...
+      (let ((meta (cider-resolve-var "myapp.core" "js-obj")))
+        (expect meta :to-be-truthy)
+        (expect (nrepl-dict-get meta "arglists") :to-equal "([& keyvals])"))))
+
+  (it "does not resolve cljs.core vars in a Clojure REPL"
+    (with-mock-ns-cache
+      ;; ...but not in a clj REPL, where the fallback is clojure.core.
+      (expect (cider-resolve-var "myapp.core" "js-obj") :to-be nil))))
 
 (describe "cider-resolve-core-ns"
   (it "returns clojure.core for Clojure REPLs"

Reply via email to