* bug#60428: 29.0.60; ERC 5.4.1: Fix default-port regression in erc-select-read-args
[not found] <87mt750ygt.fsf@neverwas.me>
@ 2023-01-02 1:41 ` J.P.
[not found] ` <87h6x9yapz.fsf@neverwas.me>
` (5 subsequent siblings)
6 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-01-02 1:41 UTC (permalink / raw)
To: 60428; +Cc: emacs-erc
[-- Attachment #1: Type: text/plain, Size: 976 bytes --]
v2. Respect `erc-prompt-for-password'. Remove `run-at-time' hack from
regression fix.
"J.P." <jp@neverwas.me> writes:
> The proposed patch abandons most of the envisioned niceties and
> instead employs a hack to just force a non-local exit and schedule a
> call to `erc-tls' when appropriate. It also instructs users to do that
> themselves in the future (issue an M-x erc-tls, that is). Hopefully,
> this makes for an acceptable compromise.
I've forsaken the first part out of an abundance of caution. So this now
just prints a warning and proceeds with a non-TLS connection. If anyone
finds that unsatisfactory, please say something.
> BTW, a POC patch set far more faithful to the original breadth of the
> feature (and way less hacky) is also attached. Perhaps it'll inform
> further exploration in this area down the road (but not for Emacs 29).
IOW, the de facto goal here is to make interactive `erc' a "universal"
entry point for both plain and TLS connections.
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0000-v1-v2.diff --]
[-- Type: text/x-patch, Size: 12273 bytes --]
From 448686bf96105833cd3e3ee319118c1672d95ca0 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Sun, 1 Jan 2023 17:36:36 -0800
Subject: [PATCH 0/4] *** NOT A PATCH ***
*** BLURB HERE ***
F. Jason Park (4):
Fix default-port regression in erc-select-read-args
[5.6] Be smarter about switching to TLS from M-x erc
[5.6] Add display option for interactive ERC invocations
[5.6] Optionally prompt for more ERC entry-point params
doc/misc/erc.texi | 2 +-
lisp/erc/erc.el | 87 +++++++++++++++++++++++++++++---------
test/lisp/erc/erc-tests.el | 66 +++++++++++++++++++++--------
3 files changed, 118 insertions(+), 37 deletions(-)
Interdiff:
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 2fcdb513b5d..7f2dd89342b 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -1486,7 +1486,8 @@ erc-interactive-display
possible values."
:package-version '(ERC . "5.4.1") ; FIXME increment upon publishing to ELPA
:group 'erc-buffers
- :type '(choice (const :tag "Split window and select" window)
+ :type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
+ (const :tag "Split window and select" window)
(const :tag "Split window, don't select" window-noselect)
(const :tag "New frame" frame)
(const :tag "Bury new and don't display existing" bury)
@@ -2180,7 +2181,7 @@ erc-select-read-args
With prefix arg, also prompt for user and full name."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
- (read-string (format "Server (default is %S): " d)
+ (read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
;; For legacy reasons, also accept a URL without a scheme.
(url (url-generic-parse-url (erc--ensure-url input)))
@@ -2199,34 +2200,33 @@ erc-select-read-args
(read-string (format "Nickname (default is %S): " d)
nil 'erc-nick-history-list d))))
(user (and current-prefix-arg
- (let ((d (or (url-user url) (erc-compute-user))))
+ (let ((d (erc-compute-user (url-user url))))
(read-string (format "User (default is %S): " d)
nil nil d))))
(full (and current-prefix-arg
- (let ((d (or (url-user url) (erc-compute-full-name))))
+ (let ((d (erc-compute-full-name (url-user url))))
(read-string (format "Full name (default is %S): " d)
nil nil d))))
- (passwd (or (url-password url)
- (let*
- ((p (with-suppressed-warnings
- ((obsolete erc-password))
- erc-password))
- (m (if p
- (format "Server password (default is %S): " p)
- "Server password (optional): ")))
- (if erc-prompt-for-password (read-passwd m nil p) p))))
- (opener erc-server-connect-function))
+ (passwd (let* ((p (with-suppressed-warnings ((obsolete erc-password))
+ (or (url-password url) erc-password)))
+ (m (if p
+ (format "Server password (default is %S): " p)
+ "Server password (optional): ")))
+ (if erc-prompt-for-password (read-passwd m nil p) p)))
+ (opener (and (or sp (eql port erc-default-port-tls)
+ (and (equal server erc-default-server)
+ (not (string-prefix-p "irc://" input))
+ (eql port erc-default-port)
+ (y-or-n-p "Connect using TLS instead? ")
+ (setq port erc-default-port-tls)))
+ #'erc-open-tls-stream)))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- (when (and (equal server erc-default-server)
- (not (string-prefix-p "irc://" input))
- (or (not (eql port erc-default-port))
- (and (y-or-n-p "Connect using TLS instead? ")
- (setq port erc-default-port-tls))))
- (setq opener #'erc-open-tls-stream))
`( :server ,server :port ,port :nick ,nick ,@(and user `(:user ,user))
,@(and passwd `(:password ,passwd)) ,@(and full `(:full-name ,full))
- buffer-display ,erc-interactive-display connect-function ,opener)))
+ ,@(and erc-interactive-display
+ `(buffer-display ,erc-interactive-display))
+ ,@(and opener `(connect-function ,opener)))))
;;;###autoload
@@ -2238,8 +2238,7 @@ erc
(full-name (erc-compute-full-name))
id
;; For interactive use
- ((buffer-display erc-buffer-display)
- erc-buffer-display)
+ ((buffer-display erc-join-buffer) erc-join-buffer)
((connect-function erc-server-connect-function)
erc-server-connect-function))
"ERC is a powerful, modular, and extensible IRC client.
@@ -2284,10 +2283,12 @@ erc-tls
client-certificate
id
;; For interactive use
- ((buffer-display erc-buffer-display)
- erc-buffer-display)
+ ((buffer-display erc-join-buffer) erc-join-buffer)
((connect-function erc-server-connect-function)
- #'erc-open-tls-stream))
+ (if (eq erc-server-connect-function
+ #'erc-open-network-stream)
+ #'erc-open-tls-stream
+ erc-server-connect-function)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC over TLS.
@@ -2334,12 +2335,7 @@ erc-tls
interactively.
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
- (interactive (let ((erc-server-connect-function
- (if (eq erc-server-connect-function
- #'erc-open-network-stream)
- #'erc-open-tls-stream
- erc-server-connect-function))
- (erc-port (or erc-port erc-default-port-tls)))
+ (interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
(progn
(erc-open server port nick full-name t password
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 9d09df44883..d05b0efe2ed 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1001,7 +1001,7 @@ erc--server-connect-dumb-ipv6-regexp
(ert-deftest erc-select-read-args ()
- (ert-info ("Doesn't default to TLS")
+ (ert-info ("Prompts for switch to TLS by default")
(should (equal (ert-simulate-keys "\r\r\r\ry\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
@@ -1010,44 +1010,58 @@ erc-select-read-args
'buffer-display 'buffer
'connect-function #'erc-open-tls-stream))))
+ (ert-info ("Switches to TLS when port matches default TLS port")
+ (should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ 'buffer-display 'buffer
+ 'connect-function #'erc-open-tls-stream))))
+
+ (ert-info ("Switches to TLS when URL is ircs://")
+ (should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ 'buffer-display 'buffer
+ 'connect-function #'erc-open-tls-stream))))
+
+ (setq-local erc-interactive-display nil) ; cheat to save space
+
(ert-info ("Opt out of non-TLS warning manually")
(should (equal (ert-simulate-keys "\r\r\r\rn\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
:port 6667
- :nick (user-login-name)
- 'buffer-display 'buffer
- 'connect-function #'erc-open-network-stream))))
+ :nick (user-login-name)))))
- (ert-info ("Override non-TLS warning via URL scheme")
+ (ert-info ("Override default TLS")
(should (equal (ert-simulate-keys "irc://irc.libera.chat\r\r\r\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
:port 6667
- :nick (user-login-name)
- 'buffer-display 'buffer
- 'connect-function #'erc-open-network-stream))))
+ :nick (user-login-name)))))
(ert-info ("Address includes port")
(should (equal (ert-simulate-keys "localhost:6667\rnick\r\r"
(erc-select-read-args))
(list :server "localhost"
:port 6667
- :nick "nick"
- 'buffer-display 'buffer
- 'connect-function #'erc-open-network-stream))))
+ :nick "nick"))))
(ert-info ("Address includes nick, password skipped via option")
(should (equal (ert-simulate-keys "nick@localhost:6667\r"
(let (erc-prompt-for-password)
- (butlast (erc-select-read-args) 4)))
+ (erc-select-read-args)))
(list :server "localhost"
:port 6667
:nick "nick"))))
(ert-info ("Address includes nick and password")
- (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r"
- (butlast (erc-select-read-args) 4))
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
+ (erc-select-read-args))
(list :server "localhost"
:port 6667
:nick "nick"
@@ -1055,29 +1069,29 @@ erc-select-read-args
(ert-info ("IPv6 address plain")
(should (equal (ert-simulate-keys "::1\r\r\r\r"
- (butlast (erc-select-read-args) 4))
+ (erc-select-read-args))
(list :server "[::1]"
:port 6667
:nick (user-login-name)))))
(ert-info ("IPv6 address with port")
(should (equal (ert-simulate-keys "[::1]:6667\r\r\r"
- (butlast (erc-select-read-args) 4))
+ (erc-select-read-args))
(list :server "[::1]"
:port 6667
:nick (user-login-name)))))
(ert-info ("IPv6 address includes nick")
(should (equal (ert-simulate-keys "nick@[::1]:6667\r\r"
- (butlast (erc-select-read-args) 4))
+ (erc-select-read-args))
(list :server "[::1]"
:port 6667
:nick "nick"))))
(ert-info ("Extra args use URL nick by default")
- (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r\r"
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r\r\r"
(let ((current-prefix-arg '(4)))
- (butlast (erc-select-read-args) 4)))
+ (erc-select-read-args)))
(list :server "localhost"
:port 6667
:nick "nick"
--
2.38.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #3: 0001-Fix-default-port-regression-in-erc-select-read-args.patch --]
[-- Type: text/x-patch, Size: 5458 bytes --]
From 574671c8bdc1cb5a56b0c4ffe0f35be9fa0161f7 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 1/4] Fix default-port regression in erc-select-read-args
* lisp/erc/erc.el (erc--warn-unencrypted): New function, likely
temporary, to warn new users connecting interactively to the default
server, "irc.libara.chat", via the default non-TLS port, 6667.
(erc-select-read-args): Remove stray code from incomplete feature
introduced by bug#56514. Ensure connecting always works with default
port, which is non-TLS. Respect `erc-prompt-for-password' when user
pastes URL containing password component into "server" prompt. Maybe
add `erc--warn-unencrypted' as one-off hook for impending connection.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Always expect
password prompt and sometimes a non-TLS port when `erc' called
interactively. (Bug#60428.)
---
lisp/erc/erc.el | 38 +++++++++++++++++++++++++++++---------
test/lisp/erc/erc-tests.el | 6 +++---
2 files changed, 32 insertions(+), 12 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index fe1201dd3a8..6315d5aa482 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2161,6 +2161,23 @@ erc--ensure-url
(setq input (concat "irc://" input)))
input)
+;; A temporary means of addressing the problem of ERC's namesake entry
+;; point defaulting to a non-TLS connection with its default server
+;; (bug#60428).
+(defun erc--warn-unencrypted ()
+ ;; Remove unconditionally to avoid wrong context due to races from
+ ;; simultaneous dialing or aborting (e.g., via `keybaord-quit').
+ (remove-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted)
+ (when (and (process-contact erc-server-process :nowait)
+ (equal erc-session-server erc-default-server)
+ (eql erc-session-port erc-default-port))
+ ;; FIXME use the autoloaded `info' instead of `Info-goto-node' in
+ ;; `erc-button-alist'.
+ (require 'info nil t)
+ (erc-display-error-notice
+ nil (concat "This connection is unencrypted. Please use `erc-tls'"
+ " from now on. See Info:\"(erc) connecting\" for more."))))
+
;;;###autoload
(defun erc-select-read-args ()
"Prompt the user for values of nick, server, port, and password."
@@ -2171,10 +2188,7 @@ erc-select-read-args
;; For legacy reasons, also accept a URL without a scheme.
(url (url-generic-parse-url (erc--ensure-url input)))
(server (url-host url))
- (sp (and (or (string-suffix-p "s" (url-type url))
- (and (equal server erc-default-server)
- (not (string-prefix-p "irc://" input))))
- 'ircs-u))
+ (sp (and (string-suffix-p "s" (url-type url)) erc-default-port-tls))
(port (or (url-portspec url)
(erc-compute-port
(let ((d (erc-compute-port sp))) ; may be a string
@@ -2187,13 +2201,19 @@ erc-select-read-args
(let ((d (erc-compute-nick)))
(read-string (format "Nickname (default is %S): " d)
nil 'erc-nick-history-list d))))
- (passwd (or (url-password url)
- (if erc-prompt-for-password
- (read-passwd "Server password (optional): ")
- (with-suppressed-warnings ((obsolete erc-password))
- erc-password)))))
+ (passwd (let* ((p (with-suppressed-warnings ((obsolete erc-password))
+ (or (url-password url) erc-password)))
+ (m (if p
+ (format "Server password (default is %S): " p)
+ "Server password (optional): ")))
+ (if erc-prompt-for-password (read-passwd m nil p) p))))
(when (and passwd (string= "" passwd))
(setq passwd nil))
+ (when (and (equal server erc-default-server)
+ (eql port erc-default-port)
+ (not (eql port erc-default-port-tls)) ; not `erc-tls'
+ (not (string-prefix-p "irc://" input))) ; not yanked URL
+ (add-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted))
(list :server server :port port :nick nick :password passwd)))
;;;###autoload
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 6807b24bfc6..85506c3d27e 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1001,11 +1001,11 @@ erc--server-connect-dumb-ipv6-regexp
(ert-deftest erc-select-read-args ()
- (ert-info ("Defaults to TLS")
+ (ert-info ("Does not default to TLS")
(should (equal (ert-simulate-keys "\r\r\r\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
- :port 6697
+ :port 6667
:nick (user-login-name)
:password nil))))
@@ -1036,7 +1036,7 @@ erc-select-read-args
:password nil))))
(ert-info ("Address includes nick and password")
- (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r"
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
(erc-select-read-args))
(list :server "localhost"
:port 6667
--
2.38.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #4: 0002-5.6-Be-smarter-about-switching-to-TLS-from-M-x-erc.patch --]
[-- Type: text/x-patch, Size: 10968 bytes --]
From 7a8659ed2132858e5c52cf09c9050cc00463607f Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 2/4] [5.6] Be smarter about switching to TLS from M-x erc
* lisp/erc/erc.el (erc--warn-unencrypted): Remove newly unused
internal function.
(erc-select-read-args): Offer to use TLS when user runs M-x erc and
opts for default server and port or provides the well-known IANA TLS
port or enters an ircs:// URL at the server prompt. For the last two,
do this immediately instead of calling `erc-tls' interactively and
imposing a review of just-chosen values. Also remove error warnings
and ensure `erc-tls' still works by setting
`erc-server-connect-function' to `erc-open-tls-stream' when
appropriate. Include the word "URL" in server prompt.
(erc, erc-tls): Add internal keyword arguments for interactive use,
but don't make them colon-prefixed, i.e., `keywordp'.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Modify return
values to expect additional `connect-function' keyword argument.
(Bug#60428.)
---
lisp/erc/erc.el | 61 +++++++++++++++++++-------------------
test/lisp/erc/erc-tests.el | 52 +++++++++++++++++++++-----------
2 files changed, 65 insertions(+), 48 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 6315d5aa482..96866432ebd 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2161,29 +2161,12 @@ erc--ensure-url
(setq input (concat "irc://" input)))
input)
-;; A temporary means of addressing the problem of ERC's namesake entry
-;; point defaulting to a non-TLS connection with its default server
-;; (bug#60428).
-(defun erc--warn-unencrypted ()
- ;; Remove unconditionally to avoid wrong context due to races from
- ;; simultaneous dialing or aborting (e.g., via `keybaord-quit').
- (remove-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted)
- (when (and (process-contact erc-server-process :nowait)
- (equal erc-session-server erc-default-server)
- (eql erc-session-port erc-default-port))
- ;; FIXME use the autoloaded `info' instead of `Info-goto-node' in
- ;; `erc-button-alist'.
- (require 'info nil t)
- (erc-display-error-notice
- nil (concat "This connection is unencrypted. Please use `erc-tls'"
- " from now on. See Info:\"(erc) connecting\" for more."))))
-
;;;###autoload
(defun erc-select-read-args ()
"Prompt the user for values of nick, server, port, and password."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
- (read-string (format "Server (default is %S): " d)
+ (read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
;; For legacy reasons, also accept a URL without a scheme.
(url (url-generic-parse-url (erc--ensure-url input)))
@@ -2206,15 +2189,20 @@ erc-select-read-args
(m (if p
(format "Server password (default is %S): " p)
"Server password (optional): ")))
- (if erc-prompt-for-password (read-passwd m nil p) p))))
+ (if erc-prompt-for-password (read-passwd m nil p) p)))
+ (opener (and (or sp (eql port erc-default-port-tls)
+ (and (equal server erc-default-server)
+ (not (string-prefix-p "irc://" input))
+ (eql port erc-default-port)
+ (y-or-n-p "Connect using TLS instead? ")
+ (setq port erc-default-port-tls)))
+ #'erc-open-tls-stream)))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- (when (and (equal server erc-default-server)
- (eql port erc-default-port)
- (not (eql port erc-default-port-tls)) ; not `erc-tls'
- (not (string-prefix-p "irc://" input))) ; not yanked URL
- (add-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted))
- (list :server server :port port :nick nick :password passwd)))
+ `( :server ,server :port ,port :nick ,nick
+ ,@(and passwd `(:password ,passwd))
+ ,@(and opener `(connect-function ,opener)))))
+
;;;###autoload
(cl-defun erc (&key (server (erc-compute-server))
@@ -2223,7 +2211,10 @@ erc
(user (erc-compute-user))
password
(full-name (erc-compute-full-name))
- id)
+ id
+ ;; For interactive use
+ ((connect-function erc-server-connect-function)
+ erc-server-connect-function))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC.
@@ -2246,7 +2237,9 @@ erc
whereas `erc-compute-port' and `erc-compute-nick' will be invoked
for the values of the other parameters.
-See `erc-tls' for the meaning of ID."
+See `erc-tls' for the meaning of ID.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME ID)"
(interactive (erc-select-read-args))
(erc-open server port nick full-name t password nil nil nil nil user id))
@@ -2262,7 +2255,13 @@ erc-tls
password
(full-name (erc-compute-full-name))
client-certificate
- id)
+ id
+ ;; For interactive use
+ ((connect-function erc-server-connect-function)
+ (if (eq erc-server-connect-function
+ #'erc-open-network-stream)
+ #'erc-open-tls-stream
+ erc-server-connect-function)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC over TLS.
@@ -2306,10 +2305,12 @@ erc-tls
the server buffer and identifying the connection unequivocally.
See info node `(erc) Network Identifier' for details. Like USER
and CLIENT-CERTIFICATE, this parameter cannot be specified
-interactively."
+interactively.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
(interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
- (let ((erc-server-connect-function 'erc-open-tls-stream))
+ (progn
(erc-open server port nick full-name t password
nil nil nil client-certificate user id)))
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 85506c3d27e..10adc9d53a7 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1001,30 +1001,50 @@ erc--server-connect-dumb-ipv6-regexp
(ert-deftest erc-select-read-args ()
- (ert-info ("Does not default to TLS")
- (should (equal (ert-simulate-keys "\r\r\r\r"
+ (ert-info ("Prompts for switch to TLS by default")
+ (should (equal (ert-simulate-keys "\r\r\r\ry\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
- :port 6667
+ :port 6697
:nick (user-login-name)
- :password nil))))
+ 'connect-function #'erc-open-tls-stream))))
+
+ (ert-info ("Switches to TLS when port matches default TLS port")
+ (should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ 'connect-function #'erc-open-tls-stream))))
+
+ (ert-info ("Switches to TLS when URL is ircs://")
+ (should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ 'connect-function #'erc-open-tls-stream))))
+
+ (ert-info ("Opt out of non-TLS warning manually")
+ (should (equal (ert-simulate-keys "\r\r\r\rn\r"
+ (erc-select-read-args))
+ (list :server "irc.libera.chat"
+ :port 6667
+ :nick (user-login-name)))))
(ert-info ("Override default TLS")
(should (equal (ert-simulate-keys "irc://irc.libera.chat\r\r\r\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("Address includes port")
- (should (equal (ert-simulate-keys
- "localhost:6667\rnick\r\r"
+ (should (equal (ert-simulate-keys "localhost:6667\rnick\r\r"
(erc-select-read-args))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick, password skipped via option")
(should (equal (ert-simulate-keys "nick@localhost:6667\r"
@@ -1032,8 +1052,7 @@ erc-select-read-args
(erc-select-read-args)))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick and password")
(should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
@@ -1048,24 +1067,21 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address with port")
(should (equal (ert-simulate-keys "[::1]:6667\r\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address includes nick")
(should (equal (ert-simulate-keys "nick@[::1]:6667\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick"
- :password nil)))))
+ :nick "nick")))))
(ert-deftest erc-tls ()
(let (calls)
--
2.38.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #5: 0003-5.6-Add-display-option-for-interactive-ERC-invocatio.patch --]
[-- Type: text/x-patch, Size: 5138 bytes --]
From 5afc6f4d40af031258bcda8fe440448ce8a1aa01 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 3/4] [5.6] Add display option for interactive ERC invocations
* lisp/erc/erc.el (erc-buffer-display, erc-receive-query-display):
Add aliases for `erc-join-buffer' and `erc-auto-query'.
(erc-interactive-display): Add new option to control display of server
buffers during interactive entry-point invocations.
(erc-select-read-args): Pass `erc-interactive-display' to entry
points.
(erc, erc-tls): Add interactive-only to control initial buffer
display.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Expect
buffer-display values from `erc-interactive-display'. (Bug#60428.)
---
lisp/erc/erc.el | 19 +++++++++++++++++++
test/lisp/erc/erc-tests.el | 5 +++++
2 files changed, 24 insertions(+)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 96866432ebd..09d55f60990 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -1459,6 +1459,7 @@ erc-default-port-tls
"IRC port to use for encrypted connections if it cannot be \
detected otherwise.")
+(defvaralias 'erc-buffer-display 'erc-join-buffer)
(defcustom erc-join-buffer 'bury
"Determines how to display a newly created IRC buffer.
@@ -1479,6 +1480,19 @@ erc-join-buffer
(const :tag "Use current buffer" buffer)
(const :tag "Use current buffer" t)))
+(defcustom erc-interactive-display 'buffer
+ "How and whether to display server buffers for M-x erc.
+See `erc-buffer-display' and friends for a description of
+possible values."
+ :package-version '(ERC . "5.4.1") ; FIXME increment upon publishing to ELPA
+ :group 'erc-buffers
+ :type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
+ (const :tag "Split window and select" window)
+ (const :tag "Split window, don't select" window-noselect)
+ (const :tag "New frame" frame)
+ (const :tag "Bury new and don't display existing" bury)
+ (const :tag "Use current buffer" buffer)))
+
(defcustom erc-reconnect-display nil
"How (and whether) to display a channel buffer upon reconnecting.
@@ -2201,6 +2215,8 @@ erc-select-read-args
(setq passwd nil))
`( :server ,server :port ,port :nick ,nick
,@(and passwd `(:password ,passwd))
+ ,@(and erc-interactive-display
+ `(buffer-display ,erc-interactive-display))
,@(and opener `(connect-function ,opener)))))
@@ -2213,6 +2229,7 @@ erc
(full-name (erc-compute-full-name))
id
;; For interactive use
+ ((buffer-display erc-join-buffer) erc-join-buffer)
((connect-function erc-server-connect-function)
erc-server-connect-function))
"ERC is a powerful, modular, and extensible IRC client.
@@ -2257,6 +2274,7 @@ erc-tls
client-certificate
id
;; For interactive use
+ ((buffer-display erc-join-buffer) erc-join-buffer)
((connect-function erc-server-connect-function)
(if (eq erc-server-connect-function
#'erc-open-network-stream)
@@ -4492,6 +4510,7 @@ erc-query
(with-current-buffer server-buffer
(erc--open-target target)))
+(defvaralias 'erc-receive-query-display 'erc-auto-query)
(defcustom erc-auto-query 'window-noselect
"If non-nil, create a query buffer each time you receive a private message.
If the buffer doesn't already exist, it is created.
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 10adc9d53a7..91cdf2f1770 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1007,6 +1007,7 @@ erc-select-read-args
(list :server "irc.libera.chat"
:port 6697
:nick (user-login-name)
+ 'buffer-display 'buffer
'connect-function #'erc-open-tls-stream))))
(ert-info ("Switches to TLS when port matches default TLS port")
@@ -1015,6 +1016,7 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
+ 'buffer-display 'buffer
'connect-function #'erc-open-tls-stream))))
(ert-info ("Switches to TLS when URL is ircs://")
@@ -1023,8 +1025,11 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
+ 'buffer-display 'buffer
'connect-function #'erc-open-tls-stream))))
+ (setq-local erc-interactive-display nil) ; cheat to save space
+
(ert-info ("Opt out of non-TLS warning manually")
(should (equal (ert-simulate-keys "\r\r\r\rn\r"
(erc-select-read-args))
--
2.38.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #6: 0004-5.6-Optionally-prompt-for-more-ERC-entry-point-param.patch --]
[-- Type: text/x-patch, Size: 4839 bytes --]
From 448686bf96105833cd3e3ee319118c1672d95ca0 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 4/4] [5.6] Optionally prompt for more ERC entry-point params
* doc/misc/erc.texi: Update statement about availability of user param
when entry points called interactively.
* lisp/erc/erc.el (erc-select-read-args): Allow optionally calling
entry points with a prefix arg to access params `user' and
`:full-name'.
(erc-tls): Update doc string.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Add test for
extra args. (Bug#60428.)
---
doc/misc/erc.texi | 2 +-
lisp/erc/erc.el | 19 ++++++++++++++-----
test/lisp/erc/erc-tests.el | 13 ++++++++++++-
3 files changed, 27 insertions(+), 7 deletions(-)
diff --git a/doc/misc/erc.texi b/doc/misc/erc.texi
index 23cdcbff575..40ecd00b226 100644
--- a/doc/misc/erc.texi
+++ b/doc/misc/erc.texi
@@ -932,7 +932,7 @@ SASL
your @samp{NickServ} password. To make this work, customize
@code{erc-sasl-user} and @code{erc-sasl-password} or specify the
@code{:user} and @code{:password} keyword arguments when invoking
-@code{erc-tls}. Note that @code{:user} cannot be given interactively.
+@code{erc-tls}.
@item @code{external} (via Client TLS Certificate)
This works in conjunction with the @code{:client-certificate} keyword
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 09d55f60990..7f2dd89342b 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2177,7 +2177,8 @@ erc--ensure-url
;;;###autoload
(defun erc-select-read-args ()
- "Prompt the user for values of nick, server, port, and password."
+ "Prompt the user for values of nick, server, port, and password.
+With prefix arg, also prompt for user and full name."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
(read-string (format "Server or URL (default is %S): " d)
@@ -2198,6 +2199,14 @@ erc-select-read-args
(let ((d (erc-compute-nick)))
(read-string (format "Nickname (default is %S): " d)
nil 'erc-nick-history-list d))))
+ (user (and current-prefix-arg
+ (let ((d (erc-compute-user (url-user url))))
+ (read-string (format "User (default is %S): " d)
+ nil nil d))))
+ (full (and current-prefix-arg
+ (let ((d (erc-compute-full-name (url-user url))))
+ (read-string (format "Full name (default is %S): " d)
+ nil nil d))))
(passwd (let* ((p (with-suppressed-warnings ((obsolete erc-password))
(or (url-password url) erc-password)))
(m (if p
@@ -2213,8 +2222,8 @@ erc-select-read-args
#'erc-open-tls-stream)))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- `( :server ,server :port ,port :nick ,nick
- ,@(and passwd `(:password ,passwd))
+ `( :server ,server :port ,port :nick ,nick ,@(and user `(:user ,user))
+ ,@(and passwd `(:password ,passwd)) ,@(and full `(:full-name ,full))
,@(and erc-interactive-display
`(buffer-display ,erc-interactive-display))
,@(and opener `(connect-function ,opener)))))
@@ -2321,8 +2330,8 @@ erc-tls
When present, ID should be a symbol or a string to use for naming
the server buffer and identifying the connection unequivocally.
-See info node `(erc) Network Identifier' for details. Like USER
-and CLIENT-CERTIFICATE, this parameter cannot be specified
+See info node `(erc) Network Identifier' for details. Like
+CLIENT-CERTIFICATE, this parameter cannot be specified
interactively.
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 91cdf2f1770..d05b0efe2ed 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1086,7 +1086,18 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick")))))
+ :nick "nick"))))
+
+ (ert-info ("Extra args use URL nick by default")
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r\r\r"
+ (let ((current-prefix-arg '(4)))
+ (erc-select-read-args)))
+ (list :server "localhost"
+ :port 6667
+ :nick "nick"
+ :user "nick"
+ :password "sesame"
+ :full-name "nick")))))
(ert-deftest erc-tls ()
(let (calls)
--
2.38.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] ` <87h6x9yapz.fsf@neverwas.me>
@ 2023-01-19 14:18 ` J.P.
0 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-01-19 14:18 UTC (permalink / raw)
To: 60428; +Cc: emacs-erc
"J.P." <jp@neverwas.me> writes:
> v2. Respect `erc-prompt-for-password'. Remove `run-at-time' hack from
> regression fix.
The first patch
0001-Fix-default-port-regression-in-erc-select-read-args.patch
was added to emacs-29 as
ff35ac9dfabf7ac33199c42bc56c8bb0f53eebc4
The rest will have to wait for 5.6, hopefully after some discussion and
improvements. Thanks.
^ permalink raw reply [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] <87mt750ygt.fsf@neverwas.me>
2023-01-02 1:41 ` bug#60428: 29.0.60; ERC 5.4.1: Fix default-port regression in erc-select-read-args J.P.
[not found] ` <87h6x9yapz.fsf@neverwas.me>
@ 2023-02-07 15:21 ` J.P.
2023-02-19 15:05 ` J.P.
` (3 subsequent siblings)
6 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-02-07 15:21 UTC (permalink / raw)
To: 60428; +Cc: emacs-erc
[-- Attachment #1: Type: text/plain, Size: 75 bytes --]
v3. Don't shadow special vars in entry-point lambda lists. Improve
tests.
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0000-v2-v3.diff --]
[-- Type: text/x-patch, Size: 11594 bytes --]
From 797e9cce1ad3fc34fc59ddbadd9d28d017955b59 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Tue, 7 Feb 2023 00:02:26 -0800
Subject: [PATCH 0/3] *** NOT A PATCH ***
*** BLURB HERE ***
F. Jason Park (3):
[5.6] Be smarter about switching to TLS from M-x erc
[5.6] Add display option for interactive ERC invocations
[5.6] Optionally prompt for more ERC entry-point params
doc/misc/erc.texi | 2 +-
lisp/erc/erc.el | 108 ++++++++++++++++++---------
test/lisp/erc/erc-tests.el | 146 +++++++++++++++++++++++++++++++------
3 files changed, 199 insertions(+), 57 deletions(-)
Interdiff:
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 691e865bfa4..6aec59e6f11 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2234,15 +2234,27 @@ erc-select-read-args
(eql port erc-default-port)
(y-or-n-p "Connect using TLS instead? ")
(setq port erc-default-port-tls)))
- #'erc-open-tls-stream)))
+ #'erc-open-tls-stream))
+ env)
+ (when erc-interactive-display
+ (push `(erc-join-buffer . ,erc-interactive-display) env))
+ (when opener
+ (push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
(setq passwd nil))
`( :server ,server :port ,port :nick ,nick ,@(and user `(:user ,user))
,@(and passwd `(:password ,passwd)) ,@(and full `(:full-name ,full))
- ,@(and erc-interactive-display
- `(buffer-display ,erc-interactive-display))
- ,@(and opener `(connect-function ,opener)))))
-
+ ,@(and env `(&interactive-env ,env)))))
+
+(defmacro erc--with-entrypoint-environment (env &rest body)
+ "Run BODY with bindings from ENV alist."
+ (declare (indent 1))
+ (let ((syms (make-symbol "syms"))
+ (vals (make-symbol "vals")))
+ `(let (,syms ,vals)
+ (pcase-dolist (`(,k . ,v) ,env) (push k ,syms) (push v ,vals))
+ (cl-progv ,syms ,vals
+ ,@body))))
;;;###autoload
(cl-defun erc (&key (server (erc-compute-server))
@@ -2252,10 +2264,8 @@ erc
password
(full-name (erc-compute-full-name))
id
- ;; For interactive use
- ((buffer-display erc-join-buffer) erc-join-buffer)
- ((connect-function erc-server-connect-function)
- erc-server-connect-function))
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC.
@@ -2282,7 +2292,8 @@ erc
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME ID)"
(interactive (erc-select-read-args))
- (erc-open server port nick full-name t password nil nil nil nil user id))
+ (erc--with-entrypoint-environment --interactive-env--
+ (erc-open server port nick full-name t password nil nil nil nil user id)))
;;;###autoload
(defalias 'erc-select #'erc)
@@ -2297,13 +2308,8 @@ erc-tls
(full-name (erc-compute-full-name))
client-certificate
id
- ;; For interactive use
- ((buffer-display erc-join-buffer) erc-join-buffer)
- ((connect-function erc-server-connect-function)
- (if (eq erc-server-connect-function
- #'erc-open-network-stream)
- #'erc-open-tls-stream
- erc-server-connect-function)))
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC over TLS.
@@ -2352,7 +2358,12 @@ erc-tls
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
(interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
- (progn
+ (unless (or (assq 'erc-server-connect-function --interactive-env--)
+ ;; Fails when advice is present, but assume user can cope.
+ (not (eq erc-server-connect-function #'erc-open-network-stream)))
+ (push '(erc-server-connect-function . erc-open-tls-stream)
+ --interactive-env--))
+ (erc--with-entrypoint-environment --interactive-env--
(erc-open server port nick full-name t password
nil nil nil client-certificate user id)))
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 1029a38c726..8f44d984f09 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -999,6 +999,13 @@ erc--server-connect-dumb-ipv6-regexp
(should (string-match erc--server-connect-dumb-ipv6-regexp
(concat "[" a "]")))))
+(ert-deftest erc--with-entrypoint-environment ()
+ (let ((env '((erc-join-buffer . foo)
+ (erc-server-connect-function . bar))))
+ (erc--with-entrypoint-environment env
+ (should (eq erc-join-buffer 'foo))
+ (should (eq erc-server-connect-function 'bar)))))
+
(ert-deftest erc-select-read-args ()
(ert-info ("Prompts for switch to TLS by default")
@@ -1007,8 +1014,9 @@ erc-select-read-args
(list :server "irc.libera.chat"
:port 6697
:nick (user-login-name)
- 'buffer-display 'buffer
- 'connect-function #'erc-open-tls-stream))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when port matches default TLS port")
(should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
@@ -1016,8 +1024,9 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- 'buffer-display 'buffer
- 'connect-function #'erc-open-tls-stream))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when URL is ircs://")
(should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
@@ -1025,8 +1034,9 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- 'buffer-display 'buffer
- 'connect-function #'erc-open-tls-stream))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(setq-local erc-interactive-display nil) ; cheat to save space
@@ -1100,17 +1110,25 @@ erc-select-read-args
:full-name "nick")))))
(ert-deftest erc-tls ()
- (let (calls)
+ (let (calls env)
(cl-letf (((symbol-function 'user-login-name)
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
- (lambda (&rest r) (push r calls))))
+ (lambda (&rest r)
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
(ert-info ("Defaults")
(erc-tls)
(should (equal (pop calls)
'("irc.libera.chat" 6697 "tester" "unknown" t
- nil nil nil nil nil "user" nil))))
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Full")
(erc-tls :server "irc.gnu.org"
@@ -1123,7 +1141,10 @@ erc-tls
:id 'GNU.org)
(should (equal (pop calls)
'("irc.gnu.org" 7000 "bob" "Bob's Name" t
- "bob:changeme" nil nil nil t "bobo" GNU.org))))
+ "bob:changeme" nil nil nil t "bobo" GNU.org)))
+ (should (equal (pop env)
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
;; Values are often nil when called by lisp code, which leads to
;; null params. This is why `erc-open' recomputes almost
@@ -1139,7 +1160,56 @@ erc-tls
:password "bob:changeme"))
(should (equal (pop calls)
'(nil 7000 nil "Bob's Name" t
- "bob:changeme" nil nil nil nil "bobo" nil)))))))
+ "bob:changeme" nil nil nil nil "bobo" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Interactive")
+ (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
+ (call-interactively #'erc-tls))
+ (should (equal (pop calls)
+ '("localhost" 6667 "nick" "unknown" t "sesame"
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer buffer) (erc-server-connect-function
+ erc-open-tls-stream))))))))
+
+;; See `erc-select-read-args' above for argument parsing.
+;; This only tests the "hidden" arguments.
+
+(ert-deftest erc--interactive ()
+ (let (calls env)
+ (cl-letf (((symbol-function 'user-login-name)
+ (lambda (&optional _) "tester"))
+ ((symbol-function 'erc-open)
+ (lambda (&rest r)
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
+
+ (ert-info ("Default click-through accept TLS upgrade")
+ (ert-simulate-keys "\r\r\r\ry\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer buffer) (erc-server-connect-function
+ erc-open-tls-stream)))))
+
+ (ert-info ("Nick supplied, decline TLS upgrade")
+ (ert-simulate-keys "\r\rdummy\r\rn\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6667 "dummy" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer buffer)
+ (erc-server-connect-function
+ erc-open-network-stream))))))))
(defun erc-tests--make-server-buf (name)
(with-current-buffer (get-buffer-create name)
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #3: 0001-5.6-Be-smarter-about-switching-to-TLS-from-M-x-erc.patch --]
[-- Type: text/x-patch, Size: 16613 bytes --]
From 929ad7b2412e45a8c3a0cd3dab00b35a7e8644c2 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 1/3] [5.6] Be smarter about switching to TLS from M-x erc
* lisp/erc/erc.el (erc--warn-unencrypted): Remove newly unused
internal function.
(erc-select-read-args): Offer to use TLS when user runs M-x erc and
opts for default server and port or provides the well-known IANA TLS
port or enters an ircs:// URL at the server prompt. For the last two,
do this immediately instead of calling `erc-tls' interactively and
imposing a review of just-chosen values. Also remove error warnings
and ensure `erc-tls' still works by setting
`erc-server-connect-function' to `erc-open-tls-stream' when
appropriate. Include the word "URL" in server prompt.
(erc--with-entrypoint-environment): Add new macro to allow interactive
form to bind special variables in associated commands' body without
shadowing them in the lambda list.
(erc, erc-tls): Add internal keyword argument for interactive use, but
don't make it colon-prefixed, i.e., `keywordp'. Also use new helper
macro, `erc--with-entrypoint-environment' to temporarily bind special
vars specified by interactive helper `erc-select-read-args'.
* test/lisp/erc/erc-tests.el (erc--with-entrypoint-environment): Add
new test.
(erc-select-read-args): Modify return values to expect additional
internal keyword argument where appropriate.
(erc-tls): Make assertions about environment.
(erc--interactive): New test. (Bug#60428.)
---
lisp/erc/erc.el | 76 +++++++++++++---------
test/lisp/erc/erc-tests.el | 126 ++++++++++++++++++++++++++++++-------
2 files changed, 148 insertions(+), 54 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index ff1820cfaf2..ba6055e1b93 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2176,29 +2176,12 @@ erc--ensure-url
(setq input (concat "irc://" input)))
input)
-;; A temporary means of addressing the problem of ERC's namesake entry
-;; point defaulting to a non-TLS connection with its default server
-;; (bug#60428).
-(defun erc--warn-unencrypted ()
- ;; Remove unconditionally to avoid wrong context due to races from
- ;; simultaneous dialing or aborting (e.g., via `keybaord-quit').
- (remove-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted)
- (when (and (process-contact erc-server-process :nowait)
- (equal erc-session-server erc-default-server)
- (eql erc-session-port erc-default-port))
- ;; FIXME use the autoloaded `info' instead of `Info-goto-node' in
- ;; `erc-button-alist'.
- (require 'info nil t)
- (erc-display-error-notice
- nil (concat "This connection is unencrypted. Please use `erc-tls'"
- " from now on. See Info:\"(erc) connecting\" for more."))))
-
;;;###autoload
(defun erc-select-read-args ()
"Prompt the user for values of nick, server, port, and password."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
- (read-string (format "Server (default is %S): " d)
+ (read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
;; For legacy reasons, also accept a URL without a scheme.
(url (url-generic-parse-url (erc--ensure-url input)))
@@ -2221,15 +2204,32 @@ erc-select-read-args
(m (if p
(format "Server password (default is %S): " p)
"Server password (optional): ")))
- (if erc-prompt-for-password (read-passwd m nil p) p))))
+ (if erc-prompt-for-password (read-passwd m nil p) p)))
+ (opener (and (or sp (eql port erc-default-port-tls)
+ (and (equal server erc-default-server)
+ (not (string-prefix-p "irc://" input))
+ (eql port erc-default-port)
+ (y-or-n-p "Connect using TLS instead? ")
+ (setq port erc-default-port-tls)))
+ #'erc-open-tls-stream))
+ env)
+ (when opener
+ (push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- (when (and (equal server erc-default-server)
- (eql port erc-default-port)
- (not (eql port erc-default-port-tls)) ; not `erc-tls'
- (not (string-prefix-p "irc://" input))) ; not yanked URL
- (add-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted))
- (list :server server :port port :nick nick :password passwd)))
+ `( :server ,server :port ,port :nick ,nick
+ ,@(and passwd `(:password ,passwd))
+ ,@(and env `(&interactive-env ,env)))))
+
+(defmacro erc--with-entrypoint-environment (env &rest body)
+ "Run BODY with bindings from ENV alist."
+ (declare (indent 1))
+ (let ((syms (make-symbol "syms"))
+ (vals (make-symbol "vals")))
+ `(let (,syms ,vals)
+ (pcase-dolist (`(,k . ,v) ,env) (push k ,syms) (push v ,vals))
+ (cl-progv ,syms ,vals
+ ,@body))))
;;;###autoload
(cl-defun erc (&key (server (erc-compute-server))
@@ -2238,7 +2238,9 @@ erc
(user (erc-compute-user))
password
(full-name (erc-compute-full-name))
- id)
+ id
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC.
@@ -2261,9 +2263,12 @@ erc
whereas `erc-compute-port' and `erc-compute-nick' will be invoked
for the values of the other parameters.
-See `erc-tls' for the meaning of ID."
+See `erc-tls' for the meaning of ID.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME ID)"
(interactive (erc-select-read-args))
- (erc-open server port nick full-name t password nil nil nil nil user id))
+ (erc--with-entrypoint-environment --interactive-env--
+ (erc-open server port nick full-name t password nil nil nil nil user id)))
;;;###autoload
(defalias 'erc-select #'erc)
@@ -2277,7 +2282,9 @@ erc-tls
password
(full-name (erc-compute-full-name))
client-certificate
- id)
+ id
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC over TLS.
@@ -2321,10 +2328,17 @@ erc-tls
the server buffer and identifying the connection unequivocally.
See info node `(erc) Network Identifier' for details. Like USER
and CLIENT-CERTIFICATE, this parameter cannot be specified
-interactively."
+interactively.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
(interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
- (let ((erc-server-connect-function 'erc-open-tls-stream))
+ (unless (or (assq 'erc-server-connect-function --interactive-env--)
+ ;; Fails when advice is present, but assume user can cope.
+ (not (eq erc-server-connect-function #'erc-open-network-stream)))
+ (push '(erc-server-connect-function . erc-open-tls-stream)
+ --interactive-env--))
+ (erc--with-entrypoint-environment --interactive-env--
(erc-open server port nick full-name t password
nil nil nil client-certificate user id)))
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 40a2d2de657..5d2a023486d 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -999,32 +999,62 @@ erc--server-connect-dumb-ipv6-regexp
(should (string-match erc--server-connect-dumb-ipv6-regexp
(concat "[" a "]")))))
+(ert-deftest erc--with-entrypoint-environment ()
+ (let ((env '((erc-join-buffer . foo)
+ (erc-server-connect-function . bar))))
+ (erc--with-entrypoint-environment env
+ (should (eq erc-join-buffer 'foo))
+ (should (eq erc-server-connect-function 'bar)))))
+
(ert-deftest erc-select-read-args ()
- (ert-info ("Does not default to TLS")
- (should (equal (ert-simulate-keys "\r\r\r\r"
+ (ert-info ("Prompts for switch to TLS by default")
+ (should (equal (ert-simulate-keys "\r\r\r\ry\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
- :port 6667
+ :port 6697
+ :nick (user-login-name)
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Switches to TLS when port matches default TLS port")
+ (should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Switches to TLS when URL is ircs://")
+ (should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
:nick (user-login-name)
- :password nil))))
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Opt out of non-TLS warning manually")
+ (should (equal (ert-simulate-keys "\r\r\r\rn\r"
+ (erc-select-read-args))
+ (list :server "irc.libera.chat"
+ :port 6667
+ :nick (user-login-name)))))
(ert-info ("Override default TLS")
(should (equal (ert-simulate-keys "irc://irc.libera.chat\r\r\r\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("Address includes port")
- (should (equal (ert-simulate-keys
- "localhost:6667\rnick\r\r"
+ (should (equal (ert-simulate-keys "localhost:6667\rnick\r\r"
(erc-select-read-args))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick, password skipped via option")
(should (equal (ert-simulate-keys "nick@localhost:6667\r"
@@ -1032,8 +1062,7 @@ erc-select-read-args
(erc-select-read-args)))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick and password")
(should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
@@ -1048,37 +1077,40 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address with port")
(should (equal (ert-simulate-keys "[::1]:6667\r\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address includes nick")
(should (equal (ert-simulate-keys "nick@[::1]:6667\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick"
- :password nil)))))
+ :nick "nick")))))
(ert-deftest erc-tls ()
- (let (calls)
+ (let (calls env)
(cl-letf (((symbol-function 'user-login-name)
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
- (lambda (&rest r) (push r calls))))
+ (lambda (&rest r)
+ (push `((erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
(ert-info ("Defaults")
(erc-tls)
(should (equal (pop calls)
'("irc.libera.chat" 6697 "tester" "unknown" t
- nil nil nil nil nil "user" nil))))
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Full")
(erc-tls :server "irc.gnu.org"
@@ -1091,7 +1123,9 @@ erc-tls
:id 'GNU.org)
(should (equal (pop calls)
'("irc.gnu.org" 7000 "bob" "Bob's Name" t
- "bob:changeme" nil nil nil t "bobo" GNU.org))))
+ "bob:changeme" nil nil nil t "bobo" GNU.org)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
;; Values are often nil when called by lisp code, which leads to
;; null params. This is why `erc-open' recomputes almost
@@ -1107,7 +1141,53 @@ erc-tls
:password "bob:changeme"))
(should (equal (pop calls)
'(nil 7000 nil "Bob's Name" t
- "bob:changeme" nil nil nil nil "bobo" nil)))))))
+ "bob:changeme" nil nil nil nil "bobo" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Interactive")
+ (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
+ (call-interactively #'erc-tls))
+ (should (equal (pop calls)
+ '("localhost" 6667 "nick" "unknown" t "sesame"
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function
+ erc-open-tls-stream))))))))
+
+;; See `erc-select-read-args' above for argument parsing.
+;; This only tests the "hidden" arguments.
+
+(ert-deftest erc--interactive ()
+ (let (calls env)
+ (cl-letf (((symbol-function 'user-login-name)
+ (lambda (&optional _) "tester"))
+ ((symbol-function 'erc-open)
+ (lambda (&rest r)
+ (push `((erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
+
+ (ert-info ("Default click-through accept TLS upgrade")
+ (ert-simulate-keys "\r\r\r\ry\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Nick supplied, decline TLS upgrade")
+ (ert-simulate-keys "\r\rdummy\r\rn\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6667 "dummy" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '(
+ (erc-server-connect-function
+ erc-open-network-stream))))))))
(defun erc-tests--make-server-buf (name)
(with-current-buffer (get-buffer-create name)
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #4: 0002-5.6-Add-display-option-for-interactive-ERC-invocatio.patch --]
[-- Type: text/x-patch, Size: 9129 bytes --]
From 481a720ade4da70e5aeb76ade67e0ff710df15ee Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 2/3] [5.6] Add display option for interactive ERC invocations
* lisp/erc/erc.el (erc-buffer-display, erc-receive-query-display):
Add aliases for `erc-join-buffer' and `erc-auto-query'.
(erc-interactive-display): Add new option to control display of server
buffers during interactive entry-point invocations.
(erc-select-read-args): Pass `erc-interactive-display' to entry
points.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Expect
buffer-display values from `erc-interactive-display'.
(erc-tls, erc--interactive): Also check `erc-join-buffer' in
environment when `erc-open' called. (Bug#60428.)
---
lisp/erc/erc.el | 17 ++++++++++++++++
test/lisp/erc/erc-tests.el | 41 ++++++++++++++++++++++++--------------
2 files changed, 43 insertions(+), 15 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index ba6055e1b93..05e124bc165 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -1468,6 +1468,7 @@ erc-default-port-tls
"IRC port to use for encrypted connections if it cannot be \
detected otherwise.")
+(defvaralias 'erc-buffer-display 'erc-join-buffer)
(defcustom erc-join-buffer 'bury
"Determines how to display a newly created IRC buffer.
@@ -1488,6 +1489,19 @@ erc-join-buffer
(const :tag "Use current buffer" buffer)
(const :tag "Use current buffer" t)))
+(defcustom erc-interactive-display 'buffer
+ "How and whether to display server buffers for M-x erc.
+See `erc-buffer-display' and friends for a description of
+possible values."
+ :package-version '(ERC . "5.4.1") ; FIXME increment upon publishing to ELPA
+ :group 'erc-buffers
+ :type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
+ (const :tag "Split window and select" window)
+ (const :tag "Split window, don't select" window-noselect)
+ (const :tag "New frame" frame)
+ (const :tag "Bury new and don't display existing" bury)
+ (const :tag "Use current buffer" buffer)))
+
(defcustom erc-reconnect-display nil
"How (and whether) to display a channel buffer upon reconnecting.
@@ -2213,6 +2227,8 @@ erc-select-read-args
(setq port erc-default-port-tls)))
#'erc-open-tls-stream))
env)
+ (when erc-interactive-display
+ (push `(erc-join-buffer . ,erc-interactive-display) env))
(when opener
(push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
@@ -4520,6 +4536,7 @@ erc-query
(with-current-buffer server-buffer
(erc--open-target target)))
+(defvaralias 'erc-receive-query-display 'erc-auto-query)
(defcustom erc-auto-query 'window-noselect
"If non-nil, create a query buffer each time you receive a private message.
If the buffer doesn't already exist, it is created.
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 5d2a023486d..91ed5c330f6 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1014,8 +1014,9 @@ erc-select-read-args
(list :server "irc.libera.chat"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when port matches default TLS port")
(should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
@@ -1023,8 +1024,9 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when URL is ircs://")
(should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
@@ -1032,8 +1034,11 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
+
+ (setq-local erc-interactive-display nil) ; cheat to save space
(ert-info ("Opt out of non-TLS warning manually")
(should (equal (ert-simulate-keys "\r\r\r\rn\r"
@@ -1099,7 +1104,8 @@ erc-tls
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
(lambda (&rest r)
- (push `((erc-server-connect-function
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
,erc-server-connect-function))
env)
(push r calls))))
@@ -1110,7 +1116,8 @@ erc-tls
'("irc.libera.chat" 6697 "tester" "unknown" t
nil nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Full")
(erc-tls :server "irc.gnu.org"
@@ -1125,7 +1132,8 @@ erc-tls
'("irc.gnu.org" 7000 "bob" "Bob's Name" t
"bob:changeme" nil nil nil t "bobo" GNU.org)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
;; Values are often nil when called by lisp code, which leads to
;; null params. This is why `erc-open' recomputes almost
@@ -1143,7 +1151,8 @@ erc-tls
'(nil 7000 nil "Bob's Name" t
"bob:changeme" nil nil nil nil "bobo" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Interactive")
(ert-simulate-keys "nick:sesame@localhost:6667\r\r"
@@ -1152,8 +1161,8 @@ erc-tls
'("localhost" 6667 "nick" "unknown" t "sesame"
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function
- erc-open-tls-stream))))))))
+ '((erc-join-buffer buffer) (erc-server-connect-function
+ erc-open-tls-stream))))))))
;; See `erc-select-read-args' above for argument parsing.
;; This only tests the "hidden" arguments.
@@ -1164,7 +1173,8 @@ erc--interactive
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
(lambda (&rest r)
- (push `((erc-server-connect-function
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
,erc-server-connect-function))
env)
(push r calls))))
@@ -1176,7 +1186,8 @@ erc--interactive
'("irc.libera.chat" 6697 "tester" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer buffer) (erc-server-connect-function
+ erc-open-tls-stream)))))
(ert-info ("Nick supplied, decline TLS upgrade")
(ert-simulate-keys "\r\rdummy\r\rn\r"
@@ -1185,7 +1196,7 @@ erc--interactive
'("irc.libera.chat" 6667 "dummy" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '(
+ '((erc-join-buffer buffer)
(erc-server-connect-function
erc-open-network-stream))))))))
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #5: 0003-5.6-Optionally-prompt-for-more-ERC-entry-point-param.patch --]
[-- Type: text/x-patch, Size: 4814 bytes --]
From 797e9cce1ad3fc34fc59ddbadd9d28d017955b59 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 3/3] [5.6] Optionally prompt for more ERC entry-point params
* doc/misc/erc.texi: Update statement about availability of user param
when entry points called interactively.
* lisp/erc/erc.el (erc-select-read-args): Allow optionally calling
entry points with a prefix arg to access params `user' and
`:full-name'.
(erc-tls): Update doc string.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Add test for
extra args. (Bug#60428.)
---
doc/misc/erc.texi | 2 +-
lisp/erc/erc.el | 19 ++++++++++++++-----
test/lisp/erc/erc-tests.el | 13 ++++++++++++-
3 files changed, 27 insertions(+), 7 deletions(-)
diff --git a/doc/misc/erc.texi b/doc/misc/erc.texi
index 8030dfa4bb7..94b98ed5e64 100644
--- a/doc/misc/erc.texi
+++ b/doc/misc/erc.texi
@@ -951,7 +951,7 @@ SASL
your @samp{NickServ} password. To make this work, customize
@code{erc-sasl-user} and @code{erc-sasl-password} or specify the
@code{:user} and @code{:password} keyword arguments when invoking
-@code{erc-tls}. Note that @code{:user} cannot be given interactively.
+@code{erc-tls}.
@item @code{external} (via Client TLS Certificate)
This works in conjunction with the @code{:client-certificate} keyword
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 05e124bc165..6aec59e6f11 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2192,7 +2192,8 @@ erc--ensure-url
;;;###autoload
(defun erc-select-read-args ()
- "Prompt the user for values of nick, server, port, and password."
+ "Prompt the user for values of nick, server, port, and password.
+With prefix arg, also prompt for user and full name."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
(read-string (format "Server or URL (default is %S): " d)
@@ -2213,6 +2214,14 @@ erc-select-read-args
(let ((d (erc-compute-nick)))
(read-string (format "Nickname (default is %S): " d)
nil 'erc-nick-history-list d))))
+ (user (and current-prefix-arg
+ (let ((d (erc-compute-user (url-user url))))
+ (read-string (format "User (default is %S): " d)
+ nil nil d))))
+ (full (and current-prefix-arg
+ (let ((d (erc-compute-full-name (url-user url))))
+ (read-string (format "Full name (default is %S): " d)
+ nil nil d))))
(passwd (let* ((p (with-suppressed-warnings ((obsolete erc-password))
(or (url-password url) erc-password)))
(m (if p
@@ -2233,8 +2242,8 @@ erc-select-read-args
(push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- `( :server ,server :port ,port :nick ,nick
- ,@(and passwd `(:password ,passwd))
+ `( :server ,server :port ,port :nick ,nick ,@(and user `(:user ,user))
+ ,@(and passwd `(:password ,passwd)) ,@(and full `(:full-name ,full))
,@(and env `(&interactive-env ,env)))))
(defmacro erc--with-entrypoint-environment (env &rest body)
@@ -2342,8 +2351,8 @@ erc-tls
When present, ID should be a symbol or a string to use for naming
the server buffer and identifying the connection unequivocally.
-See info node `(erc) Network Identifier' for details. Like USER
-and CLIENT-CERTIFICATE, this parameter cannot be specified
+See info node `(erc) Network Identifier' for details. Like
+CLIENT-CERTIFICATE, this parameter cannot be specified
interactively.
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 91ed5c330f6..8f44d984f09 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1096,7 +1096,18 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick")))))
+ :nick "nick"))))
+
+ (ert-info ("Extra args use URL nick by default")
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r\r\r"
+ (let ((current-prefix-arg '(4)))
+ (erc-select-read-args)))
+ (list :server "localhost"
+ :port 6667
+ :nick "nick"
+ :user "nick"
+ :password "sesame"
+ :full-name "nick")))))
(ert-deftest erc-tls ()
(let (calls env)
--
2.39.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] <87mt750ygt.fsf@neverwas.me>
` (2 preceding siblings ...)
2023-02-07 15:21 ` J.P.
@ 2023-02-19 15:05 ` J.P.
[not found] ` <87h6vhwv9u.fsf@neverwas.me>
` (2 subsequent siblings)
6 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-02-19 15:05 UTC (permalink / raw)
To: 60428; +Cc: emacs-erc
[-- Attachment #1: Type: text/plain, Size: 70 bytes --]
v4. Stop requiring `url-parse' library when compiling. Improve test.
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0000-v3-v4.diff --]
[-- Type: text/x-patch, Size: 6433 bytes --]
From c348a0162a84f97627bb7b9b613d6c88a12a03e7 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Fri, 17 Feb 2023 00:03:19 -0800
Subject: [PATCH 0/3] *** NOT A PATCH ***
*** BLURB HERE ***
F. Jason Park (3):
[5.6] Be smarter about switching to TLS from M-x erc
[5.6] Add display option for interactive ERC invocations
[5.6] Optionally prompt for more ERC entry-point params
doc/misc/erc.texi | 2 +-
lisp/erc/erc-compat.el | 3 +-
lisp/erc/erc.el | 120 ++++++++++++++++--------
test/lisp/erc/erc-tests.el | 182 ++++++++++++++++++++++++++++++++-----
4 files changed, 247 insertions(+), 60 deletions(-)
Interdiff:
diff --git a/lisp/erc/erc-compat.el b/lisp/erc/erc-compat.el
index 5601ede27a5..d475d9cf458 100644
--- a/lisp/erc/erc-compat.el
+++ b/lisp/erc/erc-compat.el
@@ -32,7 +32,7 @@
;;; Code:
(require 'compat nil 'noerror)
-(eval-when-compile (require 'cl-lib) (require 'url-parse))
+(eval-when-compile (require 'cl-lib))
;;;###autoload(autoload 'erc-define-minor-mode "erc-compat")
(define-obsolete-function-alias 'erc-define-minor-mode
@@ -378,6 +378,7 @@ erc-compat--with-memoization
(t `(progn ,@forms))))
(defvar url-irc-function)
+(declare-function url-type "url-parse" (cl-x))
(defun erc-compat--29-browse-url-irc (string &rest _)
(require 'url-irc)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 12d148d767f..f1a51341924 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -69,7 +69,7 @@
(require 'auth-source)
(require 'time-date)
(require 'iso8601)
-(eval-when-compile (require 'subr-x) (require 'url-parse))
+(eval-when-compile (require 'subr-x))
(defconst erc-version "5.4.1"
"This version of ERC.")
@@ -139,6 +139,12 @@ tabbar--local-hlf
(defvar motif-version-string)
(defvar gtk-version-string)
+(declare-function url-host "url-parse" (cl-x))
+(declare-function url-password "url-parse" (cl-x))
+(declare-function url-portspec "url-parse" (cl-x))
+(declare-function url-type "url-parse" (cl-x))
+(declare-function url-user "url-parse" (cl-x))
+
;; tunable connection and authentication parameters
(defcustom erc-server nil
@@ -1493,7 +1499,7 @@ erc-interactive-display
"How and whether to display server buffers for M-x erc.
See `erc-buffer-display' and friends for a description of
possible values."
- :package-version '(ERC . "5.4.1") ; FIXME increment upon publishing to ELPA
+ :package-version '(ERC . "5.6") ; FIXME sync on release
:group 'erc-buffers
:type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
(const :tag "Split window and select" window)
@@ -2194,7 +2200,6 @@ erc--ensure-url
(defun erc-select-read-args ()
"Prompt the user for values of nick, server, port, and password.
With prefix arg, also prompt for user and full name."
- (require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
(read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
@@ -2358,8 +2363,11 @@ erc-tls
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
(interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
+ ;; Bind `erc-server-connect-function' to `erc-open-tls-stream'
+ ;; around `erc-open' when a non-default value hasn't been specified
+ ;; by the user or the interactive form. And don't bother checking
+ ;; for advice, indirect functions, autoloads, etc.
(unless (or (assq 'erc-server-connect-function --interactive-env--)
- ;; Fails when advice is present, but assume user can cope.
(not (eq erc-server-connect-function #'erc-open-network-stream)))
(push '(erc-server-connect-function . erc-open-tls-stream)
--interactive-env--))
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 8f44d984f09..68b4413da44 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1172,8 +1172,44 @@ erc-tls
'("localhost" 6667 "nick" "unknown" t "sesame"
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-join-buffer buffer) (erc-server-connect-function
- erc-open-tls-stream))))))))
+ '((erc-join-buffer buffer)
+ (erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Custom connect function")
+ (let ((erc-server-connect-function 'my-connect-func))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer bury)
+ (erc-server-connect-function my-connect-func))))))
+
+ (ert-info ("Advised default function overlooked") ; intentional
+ (advice-add 'erc-server-connect-function :around #'ignore
+ '((name . erc-tests--erc-tls)))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream))))
+ (advice-remove 'erc-server-connect-function 'erc-tests--erc-tls))
+
+ (ert-info ("Advised non-default function honored")
+ (let ((f (lambda (&rest r) (ignore r))))
+ (cl-letf (((symbol-value 'erc-server-connect-function) f))
+ (advice-add 'erc-server-connect-function :around #'ignore
+ '((name . erc-tests--erc-tls)))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env) `((erc-join-buffer bury)
+ (erc-server-connect-function ,f))))
+ (advice-remove 'erc-server-connect-function
+ 'erc-tests--erc-tls)))))))
;; See `erc-select-read-args' above for argument parsing.
;; This only tests the "hidden" arguments.
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #3: 0001-5.6-Be-smarter-about-switching-to-TLS-from-M-x-erc.patch --]
[-- Type: text/x-patch, Size: 18474 bytes --]
From f782019a999bd94ddcb425458f114123d2e472dc Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 1/3] [5.6] Be smarter about switching to TLS from M-x erc
* lisp/erc/erc.el (erc--warn-unencrypted): Remove newly unused
internal function.
(erc-select-read-args): Offer to use TLS when user runs M-x erc and
opts for default server and port or provides the well-known IANA TLS
port or enters an ircs:// URL at the server prompt. For the last two,
do this immediately instead of calling `erc-tls' interactively and
imposing a review of just-chosen values. Also remove error warnings
and ensure `erc-tls' still works by setting
`erc-server-connect-function' to `erc-open-tls-stream' when
appropriate. Include the word "URL" in server prompt.
(erc--with-entrypoint-environment): Add new macro to allow interactive
form to bind special variables in associated commands' body without
shadowing them in the lambda list.
(erc, erc-tls): Add internal keyword argument for interactive use, but
don't make it colon-prefixed, i.e., `keywordp'. Also use new helper
macro, `erc--with-entrypoint-environment' to temporarily bind special
vars specified by interactive helper `erc-select-read-args'.
* test/lisp/erc/erc-tests.el (erc--with-entrypoint-environment): Add
new test.
(erc-select-read-args): Modify return values to expect additional
internal keyword argument where appropriate.
(erc-tls): Make assertions about environment.
(erc--interactive): New test. (Bug#60428.)
---
lisp/erc/erc.el | 79 ++++++++++--------
test/lisp/erc/erc-tests.el | 159 +++++++++++++++++++++++++++++++------
2 files changed, 184 insertions(+), 54 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index d35907a1677..ff91378ce79 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -2176,29 +2176,12 @@ erc--ensure-url
(setq input (concat "irc://" input)))
input)
-;; A temporary means of addressing the problem of ERC's namesake entry
-;; point defaulting to a non-TLS connection with its default server
-;; (bug#60428).
-(defun erc--warn-unencrypted ()
- ;; Remove unconditionally to avoid wrong context due to races from
- ;; simultaneous dialing or aborting (e.g., via `keybaord-quit').
- (remove-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted)
- (when (and (process-contact erc-server-process :nowait)
- (equal erc-session-server erc-default-server)
- (eql erc-session-port erc-default-port))
- ;; FIXME use the autoloaded `info' instead of `Info-goto-node' in
- ;; `erc-button-alist'.
- (require 'info nil t)
- (erc-display-error-notice
- nil (concat "This connection is unencrypted. Please use `erc-tls'"
- " from now on. See Info:\"(erc) connecting\" for more."))))
-
;;;###autoload
(defun erc-select-read-args ()
"Prompt the user for values of nick, server, port, and password."
(require 'url-parse)
(let* ((input (let ((d (erc-compute-server)))
- (read-string (format "Server (default is %S): " d)
+ (read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
;; For legacy reasons, also accept a URL without a scheme.
(url (url-generic-parse-url (erc--ensure-url input)))
@@ -2221,15 +2204,32 @@ erc-select-read-args
(m (if p
(format "Server password (default is %S): " p)
"Server password (optional): ")))
- (if erc-prompt-for-password (read-passwd m nil p) p))))
+ (if erc-prompt-for-password (read-passwd m nil p) p)))
+ (opener (and (or sp (eql port erc-default-port-tls)
+ (and (equal server erc-default-server)
+ (not (string-prefix-p "irc://" input))
+ (eql port erc-default-port)
+ (y-or-n-p "Connect using TLS instead? ")
+ (setq port erc-default-port-tls)))
+ #'erc-open-tls-stream))
+ env)
+ (when opener
+ (push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- (when (and (equal server erc-default-server)
- (eql port erc-default-port)
- (not (eql port erc-default-port-tls)) ; not `erc-tls'
- (not (string-prefix-p "irc://" input))) ; not yanked URL
- (add-hook 'erc--server-post-connect-hook #'erc--warn-unencrypted))
- (list :server server :port port :nick nick :password passwd)))
+ `( :server ,server :port ,port :nick ,nick
+ ,@(and passwd `(:password ,passwd))
+ ,@(and env `(&interactive-env ,env)))))
+
+(defmacro erc--with-entrypoint-environment (env &rest body)
+ "Run BODY with bindings from ENV alist."
+ (declare (indent 1))
+ (let ((syms (make-symbol "syms"))
+ (vals (make-symbol "vals")))
+ `(let (,syms ,vals)
+ (pcase-dolist (`(,k . ,v) ,env) (push k ,syms) (push v ,vals))
+ (cl-progv ,syms ,vals
+ ,@body))))
;;;###autoload
(cl-defun erc (&key (server (erc-compute-server))
@@ -2238,7 +2238,9 @@ erc
(user (erc-compute-user))
password
(full-name (erc-compute-full-name))
- id)
+ id
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC.
@@ -2261,9 +2263,12 @@ erc
whereas `erc-compute-port' and `erc-compute-nick' will be invoked
for the values of the other parameters.
-See `erc-tls' for the meaning of ID."
+See `erc-tls' for the meaning of ID.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME ID)"
(interactive (erc-select-read-args))
- (erc-open server port nick full-name t password nil nil nil nil user id))
+ (erc--with-entrypoint-environment --interactive-env--
+ (erc-open server port nick full-name t password nil nil nil nil user id)))
;;;###autoload
(defalias 'erc-select #'erc)
@@ -2277,7 +2282,9 @@ erc-tls
password
(full-name (erc-compute-full-name))
client-certificate
- id)
+ id
+ ;; Used by interactive form
+ ((&interactive-env --interactive-env--)))
"ERC is a powerful, modular, and extensible IRC client.
This function is the main entry point for ERC over TLS.
@@ -2321,10 +2328,20 @@ erc-tls
the server buffer and identifying the connection unequivocally.
See Info node `(erc) Network Identifier' for details. Like USER
and CLIENT-CERTIFICATE, this parameter cannot be specified
-interactively."
+interactively.
+
+\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
(interactive (let ((erc-default-port erc-default-port-tls))
(erc-select-read-args)))
- (let ((erc-server-connect-function 'erc-open-tls-stream))
+ ;; Bind `erc-server-connect-function' to `erc-open-tls-stream'
+ ;; around `erc-open' when a non-default value hasn't been specified
+ ;; by the user or the interactive form. And don't bother checking
+ ;; for advice, indirect functions, autoloads, etc.
+ (unless (or (assq 'erc-server-connect-function --interactive-env--)
+ (not (eq erc-server-connect-function #'erc-open-network-stream)))
+ (push '(erc-server-connect-function . erc-open-tls-stream)
+ --interactive-env--))
+ (erc--with-entrypoint-environment --interactive-env--
(erc-open server port nick full-name t password
nil nil nil client-certificate user id)))
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 40a2d2de657..03df72d9500 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -999,32 +999,62 @@ erc--server-connect-dumb-ipv6-regexp
(should (string-match erc--server-connect-dumb-ipv6-regexp
(concat "[" a "]")))))
+(ert-deftest erc--with-entrypoint-environment ()
+ (let ((env '((erc-join-buffer . foo)
+ (erc-server-connect-function . bar))))
+ (erc--with-entrypoint-environment env
+ (should (eq erc-join-buffer 'foo))
+ (should (eq erc-server-connect-function 'bar)))))
+
(ert-deftest erc-select-read-args ()
- (ert-info ("Does not default to TLS")
- (should (equal (ert-simulate-keys "\r\r\r\r"
+ (ert-info ("Prompts for switch to TLS by default")
+ (should (equal (ert-simulate-keys "\r\r\r\ry\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
- :port 6667
+ :port 6697
+ :nick (user-login-name)
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Switches to TLS when port matches default TLS port")
+ (should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
+ :nick (user-login-name)
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Switches to TLS when URL is ircs://")
+ (should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
+ (erc-select-read-args))
+ (list :server "irc.gnu.org"
+ :port 6697
:nick (user-login-name)
- :password nil))))
+ '&interactive-env '((erc-server-connect-function
+ . erc-open-tls-stream))))))
+
+ (ert-info ("Opt out of non-TLS warning manually")
+ (should (equal (ert-simulate-keys "\r\r\r\rn\r"
+ (erc-select-read-args))
+ (list :server "irc.libera.chat"
+ :port 6667
+ :nick (user-login-name)))))
(ert-info ("Override default TLS")
(should (equal (ert-simulate-keys "irc://irc.libera.chat\r\r\r\r"
(erc-select-read-args))
(list :server "irc.libera.chat"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("Address includes port")
- (should (equal (ert-simulate-keys
- "localhost:6667\rnick\r\r"
+ (should (equal (ert-simulate-keys "localhost:6667\rnick\r\r"
(erc-select-read-args))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick, password skipped via option")
(should (equal (ert-simulate-keys "nick@localhost:6667\r"
@@ -1032,8 +1062,7 @@ erc-select-read-args
(erc-select-read-args)))
(list :server "localhost"
:port 6667
- :nick "nick"
- :password nil))))
+ :nick "nick"))))
(ert-info ("Address includes nick and password")
(should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
@@ -1048,37 +1077,40 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address with port")
(should (equal (ert-simulate-keys "[::1]:6667\r\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick (user-login-name)
- :password nil))))
+ :nick (user-login-name)))))
(ert-info ("IPv6 address includes nick")
(should (equal (ert-simulate-keys "nick@[::1]:6667\r\r"
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick"
- :password nil)))))
+ :nick "nick")))))
(ert-deftest erc-tls ()
- (let (calls)
+ (let (calls env)
(cl-letf (((symbol-function 'user-login-name)
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
- (lambda (&rest r) (push r calls))))
+ (lambda (&rest r)
+ (push `((erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
(ert-info ("Defaults")
(erc-tls)
(should (equal (pop calls)
'("irc.libera.chat" 6697 "tester" "unknown" t
- nil nil nil nil nil "user" nil))))
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Full")
(erc-tls :server "irc.gnu.org"
@@ -1091,7 +1123,9 @@ erc-tls
:id 'GNU.org)
(should (equal (pop calls)
'("irc.gnu.org" 7000 "bob" "Bob's Name" t
- "bob:changeme" nil nil nil t "bobo" GNU.org))))
+ "bob:changeme" nil nil nil t "bobo" GNU.org)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
;; Values are often nil when called by lisp code, which leads to
;; null params. This is why `erc-open' recomputes almost
@@ -1107,7 +1141,86 @@ erc-tls
:password "bob:changeme"))
(should (equal (pop calls)
'(nil 7000 nil "Bob's Name" t
- "bob:changeme" nil nil nil nil "bobo" nil)))))))
+ "bob:changeme" nil nil nil nil "bobo" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Interactive")
+ (ert-simulate-keys "nick:sesame@localhost:6667\r\r"
+ (call-interactively #'erc-tls))
+ (should (equal (pop calls)
+ '("localhost" 6667 "nick" "unknown" t "sesame"
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function
+ erc-open-tls-stream)))))
+
+ (ert-info ("Custom connect function")
+ (let ((erc-server-connect-function 'my-connect-func))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function my-connect-func))))))
+
+ (ert-info ("Advised default function overlooked") ; intentional
+ (advice-add 'erc-server-connect-function :around #'ignore
+ '((name . erc-tests--erc-tls)))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream))))
+ (advice-remove 'erc-server-connect-function 'erc-tests--erc-tls))
+
+ (ert-info ("Advised non-default function honored")
+ (let ((f (lambda (&rest r) (ignore r))))
+ (cl-letf (((symbol-value 'erc-server-connect-function) f))
+ (advice-add 'erc-server-connect-function :around #'ignore
+ '((name . erc-tests--erc-tls)))
+ (erc-tls)
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t
+ nil nil nil nil nil "user" nil)))
+ (should (equal (pop env) `((erc-server-connect-function ,f))))
+ (advice-remove 'erc-server-connect-function
+ 'erc-tests--erc-tls)))))))
+
+;; See `erc-select-read-args' above for argument parsing.
+;; This only tests the "hidden" arguments.
+
+(ert-deftest erc--interactive ()
+ (let (calls env)
+ (cl-letf (((symbol-function 'user-login-name)
+ (lambda (&optional _) "tester"))
+ ((symbol-function 'erc-open)
+ (lambda (&rest r)
+ (push `((erc-server-connect-function
+ ,erc-server-connect-function))
+ env)
+ (push r calls))))
+
+ (ert-info ("Default click-through accept TLS upgrade")
+ (ert-simulate-keys "\r\r\r\ry\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6697 "tester" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '((erc-server-connect-function erc-open-tls-stream)))))
+
+ (ert-info ("Nick supplied, decline TLS upgrade")
+ (ert-simulate-keys "\r\rdummy\r\rn\r"
+ (call-interactively #'erc))
+ (should (equal (pop calls)
+ '("irc.libera.chat" 6667 "dummy" "unknown" t nil
+ nil nil nil nil "user" nil)))
+ (should (equal (pop env)
+ '(
+ (erc-server-connect-function
+ erc-open-network-stream))))))))
(defun erc-tests--make-server-buf (name)
(with-current-buffer (get-buffer-create name)
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #4: 0002-5.6-Add-display-option-for-interactive-ERC-invocatio.patch --]
[-- Type: text/x-patch, Size: 10701 bytes --]
From 093763faa5282f25ac238b8433715d6912b27398 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 2/3] [5.6] Add display option for interactive ERC invocations
* lisp/erc/erc.el (erc-buffer-display, erc-receive-query-display):
Add aliases for `erc-join-buffer' and `erc-auto-query'.
(erc-interactive-display): Add new option to control display of server
buffers during interactive entry-point invocations.
(erc-select-read-args): Pass `erc-interactive-display' to entry
points.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Expect
buffer-display values from `erc-interactive-display'.
(erc-tls, erc--interactive): Also check `erc-join-buffer' in
environment when `erc-open' called. (Bug#60428.)
---
lisp/erc/erc.el | 17 +++++++++++++
test/lisp/erc/erc-tests.el | 50 ++++++++++++++++++++++++--------------
2 files changed, 49 insertions(+), 18 deletions(-)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index ff91378ce79..9dbca09bb35 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -1468,6 +1468,7 @@ erc-default-port-tls
"IRC port to use for encrypted connections if it cannot be \
detected otherwise.")
+(defvaralias 'erc-buffer-display 'erc-join-buffer)
(defcustom erc-join-buffer 'bury
"Determines how to display a newly created IRC buffer.
@@ -1488,6 +1489,19 @@ erc-join-buffer
(const :tag "Use current buffer" buffer)
(const :tag "Use current buffer" t)))
+(defcustom erc-interactive-display 'buffer
+ "How and whether to display server buffers for M-x erc.
+See `erc-buffer-display' and friends for a description of
+possible values."
+ :package-version '(ERC . "5.6") ; FIXME sync on release
+ :group 'erc-buffers
+ :type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
+ (const :tag "Split window and select" window)
+ (const :tag "Split window, don't select" window-noselect)
+ (const :tag "New frame" frame)
+ (const :tag "Bury new and don't display existing" bury)
+ (const :tag "Use current buffer" buffer)))
+
(defcustom erc-reconnect-display nil
"How (and whether) to display a channel buffer upon reconnecting.
@@ -2213,6 +2227,8 @@ erc-select-read-args
(setq port erc-default-port-tls)))
#'erc-open-tls-stream))
env)
+ (when erc-interactive-display
+ (push `(erc-join-buffer . ,erc-interactive-display) env))
(when opener
(push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
@@ -4523,6 +4539,7 @@ erc-query
(with-current-buffer server-buffer
(erc--open-target target)))
+(defvaralias 'erc-receive-query-display 'erc-auto-query)
(defcustom erc-auto-query 'window-noselect
"If non-nil, create a query buffer each time you receive a private message.
If the buffer doesn't already exist, it is created.
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 03df72d9500..4edd72aade4 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1014,8 +1014,9 @@ erc-select-read-args
(list :server "irc.libera.chat"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when port matches default TLS port")
(should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
@@ -1023,8 +1024,9 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
(ert-info ("Switches to TLS when URL is ircs://")
(should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
@@ -1032,8 +1034,11 @@ erc-select-read-args
(list :server "irc.gnu.org"
:port 6697
:nick (user-login-name)
- '&interactive-env '((erc-server-connect-function
- . erc-open-tls-stream))))))
+ '&interactive-env
+ '((erc-server-connect-function . erc-open-tls-stream)
+ (erc-join-buffer . buffer))))))
+
+ (setq-local erc-interactive-display nil) ; cheat to save space
(ert-info ("Opt out of non-TLS warning manually")
(should (equal (ert-simulate-keys "\r\r\r\rn\r"
@@ -1099,7 +1104,8 @@ erc-tls
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
(lambda (&rest r)
- (push `((erc-server-connect-function
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
,erc-server-connect-function))
env)
(push r calls))))
@@ -1110,7 +1116,8 @@ erc-tls
'("irc.libera.chat" 6697 "tester" "unknown" t
nil nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Full")
(erc-tls :server "irc.gnu.org"
@@ -1125,7 +1132,8 @@ erc-tls
'("irc.gnu.org" 7000 "bob" "Bob's Name" t
"bob:changeme" nil nil nil t "bobo" GNU.org)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
;; Values are often nil when called by lisp code, which leads to
;; null params. This is why `erc-open' recomputes almost
@@ -1143,7 +1151,8 @@ erc-tls
'(nil 7000 nil "Bob's Name" t
"bob:changeme" nil nil nil nil "bobo" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Interactive")
(ert-simulate-keys "nick:sesame@localhost:6667\r\r"
@@ -1152,8 +1161,8 @@ erc-tls
'("localhost" 6667 "nick" "unknown" t "sesame"
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function
- erc-open-tls-stream)))))
+ '((erc-join-buffer buffer)
+ (erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Custom connect function")
(let ((erc-server-connect-function 'my-connect-func))
@@ -1162,7 +1171,8 @@ erc-tls
'("irc.libera.chat" 6697 "tester" "unknown" t
nil nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function my-connect-func))))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function my-connect-func))))))
(ert-info ("Advised default function overlooked") ; intentional
(advice-add 'erc-server-connect-function :around #'ignore
@@ -1172,7 +1182,8 @@ erc-tls
'("irc.libera.chat" 6697 "tester" "unknown" t
nil nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream))))
+ '((erc-join-buffer bury)
+ (erc-server-connect-function erc-open-tls-stream))))
(advice-remove 'erc-server-connect-function 'erc-tests--erc-tls))
(ert-info ("Advised non-default function honored")
@@ -1184,7 +1195,8 @@ erc-tls
(should (equal (pop calls)
'("irc.libera.chat" 6697 "tester" "unknown" t
nil nil nil nil nil "user" nil)))
- (should (equal (pop env) `((erc-server-connect-function ,f))))
+ (should (equal (pop env) `((erc-join-buffer bury)
+ (erc-server-connect-function ,f))))
(advice-remove 'erc-server-connect-function
'erc-tests--erc-tls)))))))
@@ -1197,7 +1209,8 @@ erc--interactive
(lambda (&optional _) "tester"))
((symbol-function 'erc-open)
(lambda (&rest r)
- (push `((erc-server-connect-function
+ (push `((erc-join-buffer ,erc-join-buffer)
+ (erc-server-connect-function
,erc-server-connect-function))
env)
(push r calls))))
@@ -1209,7 +1222,8 @@ erc--interactive
'("irc.libera.chat" 6697 "tester" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-server-connect-function erc-open-tls-stream)))))
+ '((erc-join-buffer buffer) (erc-server-connect-function
+ erc-open-tls-stream)))))
(ert-info ("Nick supplied, decline TLS upgrade")
(ert-simulate-keys "\r\rdummy\r\rn\r"
@@ -1218,7 +1232,7 @@ erc--interactive
'("irc.libera.chat" 6667 "dummy" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '(
+ '((erc-join-buffer buffer)
(erc-server-connect-function
erc-open-network-stream))))))))
--
2.39.1
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #5: 0003-5.6-Optionally-prompt-for-more-ERC-entry-point-param.patch --]
[-- Type: text/x-patch, Size: 6507 bytes --]
From c348a0162a84f97627bb7b9b613d6c88a12a03e7 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Thu, 29 Dec 2022 06:43:19 -0800
Subject: [PATCH 3/3] [5.6] Optionally prompt for more ERC entry-point params
* doc/misc/erc.texi: Update statement about availability of user param
when entry points called interactively.
* lisp/erc/erc/compat.el: Don't require `url-parse' when compiling.
Add forward declaration for `url-type'.
* lisp/erc/erc.el: Don't require `url-parse' when compiling. Add
forward declarations for url accessors of url struct from url-parse
library.
(erc-select-read-args): Allow optionally calling
entry points with a prefix arg to access params `user' and
`:full-name'.
(erc-tls): Update doc string.
* test/lisp/erc/erc-tests.el (erc-select-read-args): Add test for
extra args. (Bug#60428.)
---
doc/misc/erc.texi | 2 +-
lisp/erc/erc-compat.el | 3 ++-
lisp/erc/erc.el | 28 +++++++++++++++++++++-------
test/lisp/erc/erc-tests.el | 13 ++++++++++++-
4 files changed, 36 insertions(+), 10 deletions(-)
diff --git a/doc/misc/erc.texi b/doc/misc/erc.texi
index d5ec0f48e1c..d60d7fc8f2d 100644
--- a/doc/misc/erc.texi
+++ b/doc/misc/erc.texi
@@ -952,7 +952,7 @@ SASL
your @samp{NickServ} password. To make this work, customize
@code{erc-sasl-user} and @code{erc-sasl-password} or specify the
@code{:user} and @code{:password} keyword arguments when invoking
-@code{erc-tls}. Note that @code{:user} cannot be given interactively.
+@code{erc-tls}.
@item @code{external} (via Client TLS Certificate)
This works in conjunction with the @code{:client-certificate} keyword
diff --git a/lisp/erc/erc-compat.el b/lisp/erc/erc-compat.el
index 5601ede27a5..d475d9cf458 100644
--- a/lisp/erc/erc-compat.el
+++ b/lisp/erc/erc-compat.el
@@ -32,7 +32,7 @@
;;; Code:
(require 'compat nil 'noerror)
-(eval-when-compile (require 'cl-lib) (require 'url-parse))
+(eval-when-compile (require 'cl-lib))
;;;###autoload(autoload 'erc-define-minor-mode "erc-compat")
(define-obsolete-function-alias 'erc-define-minor-mode
@@ -378,6 +378,7 @@ erc-compat--with-memoization
(t `(progn ,@forms))))
(defvar url-irc-function)
+(declare-function url-type "url-parse" (cl-x))
(defun erc-compat--29-browse-url-irc (string &rest _)
(require 'url-irc)
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 9dbca09bb35..f1a51341924 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -69,7 +69,7 @@
(require 'auth-source)
(require 'time-date)
(require 'iso8601)
-(eval-when-compile (require 'subr-x) (require 'url-parse))
+(eval-when-compile (require 'subr-x))
(defconst erc-version "5.4.1"
"This version of ERC.")
@@ -139,6 +139,12 @@ tabbar--local-hlf
(defvar motif-version-string)
(defvar gtk-version-string)
+(declare-function url-host "url-parse" (cl-x))
+(declare-function url-password "url-parse" (cl-x))
+(declare-function url-portspec "url-parse" (cl-x))
+(declare-function url-type "url-parse" (cl-x))
+(declare-function url-user "url-parse" (cl-x))
+
;; tunable connection and authentication parameters
(defcustom erc-server nil
@@ -2192,8 +2198,8 @@ erc--ensure-url
;;;###autoload
(defun erc-select-read-args ()
- "Prompt the user for values of nick, server, port, and password."
- (require 'url-parse)
+ "Prompt the user for values of nick, server, port, and password.
+With prefix arg, also prompt for user and full name."
(let* ((input (let ((d (erc-compute-server)))
(read-string (format "Server or URL (default is %S): " d)
nil 'erc-server-history-list d)))
@@ -2213,6 +2219,14 @@ erc-select-read-args
(let ((d (erc-compute-nick)))
(read-string (format "Nickname (default is %S): " d)
nil 'erc-nick-history-list d))))
+ (user (and current-prefix-arg
+ (let ((d (erc-compute-user (url-user url))))
+ (read-string (format "User (default is %S): " d)
+ nil nil d))))
+ (full (and current-prefix-arg
+ (let ((d (erc-compute-full-name (url-user url))))
+ (read-string (format "Full name (default is %S): " d)
+ nil nil d))))
(passwd (let* ((p (with-suppressed-warnings ((obsolete erc-password))
(or (url-password url) erc-password)))
(m (if p
@@ -2233,8 +2247,8 @@ erc-select-read-args
(push `(erc-server-connect-function . ,opener) env))
(when (and passwd (string= "" passwd))
(setq passwd nil))
- `( :server ,server :port ,port :nick ,nick
- ,@(and passwd `(:password ,passwd))
+ `( :server ,server :port ,port :nick ,nick ,@(and user `(:user ,user))
+ ,@(and passwd `(:password ,passwd)) ,@(and full `(:full-name ,full))
,@(and env `(&interactive-env ,env)))))
(defmacro erc--with-entrypoint-environment (env &rest body)
@@ -2342,8 +2356,8 @@ erc-tls
When present, ID should be a symbol or a string to use for naming
the server buffer and identifying the connection unequivocally.
-See Info node `(erc) Network Identifier' for details. Like USER
-and CLIENT-CERTIFICATE, this parameter cannot be specified
+See Info node `(erc) Network Identifier' for details. Like
+CLIENT-CERTIFICATE, this parameter cannot be specified
interactively.
\(fn &key SERVER PORT NICK USER PASSWORD FULL-NAME CLIENT-CERTIFICATE ID)"
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 4edd72aade4..68b4413da44 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1096,7 +1096,18 @@ erc-select-read-args
(erc-select-read-args))
(list :server "[::1]"
:port 6667
- :nick "nick")))))
+ :nick "nick"))))
+
+ (ert-info ("Extra args use URL nick by default")
+ (should (equal (ert-simulate-keys "nick:sesame@localhost:6667\r\r\r\r"
+ (let ((current-prefix-arg '(4)))
+ (erc-select-read-args)))
+ (list :server "localhost"
+ :port 6667
+ :nick "nick"
+ :user "nick"
+ :password "sesame"
+ :full-name "nick")))))
(ert-deftest erc-tls ()
(let (calls env)
--
2.39.1
^ permalink raw reply related [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] ` <87h6vhwv9u.fsf@neverwas.me>
@ 2023-04-08 23:06 ` J.P.
0 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-04-08 23:06 UTC (permalink / raw)
To: 60428-done; +Cc: emacs-erc
"J.P." <jp@neverwas.me> writes:
> v4. Stop requiring `url-parse' library when compiling. Improve test.
Despite pleas from at least one person, I've decided against expanding
this patch to allow for specifying a client certificate interactively
(patches welcome, however). For now, users can add per-server certs via
auth-source. Thanks and closing.
^ permalink raw reply [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] <87mt750ygt.fsf@neverwas.me>
` (4 preceding siblings ...)
[not found] ` <87h6vhwv9u.fsf@neverwas.me>
@ 2023-04-11 3:29 ` J.P.
[not found] ` <874jpnqeoc.fsf@neverwas.me>
6 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-04-11 3:29 UTC (permalink / raw)
To: 60428; +Cc: emacs-erc
[-- Attachment #1: Type: text/plain, Size: 865 bytes --]
Reopening.
This bug's original patch set tried to walk back an austere aspect of
bug#51753's changes that lumped interactive buffer creation in with
protocol driven creation. It mainly did so by introducing a new option,
`erc-interactive-display', that reinstated direct window-buffer
replacement when running M-x erc. However, as pointed out by Corwin on
Libera, this did not account for interactive /JOINs.
The attached patch aims to address this oversight as well as simplify
the display-options picture a bit further by consolidating the roles of
`erc-interactive-display' and `erc-query-display'. The thinking is that
both options cover the same basic ground involving buffers created as a
consequence of issuing slash commands. This patch also adds an interface
for other such commands to use for detecting when they're being called
from the command line.
[-- Warning: decoded text below may be mangled, UTF-8 assumed --]
[-- Attachment #2: 0001-5.6-Extend-erc-interactive-display-to-cover-JOINs.patch --]
[-- Type: text/x-patch, Size: 20261 bytes --]
From 3658e117ca66a11ef8bc4a071e98c1d0130c3101 Mon Sep 17 00:00:00 2001
From: "F. Jason Park" <jp@neverwas.me>
Date: Mon, 10 Apr 2023 17:58:05 -0700
Subject: [PATCH] [5.6] Extend erc-interactive-display to cover /JOINs
* lisp/erc/erc.el (erc-buffer-display, erc-join-buffer): Swap alias
and aliased so that `erc-buffer-display' appears in Customize.
(erc-query-display, erc-interactive-display): Make former an alias for
latter because they're redundant and quite possibly confusing. Change
the default value to match the longstanding default of
`erc-query-display' because it has seniority.
(erc--called-as-input-p): New variable for "slash"
commands, like `erc-cmd-FOO', to detect whether they're being called
"interactively" as a result of input given at ERC's prompt.
(erc-process-input-line): Bind `erc--called-as-input-p' when running
slash commands.
(erc-cmd-JOIN): Schedule callback to control how new buffer is
displayed when called interactively.
* test/lisp/erc/erc-scenarios-base-buffer-display.el: New file.
* test/lisp/erc/erc-scenarios-base-reconnect.el
(erc-scenarios-common--base-reconnect-options,
ert-deftest erc-scenarios-base-reconnect-options--buffer,
erc-scenarios-base-reconnect-options--default): Move to new file
erc-scenarios-base-buffer-display.el and rename.
* test/lisp/erc/erc-tests.el (erc-select-read-args, erc-tls,
erc--interactive): Change expected default value of
`erc-interactive-display' from `buffer' to `window'. (Bug#60428.)
---
lisp/erc/erc.el | 61 ++++---
.../erc/erc-scenarios-base-buffer-display.el | 158 ++++++++++++++++++
test/lisp/erc/erc-scenarios-base-reconnect.el | 89 ----------
test/lisp/erc/erc-tests.el | 12 +-
4 files changed, 200 insertions(+), 120 deletions(-)
create mode 100644 test/lisp/erc/erc-scenarios-base-buffer-display.el
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 284990e2d43..a3a9b03a93c 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -1507,8 +1507,8 @@ erc-default-port-tls
"IRC port to use for encrypted connections if it cannot be \
detected otherwise.")
-(defvaralias 'erc-buffer-display 'erc-join-buffer)
-(defcustom erc-join-buffer 'bury
+(defvaralias 'erc-join-buffer 'erc-buffer-display)
+(defcustom erc-buffer-display 'bury
"Determines how to display a newly created IRC buffer.
The available choices are:
@@ -1528,13 +1528,21 @@ erc-join-buffer
(const :tag "Use current buffer" buffer)
(const :tag "Use current buffer" t)))
-(defcustom erc-interactive-display 'buffer
- "How and whether to display server buffers for M-x erc.
-See `erc-buffer-display' and friends for a description of
-possible values."
+(defvaralias 'erc-query-display 'erc-interactive-display)
+(defcustom erc-interactive-display 'window
+ "How to display buffers created by issuing a /SLASH command.
+Examples include /QUERY and /JOIN. See `erc-buffer-display' for
+a full description of available choices.
+
+Note that this does not affect the behavior of commands like
+`erc-cmd-JOIN' when called from lisp code. Also, this option
+used to be called `erc-query-display' but now applies to more
+than just /QUERY. See option `erc-receive-query-display' in the
+Custom group `erc-query' to decide how private messages from
+other people should be displayed."
:package-version '(ERC . "5.6") ; FIXME sync on release
:group 'erc-buffers
- :type '(choice (const :tag "Use value of `erc-join-buffer'" nil)
+ :type '(choice (const :tag "Use value of `erc-buffer-display'" nil)
(const :tag "Split window and select" window)
(const :tag "Split window, don't select" window-noselect)
(const :tag "New frame" frame)
@@ -3057,6 +3065,10 @@ erc-message-type-member
(let ((prop-val (erc-get-parsed-vector position)))
(and prop-val (member (erc-response.command prop-val) list))))
+(defvar erc--called-as-input-p nil
+ "Non-nil when a user types a \"/slash\" command.
+Remains bound until `erc-cmd-SLASH' returns.")
+
(defvar-local erc-send-input-line-function 'erc-send-input-line
"Function for sending lines lacking a leading user command.
When a line typed into a buffer contains an explicit command, like /msg,
@@ -3110,7 +3122,8 @@ erc-process-input-line
(if (and command-list
(not no-command))
(let* ((cmd (nth 0 command-list))
- (args (nth 1 command-list)))
+ (args (nth 1 command-list))
+ (erc--called-as-input-p t))
(condition-case nil
(if (listp args)
(apply cmd args)
@@ -3584,6 +3597,21 @@ erc-cmd-JOIN
(erc-get-channel-user (erc-current-nick)))))
(switch-to-buffer existing)
(setq erc--server-last-reconnect-count 0)
+ (when-let* ; bind `erc-join-buffer' when /JOIN issued
+ ((erc--called-as-input-p)
+ (fn (lambda (proc parsed)
+ (when-let* ; `fn' wrapper already removed from hook
+ (((equal (car (erc-response.command-args parsed))
+ channel))
+ (sn (erc-extract-nick (erc-response.sender parsed)))
+ ((erc-nick-equal-p sn (erc-current-nick)))
+ (erc-join-buffer (or erc-interactive-display
+ erc-join-buffer)))
+ (run-hook-with-args-until-success
+ 'erc-server-JOIN-functions proc parsed)
+ t))))
+ (erc-with-server-buffer
+ (erc-once-with-server-event "JOIN" fn)))
(erc-server-join-channel nil chnl key))))
t)
@@ -3947,23 +3975,6 @@ erc-cmd-QUOTE
(t nil)))
(put 'erc-cmd-QUOTE 'do-not-parse-args t)
-(defcustom erc-query-display 'window
- "How to display query buffers when using the /QUERY command to talk to someone.
-
-The default behavior is to display the message in a new window
-and bring it to the front. See the documentation for
-`erc-join-buffer' for a description of the available choices.
-
-See also `erc-auto-query' to decide how private messages from
-other people should be displayed."
- :group 'erc-query
- :type '(choice (const :tag "Split window and select" window)
- (const :tag "Split window, don't select" window-noselect)
- (const :tag "New frame" frame)
- (const :tag "Bury in new buffer" bury)
- (const :tag "Use current buffer" buffer)
- (const :tag "Use current buffer" t)))
-
(defun erc-cmd-QUERY (&optional user)
"Open a query with USER.
How the query is displayed (in a new window, frame, etc.) depends
diff --git a/test/lisp/erc/erc-scenarios-base-buffer-display.el b/test/lisp/erc/erc-scenarios-base-buffer-display.el
new file mode 100644
index 00000000000..3ed7a83653e
--- /dev/null
+++ b/test/lisp/erc/erc-scenarios-base-buffer-display.el
@@ -0,0 +1,158 @@
+;;; erc-scenarios-base-buffer-display.el --- Buffer display scenarios -*- lexical-binding: t -*-
+
+;; Copyright (C) 2023 Free Software Foundation, Inc.
+
+;; This file is part of GNU Emacs.
+
+;; GNU Emacs 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.
+
+;; GNU Emacs 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 GNU Emacs. If not, see <https://www.gnu.org/licenses/>.
+
+;;; Code:
+
+(require 'ert-x)
+(eval-and-compile
+ (let ((load-path (cons (ert-resource-directory) load-path)))
+ (require 'erc-scenarios-common)))
+
+(eval-when-compile (require 'erc-join))
+
+;; These first couple `erc-reconnect-display' tests used to live in
+;; erc-scenarios-base-reconnect but have since been renamed.
+
+(defun erc-scenarios-base-buffer-display--reconnect-common (test)
+ (erc-scenarios-common-with-cleanup
+ ((erc-scenarios-common-dialog "base/reconnect")
+ (dumb-server (erc-d-run "localhost" t 'options 'options-again))
+ (port (process-contact dumb-server :service))
+ (expect (erc-d-t-make-expecter))
+ (erc-server-flood-penalty 0.1)
+ (erc-server-auto-reconnect t)
+ erc-autojoin-channels-alist
+ erc-server-buffer)
+
+ (should (memq 'autojoin erc-modules))
+
+ (ert-info ("Connect to foonet")
+ (setq erc-server-buffer (erc :server "127.0.0.1"
+ :port port
+ :nick "tester"
+ :password "changeme"
+ :full-name "tester"))
+ (with-current-buffer erc-server-buffer
+ (should (string= (buffer-name) (format "127.0.0.1:%d" port)))
+ (funcall expect 10 "debug mode")))
+
+ (ert-info ("Wait for some output in channels")
+ (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#chan"))
+ (funcall expect 10 "welcome")))
+
+ (ert-info ("Server buffer shows connection failed")
+ (with-current-buffer erc-server-buffer
+ (funcall expect 10 "Connection failed! Re-establishing")))
+
+ (should (equal erc-autojoin-channels-alist '((FooNet "#chan"))))
+
+ (funcall test)
+
+ ;; A manual /JOIN command tells ERC we're done auto-reconnecting
+ (with-current-buffer "FooNet" (erc-cmd-JOIN "#spam"))
+
+ (erc-d-t-ensure-for 1 "Newly joined chan ignores `erc-reconnect-display'"
+ (not (eq (window-buffer) (get-buffer "#spam"))))
+
+ (ert-info ("Wait for auto reconnect")
+ (with-current-buffer erc-server-buffer
+ (funcall expect 10 "still in debug mode")))
+
+ (ert-info ("Wait for activity to recommence in channels")
+ (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#chan"))
+ (funcall expect 10 "forest of Arden"))
+ (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#spam"))
+ (funcall expect 10 "her elves come here anon")))))
+
+(ert-deftest erc-scenarios-base-reconnect-options--buffer ()
+ :tags '(:expensive-test)
+ (should (eq erc-join-buffer 'bury))
+ (should-not erc-reconnect-display)
+
+ ;; FooNet (the server buffer) is not switched to because it's
+ ;; already current (but not shown) when `erc-open' is called. See
+ ;; related conditional guard towards the end of that function.
+
+ (let ((erc-reconnect-display 'buffer))
+ (erc-scenarios-base-buffer-display--reconnect-common
+ (lambda ()
+ (pop-to-buffer-same-window "*Messages*")
+
+ (erc-d-t-ensure-for 1 "Server buffer not shown"
+ (not (eq (window-buffer) (get-buffer "FooNet"))))
+
+ (erc-d-t-wait-for 5 "Channel #chan shown when autojoined"
+ (eq (window-buffer) (get-buffer "#chan")))))))
+
+(ert-deftest erc-scenarios-base-reconnect-options--default ()
+ :tags '(:expensive-test)
+ (should (eq erc-join-buffer 'bury))
+ (should-not erc-reconnect-display)
+
+ (erc-scenarios-base-buffer-display--reconnect-common
+
+ (lambda ()
+ (pop-to-buffer-same-window "*Messages*")
+
+ (erc-d-t-ensure-for 1 "Server buffer not shown"
+ (not (eq (window-buffer) (get-buffer "FooNet"))))
+
+ (erc-d-t-ensure-for 3 "Channel #chan not shown"
+ (not (eq (window-buffer) (get-buffer "#chan"))))
+
+ (should (eq (window-buffer) (messages-buffer))))))
+
+
+;; This shows that the option `erc-interactive-display' overrides
+;; `erc-join-buffer' during cold opens and interactive /JOINs.
+
+(ert-deftest erc-scenarios-base-buffer-display--interactive-default ()
+ :tags '(:expensive-test)
+ (should (eq erc-join-buffer 'bury))
+ (should (eq erc-interactive-display 'window))
+
+ (erc-scenarios-common-with-cleanup
+ ((erc-scenarios-common-dialog "join/legacy")
+ (dumb-server (erc-d-run "localhost" t 'foonet))
+ (port (process-contact dumb-server :service))
+ (url (format "tester:changeme@127.0.0.1:%d\r\r" port))
+ (expect (erc-d-t-make-expecter))
+ (erc-server-flood-penalty 0.1)
+ (erc-server-auto-reconnect t)
+ (erc-user-full-name "tester"))
+
+ (ert-info ("Connect to foonet")
+ (with-current-buffer (let (inhibit-interaction)
+ (ert-simulate-keys url
+ (call-interactively #'erc)))
+ (should (string= (buffer-name) (format "127.0.0.1:%d" port)))
+
+ (erc-d-t-wait-for 10 "Server buffer shown"
+ (eq (window-buffer) (current-buffer)))
+ (funcall expect 10 "debug mode")
+ (erc-scenarios-common-say "/JOIN #chan")))
+
+ (ert-info ("Wait for output in #chan")
+ (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#chan"))
+ (funcall expect 10 "welcome")
+ (erc-d-t-ensure-for 3 "Channel #chan shown"
+ (eq (window-buffer) (current-buffer)))
+ (funcall expect 10 "be prosperous")))))
+
+;;; erc-scenarios-base-buffer-display.el ends here
diff --git a/test/lisp/erc/erc-scenarios-base-reconnect.el b/test/lisp/erc/erc-scenarios-base-reconnect.el
index 5b4dc549042..7bd16d1ed14 100644
--- a/test/lisp/erc/erc-scenarios-base-reconnect.el
+++ b/test/lisp/erc/erc-scenarios-base-reconnect.el
@@ -65,95 +65,6 @@ erc-scenarios-base-reconnect-timer
(should (equal (list (get-buffer (format "127.0.0.1:%d" port)))
(erc-scenarios-common-buflist "127.0.0.1"))))))
-(defun erc-scenarios-common--base-reconnect-options (test)
- (erc-scenarios-common-with-cleanup
- ((erc-scenarios-common-dialog "base/reconnect")
- (dumb-server (erc-d-run "localhost" t 'options 'options-again))
- (port (process-contact dumb-server :service))
- (expect (erc-d-t-make-expecter))
- (erc-server-flood-penalty 0.1)
- (erc-server-auto-reconnect t)
- erc-autojoin-channels-alist
- erc-server-buffer)
-
- (should (memq 'autojoin erc-modules))
-
- (ert-info ("Connect to foonet")
- (setq erc-server-buffer (erc :server "127.0.0.1"
- :port port
- :nick "tester"
- :password "changeme"
- :full-name "tester"))
- (with-current-buffer erc-server-buffer
- (should (string= (buffer-name) (format "127.0.0.1:%d" port)))
- (funcall expect 10 "debug mode")))
-
- (ert-info ("Wait for some output in channels")
- (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#chan"))
- (funcall expect 10 "welcome")))
-
- (ert-info ("Server buffer shows connection failed")
- (with-current-buffer erc-server-buffer
- (funcall expect 10 "Connection failed! Re-establishing")))
-
- (should (equal erc-autojoin-channels-alist '((FooNet "#chan"))))
-
- (funcall test)
-
- ;; A manual /JOIN command tells ERC we're done auto-reconnecting
- (with-current-buffer "FooNet" (erc-cmd-JOIN "#spam"))
-
- (erc-d-t-ensure-for 1 "Newly joined chan ignores `erc-reconnect-display'"
- (not (eq (window-buffer) (get-buffer "#spam"))))
-
- (ert-info ("Wait for auto reconnect")
- (with-current-buffer erc-server-buffer
- (funcall expect 10 "still in debug mode")))
-
- (ert-info ("Wait for activity to recommence in channels")
- (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#chan"))
- (funcall expect 10 "forest of Arden"))
- (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#spam"))
- (funcall expect 10 "her elves come here anon")))))
-
-(ert-deftest erc-scenarios-base-reconnect-options--buffer ()
- :tags '(:expensive-test)
- (should (eq erc-join-buffer 'bury))
- (should-not erc-reconnect-display)
-
- ;; FooNet (the server buffer) is not switched to because it's
- ;; already current (but not shown) when `erc-open' is called. See
- ;; related conditional guard towards the end of that function.
-
- (let ((erc-reconnect-display 'buffer))
- (erc-scenarios-common--base-reconnect-options
- (lambda ()
- (pop-to-buffer-same-window "*Messages*")
-
- (erc-d-t-ensure-for 1 "Server buffer not shown"
- (not (eq (window-buffer) (get-buffer "FooNet"))))
-
- (erc-d-t-wait-for 5 "Channel #chan shown when autojoined"
- (eq (window-buffer) (get-buffer "#chan")))))))
-
-(ert-deftest erc-scenarios-base-reconnect-options--default ()
- :tags '(:expensive-test)
- (should (eq erc-join-buffer 'bury))
- (should-not erc-reconnect-display)
-
- (erc-scenarios-common--base-reconnect-options
-
- (lambda ()
- (pop-to-buffer-same-window "*Messages*")
-
- (erc-d-t-ensure-for 1 "Server buffer not shown"
- (not (eq (window-buffer) (get-buffer "FooNet"))))
-
- (erc-d-t-ensure-for 3 "Channel #chan not shown"
- (not (eq (window-buffer) (get-buffer "#chan"))))
-
- (eq (window-buffer) (messages-buffer)))))
-
;; Upon reconnecting, playback for channel and target buffers is
;; routed correctly. Autojoin is irrelevant here, but for the
;; skeptical, see `erc-scenarios-common--join-network-id', which
diff --git a/test/lisp/erc/erc-tests.el b/test/lisp/erc/erc-tests.el
index 29bda7e742d..b516b885895 100644
--- a/test/lisp/erc/erc-tests.el
+++ b/test/lisp/erc/erc-tests.el
@@ -1469,7 +1469,7 @@ erc-select-read-args
:nick (user-login-name)
'&interactive-env
'((erc-server-connect-function . erc-open-tls-stream)
- (erc-join-buffer . buffer))))))
+ (erc-join-buffer . window))))))
(ert-info ("Switches to TLS when port matches default TLS port")
(should (equal (ert-simulate-keys "irc.gnu.org\r6697\r\r\r"
@@ -1479,7 +1479,7 @@ erc-select-read-args
:nick (user-login-name)
'&interactive-env
'((erc-server-connect-function . erc-open-tls-stream)
- (erc-join-buffer . buffer))))))
+ (erc-join-buffer . window))))))
(ert-info ("Switches to TLS when URL is ircs://")
(should (equal (ert-simulate-keys "ircs://irc.gnu.org\r\r\r\r"
@@ -1489,7 +1489,7 @@ erc-select-read-args
:nick (user-login-name)
'&interactive-env
'((erc-server-connect-function . erc-open-tls-stream)
- (erc-join-buffer . buffer))))))
+ (erc-join-buffer . window))))))
(setq-local erc-interactive-display nil) ; cheat to save space
@@ -1625,7 +1625,7 @@ erc-tls
'("localhost" 6667 "nick" "unknown" t "sesame"
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-join-buffer buffer)
+ '((erc-join-buffer window)
(erc-server-connect-function erc-open-tls-stream)))))
(ert-info ("Custom connect function")
@@ -1686,7 +1686,7 @@ erc--interactive
'("irc.libera.chat" 6697 "tester" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-join-buffer buffer) (erc-server-connect-function
+ '((erc-join-buffer window) (erc-server-connect-function
erc-open-tls-stream)))))
(ert-info ("Nick supplied, decline TLS upgrade")
@@ -1696,7 +1696,7 @@ erc--interactive
'("irc.libera.chat" 6667 "dummy" "unknown" t nil
nil nil nil nil "user" nil)))
(should (equal (pop env)
- '((erc-join-buffer buffer)
+ '((erc-join-buffer window)
(erc-server-connect-function
erc-open-network-stream))))))))
--
2.39.2
^ permalink raw reply related [flat|nested] 7+ messages in thread
* bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point
[not found] ` <874jpnqeoc.fsf@neverwas.me>
@ 2023-04-14 14:01 ` J.P.
0 siblings, 0 replies; 7+ messages in thread
From: J.P. @ 2023-04-14 14:01 UTC (permalink / raw)
To: 60428-done; +Cc: emacs-erc
Since this discussion is now focused entirely on buffer-display options,
I've moved it to a new bug that will also serve as a follow-on to
bug#51753: "ERC switches to channel buffer on reconnect"
Please direct any responses to
bug#62833: 30.0.50; ERC 5.6: Rethink buffer-display options and behavior
Thanks.
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2023-04-14 14:01 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
[not found] <87mt750ygt.fsf@neverwas.me>
2023-01-02 1:41 ` bug#60428: 29.0.60; ERC 5.4.1: Fix default-port regression in erc-select-read-args J.P.
[not found] ` <87h6x9yapz.fsf@neverwas.me>
2023-01-19 14:18 ` bug#60428: 30.0.50; ERC >5.5: Make M-x erc a more welcoming entry point J.P.
2023-02-07 15:21 ` J.P.
2023-02-19 15:05 ` J.P.
[not found] ` <87h6vhwv9u.fsf@neverwas.me>
2023-04-08 23:06 ` J.P.
2023-04-11 3:29 ` J.P.
[not found] ` <874jpnqeoc.fsf@neverwas.me>
2023-04-14 14:01 ` J.P.
Code repositories for project(s) associated with this external index
https://git.savannah.gnu.org/cgit/emacs.git
https://git.savannah.gnu.org/cgit/emacs/org-mode.git
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.