emacs-diffs
[Top][All Lists]
Advanced

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

master 8c0c9826844 08/37: Add hook to regain nickname in ERC


From: F. Jason Park
Subject: master 8c0c9826844 08/37: Add hook to regain nickname in ERC
Date: Sat, 8 Apr 2023 17:31:28 -0400 (EDT)

branch: master
commit 8c0c98268440b27a77faf30738dfd72c909bb33f
Author: F. Jason Park <jp@neverwas.me>
Commit: F. Jason Park <jp@neverwas.me>

    Add hook to regain nickname in ERC
    
    * lisp/erc/erc-backend.el (erc-server-reconnect-timeout): Mention
    `erc-nickname-in-use-functions' in doc string.
    * lisp/erc/erc.el (erc-nickname-in-use-functions,
    erc-regain-nick-on-connect): Add abnormal hook and possible value to
    handle stale connections preventing a desired nick from being reissued
    by the server.  Follows directly from bug#62044.
    (erc-nickname-in-use): Call `erc-nickname-in-use-functions'.
    * test/lisp/erc/erc-scenarios-base-renick.el
    (erc-scenarios-base-renick-auto-regain): New test.
    * test/lisp/erc/resources/base/renick/regain/normal-again.eld: New file.
    * test/lisp/erc/resources/base/renick/regain/normal.eld: New file.
---
 lisp/erc/erc-backend.el                            |  4 +-
 lisp/erc/erc.el                                    | 47 ++++++++++++++++++
 test/lisp/erc/erc-scenarios-base-renick.el         | 43 +++++++++++++++++
 .../resources/base/renick/regain/normal-again.eld  | 56 ++++++++++++++++++++++
 .../erc/resources/base/renick/regain/normal.eld    | 53 ++++++++++++++++++++
 5 files changed, 202 insertions(+), 1 deletion(-)

diff --git a/lisp/erc/erc-backend.el b/lisp/erc/erc-backend.el
index acfbe3ef3a6..84d6b8a7efd 100644
--- a/lisp/erc/erc-backend.el
+++ b/lisp/erc/erc-backend.el
@@ -418,7 +418,9 @@ This only has an effect if `erc-server-auto-reconnect' is 
non-nil."
 If this value is too low, servers may reject your initial nick
 request upon reconnecting because they haven't yet noticed that
 your previous connection is dead.  If this happens, try setting
-this value to 120 or greater."
+this value to 120 or greater and/or exploring the option
+`erc-nickname-in-use-functions', which may provide a more
+proactive means of handling this situation on some servers."
   :type 'number)
 
 (defcustom erc-server-reconnect-function 'erc-server-delayed-reconnect
diff --git a/lisp/erc/erc.el b/lisp/erc/erc.el
index 66bc4985027..6d35a62518d 100644
--- a/lisp/erc/erc.el
+++ b/lisp/erc/erc.el
@@ -392,6 +392,24 @@ Each function should accept two arguments, NEW-NICK and 
OLD-NICK."
   :group 'erc-hooks
   :type 'hook)
 
+(defcustom erc-nickname-in-use-functions nil
+  "Function to run before trying for a different nickname.
+Called with two arguments: the desired but just rejected nickname
+and the alternate nickname about to be requested.  Use cases
+include special handling during connection registration and
+wrestling with nickname services.  For example, value
+`erc-regain-nick-on-connect' is aimed at dealing with reaping
+lingering connections that may prevent you from being issued a
+requested nick immediately when reconnecting.  It's meant to be
+used with an `erc-server-reconnect-function' value of
+`erc-server-delayed-check-reconnect' alongside SASL
+authentication."
+  :package-version '(ERC . "5.6")
+  :group 'erc-hooks
+  :type '(choice (function-item erc-regain-nick-on-connect)
+                 function
+                 (const nil)))
+
 (defcustom erc-connect-pre-hook '(erc-initialize-log-marker)
   "Hook called just before `erc' calls `erc-connect'.
 Functions are passed a buffer as the first argument."
@@ -4594,6 +4612,34 @@ E.g. \"Read error to Nick [user@some.host]: 110\" would 
be shortened to
         (match-string 1 reason))
       reason))
 
+(defun erc-regain-nick-on-connect (want temp)
+  "Try at most once to grab nickname WANT after settling for TEMP.
+Only do so during connection registration, likely prior to
+authenticating with SASL.  Assume the prior connection was lost
+due to connectivity failure and that the server hasn't yet
+noticed.  Also assume that the server won't process any
+authentication-related messages until it has accepted a mulligan
+nick or at least sent a 433 and thus triggered
+`erc-nickname-in-use-functions'.  Expect authentication to have
+succeeded by the time a logical IRC connection has been
+established and that the contending connection may otherwise
+still be alive and require manual intervention involving
+NickServ."
+  (unless erc-server-connected
+    (letrec ((after-connect
+              (lambda (_ nick)
+                (remove-hook 'erc-after-connect after-connect t)
+                (when (equal temp nick)
+                  (erc-cmd-NICK want))))
+             (on-900
+              (lambda (_ parsed)
+                (remove-hook 'erc-server-900-functions on-900 t)
+                (unless erc-server-connected
+                  (when (equal (car (erc-response.command-args parsed)) temp)
+                    (add-hook 'erc-after-connect after-connect nil t)))
+                nil)))
+      (add-hook 'erc-server-900-functions on-900 nil t))))
+
 (defun erc-nickname-in-use (nick reason)
   "If NICK is unavailable, tell the user the REASON.
 
@@ -4627,6 +4673,7 @@ See also `erc-display-error-notice'."
                                    ;; established a connection yet
                                    (- 9 (length erc-nick-uniquifier))))
                                erc-nick-uniquifier)))
+      (run-hook-with-args 'erc-nickname-in-use-functions nick newnick)
       (erc-cmd-NICK newnick)
       (erc-display-error-notice
        nil
diff --git a/test/lisp/erc/erc-scenarios-base-renick.el 
b/test/lisp/erc/erc-scenarios-base-renick.el
index f1723200533..f8350676fb7 100644
--- a/test/lisp/erc/erc-scenarios-base-renick.el
+++ b/test/lisp/erc/erc-scenarios-base-renick.el
@@ -303,4 +303,47 @@
       (should-not (search-forward "now known as frenemy" nil t))
       (erc-d-t-search-for 25 "I have lost"))))
 
+;; The server rejects your nick during registration, so ERC acquires a
+;; placeholder and successfully renicks once the connection is up.
+;; See also `erc-scenarios-base-renick-self-auto'.
+
+(ert-deftest erc-scenarios-base-renick-auto-regain ()
+  :tags '(:expensive-test)
+  (erc-scenarios-common-with-cleanup
+      ((erc-server-flood-penalty 0.1)
+       (erc-scenarios-common-dialog "base/renick/regain")
+       (dumb-server (erc-d-run "localhost" t 'normal 'normal-again))
+       (port (process-contact dumb-server :service))
+       (erc-server-auto-reconnect t)
+       (erc-modules (cons 'sasl erc-modules))
+       (erc-nickname-in-use-functions '(erc-regain-nick-on-connect))
+       (expect (erc-d-t-make-expecter)))
+
+    (ert-info ("Session succeeds but cut short")
+      (with-current-buffer (erc :server "127.0.0.1"
+                                :port port
+                                :nick "tester"
+                                :user "tester"
+                                :password "changeme"
+                                :full-name "tester")
+        (funcall expect 10 "Last login from")
+        (erc-cmd-JOIN "#test")))
+
+    (with-current-buffer (erc-d-t-wait-for 10 (get-buffer "#test"))
+      (funcall expect 10 "was created on"))
+
+    (ert-info ("Service restored")
+      (with-current-buffer "Libera.Chat"
+        (erc-d-t-wait-for 10 erc--server-reconnect-timer)
+        (funcall expect 10 "Connection failed!")
+        (funcall expect 10 "already in use")
+        (funcall expect 10 "changed mode for tester`")
+        (funcall expect 10 "Last login from")
+        (funcall expect 10 "Your new nickname is tester")))
+
+    (with-current-buffer (get-buffer "#test")
+      (funcall expect 10 "tester ")
+      (funcall expect 10 "was created on"))))
+
+
 ;;; erc-scenarios-base-renick.el ends here
diff --git a/test/lisp/erc/resources/base/renick/regain/normal-again.eld 
b/test/lisp/erc/resources/base/renick/regain/normal-again.eld
new file mode 100644
index 00000000000..c0529052c70
--- /dev/null
+++ b/test/lisp/erc/resources/base/renick/regain/normal-again.eld
@@ -0,0 +1,56 @@
+;; -*- mode: lisp-data; -*-
+((cap 10 "CAP REQ :sasl"))
+((nick 10 "NICK tester"))
+((user 10 "USER tester 0 * :tester"))
+
+((authenticate 10 "AUTHENTICATE PLAIN")
+ (0.04 ":tantalum.libera.chat NOTICE * :*** Checking Ident")
+ (0.01 ":tantalum.libera.chat NOTICE * :*** Looking up your hostname...")
+ (0.01 ":tantalum.libera.chat NOTICE * :*** Couldn't look up your hostname")
+ (0.06 ":tantalum.libera.chat NOTICE * :*** No Ident response")
+ (0.02 ":tantalum.libera.chat CAP * ACK :sasl")
+ (0.03 ":tantalum.libera.chat 433 * tester :Nickname is already in use."))
+
+((nick 10 "NICK tester`")
+ (0.03 "AUTHENTICATE +"))
+
+((authenticate 10 "AUTHENTICATE AHRlc3RlcgBjaGFuZ2VtZQ==")
+ (0.06 ":tantalum.libera.chat 900 tester` tester`!tester@127.0.0.1 tester :You 
are now logged in as tester")
+ (0.02 ":tantalum.libera.chat 903 tester` :SASL authentication successful"))
+
+((cap 10 "CAP END")
+ (0.02 ":tantalum.libera.chat 001 tester` :Welcome to the Libera.Chat Internet 
Relay Chat Network tester`")
+ (0.02 ":tantalum.libera.chat 002 tester` :Your host is 
tantalum.libera.chat[93.158.237.2/6697], running version solanum-1.0-dev")
+ (0.02 ":tantalum.libera.chat 003 tester` :This server was created Mon Feb 13 
2023 at 12:05:04 UTC")
+ (0.01 ":tantalum.libera.chat 004 tester` tantalum.libera.chat solanum-1.0-dev 
DGMQRSZaghilopsuwz CFILMPQRSTbcefgijklmnopqrstuvz bkloveqjfI")
+ (0.01 ":tantalum.libera.chat 005 tester` WHOX MONITOR=100 SAFELIST 
ELIST=CMNTU ETRACE FNC CALLERID=g KNOCK CHANTYPES=# EXCEPTS INVEX 
CHANMODES=eIbq,k,flj,CFLMPQRSTcgimnprstuz :are supported by this server")
+ (0.01 ":tantalum.libera.chat 005 tester` CHANLIMIT=#:250 PREFIX=(ov)@+ 
MAXLIST=bqeI:100 MODES=4 NETWORK=Libera.Chat STATUSMSG=@+ CASEMAPPING=rfc1459 
NICKLEN=16 MAXNICKLEN=16 CHANNELLEN=50 TOPICLEN=390 DEAF=D :are supported by 
this server")
+ (0.03 ":tantalum.libera.chat 005 tester` 
TARGMAX=NAMES:1,LIST:1,KICK:1,WHOIS:1,PRIVMSG:4,NOTICE:4,ACCEPT:,MONITOR: 
EXTBAN=$,ajrxz :are supported by this server")
+ (0.01 ":tantalum.libera.chat 251 tester` :There are 70 users and 42977 
invisible on 28 servers")
+ (0.00 ":tantalum.libera.chat 252 tester` 38 :IRC Operators online")
+ (0.00 ":tantalum.libera.chat 253 tester` 87 :unknown connection(s)")
+ (0.00 ":tantalum.libera.chat 254 tester` 22908 :channels formed")
+ (0.00 ":tantalum.libera.chat 255 tester` :I have 2507 clients and 1 servers")
+ (0.00 ":tantalum.libera.chat 265 tester` 2507 3232 :Current local users 2507, 
max 3232")
+ (0.00 ":tantalum.libera.chat 266 tester` 43047 51777 :Current global users 
43047, max 51777")
+ (0.00 ":tantalum.libera.chat 250 tester` :Highest connection count: 3233 
(3232 clients) (284887 connections received)")
+ (0.03 ":tantalum.libera.chat 375 tester` :- tantalum.libera.chat Message of 
the Day - ")
+ (0.00 ":tantalum.libera.chat 372 tester` :- This server provided by 
Hyperfilter (https://hyperfilter.com)")
+ (0.00 ":tantalum.libera.chat 372 tester` :- Email:                      
support@libera.chat")
+ (0.02 ":tantalum.libera.chat 376 tester` :End of /MOTD command."))
+
+((mode 10 "MODE tester` +i")
+ (0.01 ":tester` MODE tester` :+Ziw")
+ (0.02 ":SaslServ!SaslServ@services.libera.chat NOTICE tester` :Last login 
from: \2~tester@127.0.0.1\2 on Apr 07 01:36:25 2023 +0000."))
+
+((nick 10 "NICK tester")
+ (0.02 ":tester`!~tester@127.0.0.1 NICK :tester"))
+
+((join 10 "JOIN #test")
+ (0.02 ":tester!~tester@127.0.0.1 JOIN #test")
+ (0.02 ":tantalum.libera.chat 353 tester = #test :tester zbyqbepbqre7 
pusevgfpu Thrfg2187 zngbeb qnexNssvavgl wrebzr- rqpentt Ilehf grfg2 AvtugZbaxrl 
pevfgvvbna xrivap_ fnvybePng shohxv gxan arrqyr avpx16 NeanhqW_kzcc jvyyr 
wrnaogeq Wnarg cnefavc0 Xbentt RcvpArb flfqrs wfgbxre hafcrag__ Lbevpx_")
+ (0.02 ":tantalum.libera.chat 366 tester #test :End of /NAMES list."))
+
+((mode 10 "MODE #test")
+ (0.02 ":tantalum.libera.chat 324 tester #test +nt")
+ (0.02 ":tantalum.libera.chat 329 tester #test 1621432263"))
diff --git a/test/lisp/erc/resources/base/renick/regain/normal.eld 
b/test/lisp/erc/resources/base/renick/regain/normal.eld
new file mode 100644
index 00000000000..9f4df70e580
--- /dev/null
+++ b/test/lisp/erc/resources/base/renick/regain/normal.eld
@@ -0,0 +1,53 @@
+;; -*- mode: lisp-data; -*-
+((cap 10 "CAP REQ :sasl"))
+((nick 10 "NICK tester"))
+((user 10 "USER tester 0 * :tester"))
+
+((authenticate 10 "AUTHENTICATE PLAIN")
+ (0.02 ":cadmium.libera.chat NOTICE * :*** Checking Ident")
+ (0.01 ":cadmium.libera.chat NOTICE * :*** Looking up your hostname...")
+ (0.01 ":cadmium.libera.chat NOTICE * :*** Couldn't look up your hostname")
+ (0.06 ":cadmium.libera.chat NOTICE * :*** No Ident response")
+ (0.09 ":cadmium.libera.chat CAP * ACK :sasl")
+ (0.01 "AUTHENTICATE +"))
+
+((authenticate 10 "AUTHENTICATE AHRlc3RlcgBjaGFuZ2VtZQ==")
+ (0.03 ":cadmium.libera.chat 900 tester tester!tester@127.0.0.1 tester :You 
are now logged in as tester")
+ (0.01 ":cadmium.libera.chat 903 tester :SASL authentication successful"))
+
+((cap 10 "CAP END")
+ (0.03 ":cadmium.libera.chat 001 tester :Welcome to the Libera.Chat Internet 
Relay Chat Network tester")
+ (0.02 ":cadmium.libera.chat 002 tester :Your host is 
cadmium.libera.chat[103.196.37.95/6697], running version solanum-1.0-dev")
+ (0.01 ":cadmium.libera.chat 003 tester :This server was created Wed Jan 25 
2023 at 10:22:45 UTC")
+ (0.01 ":cadmium.libera.chat 004 tester cadmium.libera.chat solanum-1.0-dev 
DGMQRSZaghilopsuwz CFILMPQRSTbcefgijklmnopqrstuvz bkloveqjfI")
+ (0.00 ":cadmium.libera.chat 005 tester CALLERID=g WHOX ETRACE FNC SAFELIST 
ELIST=CMNTU KNOCK MONITOR=100 CHANTYPES=# EXCEPTS INVEX 
CHANMODES=eIbq,k,flj,CFLMPQRSTcgimnprstuz :are supported by this server")
+ (0.01 ":cadmium.libera.chat 005 tester CHANLIMIT=#:250 PREFIX=(ov)@+ 
MAXLIST=bqeI:100 MODES=4 NETWORK=Libera.Chat STATUSMSG=@+ CASEMAPPING=rfc1459 
NICKLEN=16 MAXNICKLEN=16 CHANNELLEN=50 TOPICLEN=390 DEAF=D :are supported by 
this server")
+ (0.01 ":cadmium.libera.chat 005 tester 
TARGMAX=NAMES:1,LIST:1,KICK:1,WHOIS:1,PRIVMSG:4,NOTICE:4,ACCEPT:,MONITOR: 
EXTBAN=$,ajrxz :are supported by this server")
+ (0.01 ":cadmium.libera.chat 251 tester :There are 70 users and 42996 
invisible on 28 servers")
+ (0.02 ":cadmium.libera.chat 252 tester 38 :IRC Operators online")
+ (0.01 ":cadmium.libera.chat 253 tester 57 :unknown connection(s)")
+ (0.01 ":cadmium.libera.chat 254 tester 22912 :channels formed")
+ (0.01 ":cadmium.libera.chat 255 tester :I have 2499 clients and 1 servers")
+ (0.01 ":cadmium.libera.chat 265 tester 2499 4187 :Current local users 2499, 
max 4187")
+ (0.01 ":cadmium.libera.chat 266 tester 43066 51827 :Current global users 
43066, max 51827")
+ (0.01 ":cadmium.libera.chat 250 tester :Highest connection count: 4188 (4187 
clients) (319420 connections received)")
+ (0.01 ":cadmium.libera.chat 375 tester :- cadmium.libera.chat Message of the 
Day - ")
+ (0.01 ":cadmium.libera.chat 372 tester :- This server kindly provided by Mach 
Dilemma (www.m-d.net)")
+ (0.01 ":cadmium.libera.chat 372 tester :- Welcome to Libera Chat, the IRC 
network for")
+ (0.00 ":cadmium.libera.chat 372 tester :- Email:                      
support@libera.chat")
+ (0.00 ":cadmium.libera.chat 376 tester :End of /MOTD command.")
+ (0.00 ":tester MODE tester :+Ziw")
+ (0.02 ":SaslServ!SaslServ@services.libera.chat NOTICE tester :Last login 
from: \2~tester@127.0.0.1\2 on Apr 07 01:02:11 2023 +0000."))
+
+((mode 10 "MODE tester +i"))
+
+((join 10 "JOIN #test")
+ (0.09 ":tester!~tester@127.0.0.1 JOIN #test"))
+
+((mode 10 "MODE #test")
+ (0.03 ":cadmium.libera.chat 353 tester = #test :tester zbyqbepbqre7 pusevgfpu 
Thrfg2187 zngbeb qnexNssvavgl wrebzr- rqpentt Ilehf grfg2 AvtugZbaxrl 
pevfgvvbna xrivap_ fnvybePng shohxv gxan arrqyr avpx16 NeanhqW_kzcc Lbevpx_ 
hafcrag__ wfgbxre flfqrs RcvpArb Xbentt jvyyr cnefavc0 Wnarg wrnaogeq")
+ (0.02 ":cadmium.libera.chat 366 tester #test :End of /NAMES list.")
+ (0.00 ":cadmium.libera.chat 324 tester #test +nt")
+ (0.01 ":cadmium.libera.chat 329 tester #test 1621432263"))
+
+((drop 0 DROP))



reply via email to

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