changeset 3942:a92eef737703

plugin XEP-0373: download public keys if they are not found in local storage: public keys were only obtained from PEP notifications, however this wasn't working if the entity was not in our roster. Now if no public key is retrieved from local storage, the public key node is requested, and an error is raised if nothing is found. This allows the use of OX with entities which are not in roster. rel 380
author Goffi <goffi@goffi.org>
date Sat, 15 Oct 2022 20:38:33 +0200
parents 036188fff714
children 8dc6a4cfda4b
files sat/plugins/plugin_xep_0373.py
diffstat 1 files changed, 21 insertions(+), 7 deletions(-) [+]
line wrap: on
line diff
--- a/sat/plugins/plugin_xep_0373.py	Sat Oct 15 20:38:33 2022 +0200
+++ b/sat/plugins/plugin_xep_0373.py	Sat Oct 15 20:38:33 2022 +0200
@@ -99,6 +99,7 @@
 
 PARAM_CATEGORY = "Security"
 PARAM_NAME = "ox_policy"
+STR_KEY_PUBLIC_KEYS_METADATA = "/public-keys-metadata/{}"
 
 
 class VerificationError(Exception):
@@ -1096,7 +1097,7 @@
             timestamp=parse_datetime(cast(str, pubkey_metadata_elt["date"]))
         ) for pubkey_metadata_elt in pubkey_metadata_elts }
 
-        storage_key = f"/public-keys-metadata/{sender.userhost()}"
+        storage_key = STR_KEY_PUBLIC_KEYS_METADATA.format(sender.userhost())
 
         local_public_keys_metadata = cast(
             Set[PublicKeyMetadata],
@@ -1185,7 +1186,7 @@
 
         await self.publish_public_key(client, secret_key.public_key)
 
-        storage_key = f"/public-keys-metadata/{client.jid.userhost()}"
+        storage_key = STR_KEY_PUBLIC_KEYS_METADATA.format(client.jid.userhost())
 
         public_keys_list = cast(
             Set[PublicKeyMetadata],
@@ -1489,7 +1490,7 @@
     async def import_all_public_keys(
         self,
         client: SatXMPPClient,
-        jid: jid.JID
+        entity_jid: jid.JID
     ) -> Set[GPGPublicKey]:
         """Import all public keys of a JID that have not been imported before.
 
@@ -1500,14 +1501,27 @@
             result.
         """
 
-        available_public_keys = self.list_public_keys(client, jid)
+        available_public_keys = self.list_public_keys(client, entity_jid)
 
-        storage_key = f"/public-keys-metadata/{jid.userhost()}"
+        storage_key = STR_KEY_PUBLIC_KEYS_METADATA.format(entity_jid.userhost())
 
         public_keys_metadata = cast(
             Set[PublicKeyMetadata],
             await self.__storage[client.profile].get(storage_key, set())
         )
+        if not public_keys_metadata:
+            public_keys_metadata = await self.download_public_keys_list(
+                client, entity_jid
+            )
+            if not public_keys_metadata:
+                raise exceptions.NotFound(
+                    f"Can't find public keys for {entity_jid}"
+                )
+            else:
+                await self.__storage[client.profile].aset(
+                    storage_key, public_keys_metadata
+                )
+
 
         missing_keys = set(filter(lambda public_key_metadata: all(
             public_key_metadata.fingerprint != public_key.fingerprint
@@ -1518,12 +1532,12 @@
         for missing_key in missing_keys:
             try:
                 available_public_keys.add(
-                    await self.import_public_key(client, jid, missing_key.fingerprint)
+                    await self.import_public_key(client, entity_jid, missing_key.fingerprint)
                 )
             except Exception as e:
                 log.warning(
                     f"Import of public key {missing_key.fingerprint} owned by"
-                    f" {jid.userhost()} failed, ignoring: {e}"
+                    f" {entity_jid.userhost()} failed, ignoring: {e}"
                 )
 
         return available_public_keys