home · contact · privacy
For any NICK_USER_HOST message tokens potentially update entry; get rid of irregular... master
authorChristian Heller <c.heller@plomlompom.de>
Thu, 4 Sep 2025 05:41:31 +0000 (07:41 +0200)
committerChristian Heller <c.heller@plomlompom.de>
Thu, 4 Sep 2025 05:41:31 +0000 (07:41 +0200)
ircplom/client.py
ircplom/msg_parse_expectations.py

index db59a8946405babf53a989e5e4e8b63b376df8c1..e26dd0a1460f4fa248ad9f574977a930a84c07cb 100644 (file)
@@ -519,11 +519,14 @@ class _ClientDb(_UpdatingMixin, SharedClientDbFields):
 
     def userid_for_nickuserhost(self,
                                 nickuserhost: _NickUserHost,
-                                create_if_none=False) -> str:
+                                create_if_none=False,
+                                allow_none=False
+                                ) -> Optional[str]:
         'Return user_id for nickuserhost.nick, create if none, maybe update.'
         matches = [id_ for id_ in self.users.keys()
                    if self.users[id_].nick == nickuserhost.nick]
-        assert len(matches) in ({0, 1} if create_if_none else {1})
+        assert len(matches) in ({0, 1} if (create_if_none or allow_none)
+                                else {1})
         if len(matches) == 1:
             id_ = matches[0]
             if '?' in {nickuserhost.user, nickuserhost.host}:
@@ -531,7 +534,7 @@ class _ClientDb(_UpdatingMixin, SharedClientDbFields):
                 return id_
             stored = self.users[id_]
             if '?' in {stored.user, stored.host}:
-                assert stored.user == stored.host
+                assert stored.host in {stored.user, '?'}
                 self.users.set_updating(id_, nickuserhost)
             else:
                 assert nickuserhost.host == stored.host
@@ -539,9 +542,11 @@ class _ClientDb(_UpdatingMixin, SharedClientDbFields):
                     self.users.set_updating(id_, nickuserhost)
                 else:
                     assert nickuserhost.user == stored.user
-        else:
+        elif create_if_none:
             id_ = str(uuid4())
             self.users.set_updating(id_, nickuserhost)
+        else:
+            return None
         return id_
 
 
@@ -708,12 +713,8 @@ class Client(ABC, ClientQueueMixin):
         if '_verb' not in ret:
             self._log(f'PLEASE IMPLEMENT HANDLER FOR: {msg.raw}')
             return
-        for task, tok_names in [t for t in ret['_tasks'].items()
-                                if t[0].verb == 'set']:
-            assert task.path == ('user',)
-            assert tok_names in (['sender'], ['joiner'])
-            self.db.userid_for_nickuserhost(ret[tok_names[0]],
-                                            create_if_none=True)
+        for nickuserhost in ret['_nickuserhosts']:
+            self.db.userid_for_nickuserhost(nickuserhost, allow_none=True)
         for verb in ('setattr', 'do', 'doafter'):
             for task, tok_names in [t for t in ret['_tasks'].items()
                                     if t[0].verb == verb]:
@@ -772,6 +773,7 @@ class Client(ABC, ClientQueueMixin):
             self.db.channels[ret['channel']].append_nick(ret['joiner'])
         elif ret['_verb'] == 'NICK':
             user_id = self.db.userid_for_nickuserhost(ret['named'])
+            assert user_id is not None
             self.db.users[user_id].nick = ret['nick']
             if user_id == 'me':
                 self.db.nick_wanted = ret['nick']
index 99839023ce299555e62bd788a24e321b6dd274c3..4d372b6337202dd5f944523330c2df44e0ac0b43 100644 (file)
@@ -101,19 +101,23 @@ class _MsgParseExpectation:
         }
         parsed: dict[str, str | tuple[str, ...]] = {}
         singled_tasks: list[tuple[_Command, str]] = []
+        nickuserhosts = []
         for ex_tok, cmp_tok in [(ex_tok, cmp_fields[idx])
                                 for idx, ex_tok in enumerate(ex_fields)]:
             if (not isinstance(ex_tok.type_, str))\
                     and ex_tok.type_ in validators\
                     and (not validators[ex_tok.type_](cmp_tok)):
                 return None
-            if ex_tok.code:
-                parsed[ex_tok.code.title] = (
-                        cmp_tok if (isinstance(ex_tok.type_, str)
-                                    or ex_tok.type_ not in parsers)
-                        else parsers[ex_tok.type_](cmp_tok))
-                singled_tasks += [(cmd, ex_tok.code.title)
-                                  for cmd in ex_tok.code.commands]
+            if ex_tok.code or ex_tok.type_ is _MsgTok.NICK_USER_HOST:
+                value = (cmp_tok if (isinstance(ex_tok.type_, str)
+                                     or ex_tok.type_ not in parsers)
+                         else parsers[ex_tok.type_](cmp_tok))
+                if ex_tok.type_ is _MsgTok.NICK_USER_HOST:
+                    nickuserhosts += [value]
+                if ex_tok.code:
+                    parsed[ex_tok.code.title] = value
+                    singled_tasks += [(cmd, ex_tok.code.title)
+                                      for cmd in ex_tok.code.commands]
         for code in self.bonus_tasks:
             singled_tasks += [(cmd, code.title) for cmd in code.commands]
         tasks: dict[_Command, list[str]] = {}
@@ -121,7 +125,8 @@ class _MsgParseExpectation:
             if cmd not in tasks:
                 tasks[cmd] = []
             tasks[cmd] += [title]
-        return parsed | {'_verb': self.verb, '_tasks': tasks}
+        return parsed | {'_verb': self.verb, '_tasks': tasks,
+                         '_nickuserhosts': nickuserhosts}
 
 
 MSG_EXPECTATIONS: list[_MsgParseExpectation] = [
@@ -458,7 +463,7 @@ MSG_EXPECTATIONS: list[_MsgParseExpectation] = [
 
     _MsgParseExpectation(
         'JOIN',
-        (_MsgTok.NICK_USER_HOST, 'set_user:joiner'),
+        (_MsgTok.NICK_USER_HOST, ':joiner'),
         ((_MsgTok.CHANNEL, ':channel'),)),
 
     _MsgParseExpectation(
@@ -492,23 +497,23 @@ MSG_EXPECTATIONS: list[_MsgParseExpectation] = [
          (_MsgTok.ANY, ':message'))),
     _MsgParseExpectation(
         'NOTICE',
-        (_MsgTok.NICK_USER_HOST, 'set_user:sender'),
+        (_MsgTok.NICK_USER_HOST, ':sender'),
         ((_MsgTok.NICKNAME, 'setattr_db.users.me:nick'),
          (_MsgTok.ANY, ':message'))),
     _MsgParseExpectation(
         'NOTICE',
-        (_MsgTok.NICK_USER_HOST, 'set_user:sender'),
+        (_MsgTok.NICK_USER_HOST, ':sender'),
         ((_MsgTok.CHANNEL, ':channel'),
          (_MsgTok.ANY, ':message'))),
 
     _MsgParseExpectation(
         'PRIVMSG',
-        (_MsgTok.NICK_USER_HOST, 'set_user:sender'),
+        (_MsgTok.NICK_USER_HOST, ':sender'),
         ((_MsgTok.NICKNAME, 'setattr_db.users.me:nick'),
          (_MsgTok.ANY, ':message'))),
     _MsgParseExpectation(
         'PRIVMSG',
-        (_MsgTok.NICK_USER_HOST, 'set_user:sender'),
+        (_MsgTok.NICK_USER_HOST, ':sender'),
         ((_MsgTok.CHANNEL, ':channel'),
          (_MsgTok.ANY, ':message'))),