Skip to content

Commit 017e708

Browse files
committed
Merge pull request #756 from vitoshka/ssh-tunnel
Rename on-connection-* into tunnel-* and simplify related code.
2 parents 08f48fb + 67615c9 commit 017e708

File tree

1 file changed

+47
-71
lines changed

1 file changed

+47
-71
lines changed

nrepl-client.el

Lines changed: 47 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -122,33 +122,20 @@ Setting this to nil disables the timeout functionality."
122122
:type 'integer
123123
:group 'nrepl)
124124

125-
(defcustom nrepl-connection-endpoint
126-
'nrepl-connection-ssh-tunnel
127-
"A function that is called to determine command that will be run
128-
once an nrepl server process is running. Used to set up an ssh tunnel
129-
on remote connections.
130-
131-
The arguments are dir and port. The return value
132-
should be an `plist` of the form
133-
(:proc-buffer-name \"*buf*\" :hostname \"hostname\" :port 1234)"
134-
:type 'function
135-
:group 'nrepl)
136-
137125
(defcustom nrepl-hide-special-buffers nil
138126
"Control the display of some special buffers in buffer switching commands.
139127
When true some special buffers like the connection and the server
140128
buffer will be hidden."
141129
:type 'boolean
142130
:group 'nrepl)
143131

144-
145132

146133
;;; nREPL Buffer Names
147134

148135
(defconst nrepl-repl-buffer-name-template "*cider-repl%s*")
149136
(defconst nrepl-connection-buffer-name-template "*nrepl-connection%s*")
150137
(defconst nrepl-server-buffer-name-template "*nrepl-server%s*")
151-
(defconst nrepl-on-connection-buffer-name-template "*nrepl-on-connection%s*")
138+
(defconst nrepl-tunnel-buffer-name-template "*nrepl-tunnel%s*")
152139

153140
(defun nrepl-format-buffer-name-template (buffer-name-template designation)
154141
"Apply the DESIGNATION to the corresponding BUFFER-NAME-TEMPLATE."
@@ -160,8 +147,8 @@ buffer will be hidden."
160147
(defun nrepl-make-buffer-name (buffer-name-template &optional project-dir host port)
161148
"Generate a buffer name using BUFFER-NAME-TEMPLATE.
162149
163-
If not supplied PROJECT-DIR, PORT and HOST default to the buffer local value of the
164-
`nrepl-project-dir' and `nrepl-endpoint'.
150+
If not supplied PROJECT-DIR, PORT and HOST default to the buffer local
151+
value of the `nrepl-project-dir' and `nrepl-endpoint'.
165152
166153
The name will include the project name if available or the endpoint host if
167154
it is not. The name will also include the connection port if
@@ -193,11 +180,11 @@ PROJECT-DIR, HOST and PORT are as in `nrepl-make-buffer-name'."
193180
(nrepl-make-buffer-name nrepl-server-buffer-name-template
194181
project-dir host port)))
195182

196-
(defun nrepl-on-connection-buffer-name (&optional project-dir host port)
197-
"Return the name of the on-connection buffer.
183+
(defun nrepl-tunnel-buffer-name (&optional project-dir host port)
184+
"Return the name of the tunnel buffer.
198185
PROJECT-DIR, HOST and PORT are as in `nrepl-make-buffer-name'."
199186
(nrepl--make-hidden-name
200-
(nrepl-make-buffer-name nrepl-on-connection-buffer-name-template
187+
(nrepl-make-buffer-name nrepl-tunnel-buffer-name-template
201188
project-dir host port)))
202189

203190

@@ -209,7 +196,7 @@ PROJECT-DIR, HOST and PORT are as in `nrepl-make-buffer-name'."
209196
(defvar-local nrepl-repl-buffer nil)
210197
(defvar-local nrepl-endpoint nil)
211198
(defvar-local nrepl-project-dir nil)
212-
(defvar-local nrepl-on-connection-buffer nil)
199+
(defvar-local nrepl-tunnel-buffer nil)
213200

214201
(defvar-local nrepl-session nil
215202
"Current nREPL session id.")
@@ -501,19 +488,18 @@ nil, pick them from the value returned by `nrepl-connection-endpoint'. If
501488
REPLP is non-nil create a client connection which is associated with a repl
502489
buffer. When non-nil, SERVER-PROC must be a running nrepl server process
503490
within Emacs. Return the newly created client connection process."
504-
(let* ((endpoint (if (functionp nrepl-connection-endpoint)
505-
(funcall nrepl-connection-endpoint directory port)
506-
(nrepl--default-endpoint directory port)))
491+
(let* ((endpoint (unless (and host port)
492+
(nrepl-connection-endpoint directory port)))
507493
(directory (or directory default-directory))
508494
(host (or host (plist-get endpoint :hostname)))
509495
(port (or port (plist-get endpoint :port)))
510-
(proc-buffer-name (plist-get endpoint :proc-buffer-name))
511496
(server-buf (and server-proc
512497
(buffer-name (process-buffer server-proc))))
513498
(client-buf (if replp
514499
(cider-repl-create directory host port)
515500
(nrepl-create-connection-buffer directory host port)))
516501
(client-proc (open-network-stream "nrepl" client-buf host port))
502+
(tunnel-proc (plist-get endpoint :proc))
517503
(nrepl-connection-dispatch client-buf))
518504

519505
(set-process-filter client-proc 'nrepl-client-filter)
@@ -532,10 +518,10 @@ within Emacs. Return the newly created client connection process."
532518
;; fixme: repl and connection buffers are the same thing
533519
nrepl-connection-buffer client-buf
534520
nrepl-repl-buffer (when replp client-buf)
535-
nrepl-on-connection-buffer proc-buffer-name
521+
nrepl-tunnel-buffer (and tunnel-proc (process-buffer tunnel-proc))
536522
nrepl-pending-requests (make-hash-table :test 'equal)
537523
nrepl-completed-requests (make-hash-table :test 'equal)))
538-
524+
539525
(nrepl-make-connection-default client-buf)
540526

541527
;; Everything is set. We are ready to send requests.
@@ -844,52 +830,43 @@ Return a newly created process."
844830
(error "Leiningen 2.x is required by CIDER"))
845831
(t (error "Could not start nREPL server: %s" problem)))))
846832

847-
(defun nrepl-connection-ssh-tunnel (dir port)
848-
"Return an endpoint for SSH tunnel to project DIR stack, and PORT port.
849-
If DIR is remote, then attempt to open an SSH tunnel to port. If
850-
the ssh executable is not found on the stack, then fall back to
851-
specifying a direct conneciton."
852-
;; this abuses the -v option for ssh to get output when the port
853-
;; forwarding is set up, which is used to synchronise on, so that
854-
;; the port forwarding is up when we try to connect.
833+
(defun nrepl-connection-endpoint (dir port)
834+
"Return a connection endpoint.
835+
The returned endpoint is a `plist` of the form:
836+
837+
(:proc PROCESS :hostname \"hostname\" :port 1234)
838+
839+
If DIR is local :proc is nil, :hostname is \"localhost\" and :port is PORT.
840+
841+
If DIR is remote and `ssh' executable has been found, attempt to start an
842+
SSH tunnel and return it as :proc. If no `ssh' executable has been found,
843+
fall back to specifying a direct connection to the remote host."
855844
(if (file-remote-p dir)
856845
(let ((ssh (executable-find "ssh")))
857846
(if ssh
858847
;; run cmd in a local shell
859848
(let* ((cmd (nrepl--ssh-tunnel-command ssh dir port))
860-
(on-connection-buffer-name (nrepl-on-connection-buffer-name))
861849
(proc (start-process-shell-command
862-
"nrepl-on-connection"
863-
on-connection-buffer-name
864-
cmd))
865-
(on-connection-buffer (get-buffer
866-
on-connection-buffer-name)))
867-
(with-current-buffer on-connection-buffer-name
868-
(setq-local nrepl-wait-for-port t))
850+
"nrepl-tunnel"
851+
(nrepl-tunnel-buffer-name)
852+
cmd)))
853+
(process-put proc :waiting-for-port t)
869854
(set-process-filter proc (nrepl--ssh-tunnel-filter port))
870-
(while (and (buffer-local-value 'nrepl-wait-for-port
871-
on-connection-buffer)
872-
(process-live-p proc))
855+
(while (and (process-live-p proc)
856+
(process-get proc :waiting-for-port))
873857
(accept-process-output nil 0.005))
874858
(unless (process-live-p proc)
875859
(message "SSH port forwarding failed"))
876-
(list :hostname "localhost" :port port
877-
:proc-buffer-name on-connection-buffer-name))
878-
(nrepl--default-endpoint dir port)))
879-
(list :hostname "localhost" :port port :proc-buffer-name nil)))
880-
881-
(defun nrepl--default-endpoint (dir port)
882-
"The endpoint for a repl in project DIR on PORT.
883-
Return a plist with :hostname, :port and :proc keys."
884-
(list :hostname (if (file-remote-p dir)
885-
tramp-current-host
886-
"localhost")
887-
:port port
888-
:proc-buffer-name nil))
860+
(list :hostname "localhost" :port port :proc proc))
861+
(list :hostname tramp-current-host :port port :proc nil)))
862+
(list :hostname "localhost" :port port :proc nil)))
889863

890864
(defun nrepl--ssh-tunnel-command (ssh dir port)
891865
"Command string to open SSH tunnel to the host associated with DIR's PORT."
892866
(with-parsed-tramp-file-name dir nil
867+
;; this abuses the -v option for ssh to get output when the port
868+
;; forwarding is set up, which is used to synchronise on, so that
869+
;; the port forwarding is up when we try to connect.
893870
(format-spec
894871
"%s -v -N -L %p:localhost:%p %u'%h'"
895872
`((?s . ,ssh)
@@ -901,17 +878,16 @@ Return a plist with :hostname, :port and :proc keys."
901878
"Return a filter function for waiting on PORT to appear in output."
902879
(let ((port-string (format "LOCALHOST:%s" port)))
903880
(lambda (proc string)
881+
(when (string-match port-string string)
882+
(process-put proc :waiting-for-port nil))
904883
(when (buffer-live-p (process-buffer proc))
905884
(with-current-buffer (process-buffer proc)
906885
(let ((moving (= (point) (process-mark proc))))
907886
(save-excursion
908887
(goto-char (process-mark proc))
909888
(insert string)
910889
(set-marker (process-mark proc) (point)))
911-
(if moving (goto-char (process-mark proc))))))
912-
(when (string-match port-string string)
913-
(with-current-buffer (process-buffer proc)
914-
(setq nrepl-wait-for-port nil))))))
890+
(if moving (goto-char (process-mark proc)))))))))
915891

916892

917893
;;; Utilities
@@ -1091,19 +1067,19 @@ Moves CONNECITON-BUFFER to the front of `nrepl-connection-list'."
10911067
(nrepl--connections-refresh))
10921068
(message "Not in an nREPL REPL buffer.")))
10931069

1094-
(defun nrepl--close-connection-buffer (connection-buffer)
1095-
"Closes CONNECTION-BUFFER, removing it from `nrepl-connection-list'.
1070+
(defun nrepl--close-connection-buffer (conn-buffer)
1071+
"Closes CONN-BUFFER, removing it from `nrepl-connection-list'.
10961072
Also closes associated REPL and server buffers."
1097-
(let ((nrepl-connection-dispatch connection-buffer))
1098-
(let ((buffer (get-buffer connection-buffer)))
1073+
(let ((nrepl-connection-dispatch conn-buffer))
1074+
(let ((buffer (get-buffer conn-buffer)))
10991075
(setq nrepl-connection-list
11001076
(delq (buffer-name buffer) nrepl-connection-list))
11011077
(when (buffer-live-p buffer)
1102-
(dolist (buf-name `(,(buffer-local-value 'nrepl-server-buffer buffer)
1103-
,(buffer-local-value 'nrepl-on-connection-buffer buffer)
1104-
,buffer))
1105-
(when buf-name
1106-
(cider--close-buffer buf-name)))))))
1078+
(dolist (buf `(,(buffer-local-value 'nrepl-server-buffer buffer)
1079+
,(buffer-local-value 'nrepl-tunnel-buffer buffer)
1080+
,buffer))
1081+
(when buf
1082+
(cider--close-buffer buf)))))))
11071083

11081084

11091085
;;; Connection Browser

0 commit comments

Comments
 (0)