From a4bd3f59bb959ed1b74d2d3c6d236b9eae476b46 Mon Sep 17 00:00:00 2001
From: William Grant <willmgrant@gmail.com>
Date: Mon, 25 Sep 2023 12:00:46 +1000
Subject: [PATCH] feat: improved expire swarm result logic

better logging and handle errors more smoothly
---
 ts/models/message.ts                       |  4 +-
 ts/session/apis/snode_api/expireRequest.ts | 46 ++++++++++++++++------
 ts/util/expiringMessages.ts                |  2 +-
 3 files changed, 37 insertions(+), 15 deletions(-)

diff --git a/ts/models/message.ts b/ts/models/message.ts
index 1df719ce6..dbfcbd3a7 100644
--- a/ts/models/message.ts
+++ b/ts/models/message.ts
@@ -1190,7 +1190,9 @@ export class MessageModel extends Backbone.Model<MessageAttributes> {
 
         if (newTTL) {
           window.log.debug(
-            `WIP: [setToExpire] messageHash ${messageHash} has a new TTL of ${newTTL}`
+            `WIP: [setToExpire] messageHash ${messageHash} has a new TTL of ${newTTL} which expires at ${new Date(
+              newTTL
+            ).toUTCString()}`
           );
           this.set({
             expires_at: newTTL,
diff --git a/ts/session/apis/snode_api/expireRequest.ts b/ts/session/apis/snode_api/expireRequest.ts
index 6503e96c4..0d74af711 100644
--- a/ts/session/apis/snode_api/expireRequest.ts
+++ b/ts/session/apis/snode_api/expireRequest.ts
@@ -28,7 +28,9 @@ async function verifyExpireMsgsResponseSignature({
   messageHashes: Array<string>;
 }): Promise<boolean> {
   if (!expiry || isEmpty(messageHashes) || isEmpty(signature)) {
-    window.log.warn('WIP: [verifyExpireMsgsSignature] missing argument');
+    window.log.warn(
+      `WIP: [verifyExpireMsgsSignature] missing argument\nexpiry:${expiry}\nmessageHashes:${messageHashes}\nsignature:${signature}`
+    );
     return false;
   }
 
@@ -72,7 +74,7 @@ async function processExpireRequestResponse(
   messageHashes: Array<string>
 ): Promise<ExpireRequestResponseResults> {
   if (isEmpty(swarm)) {
-    throw Error(`[expireOnNodes] failed! ${messageHashes}`);
+    throw Error(`[processExpireRequestResponse] Swarm is missing! ${messageHashes}`);
   }
 
   const results: ExpireRequestResponseResults = {};
@@ -80,15 +82,12 @@ async function processExpireRequestResponse(
 
   for (const nodeKey of Object.keys(swarm)) {
     if (!isEmpty(swarm[nodeKey].failed)) {
-      const reason = 'Unknown';
-      const statusCode = '404';
-      window?.log?.warn(
-        `WIP: loki_message:::expireMessage - Couldn't delete data from: ${
+      window.log.warn(
+        `WIP: [processExpireRequestResponse] Swarm result failure on ${
           targetNode.pubkey_ed25519
-        }${reason && statusCode && ` due to an error ${reason} (${statusCode})`}`
+        } for nodeKey ${nodeKey}\n${JSON.stringify(swarm[nodeKey])}`
       );
-      // Make sure to clear the result since it failed
-      results[nodeKey] = { hashes: [], expiry: 0 };
+      continue;
     }
 
     const updatedHashes = swarm[nodeKey].updated;
@@ -96,6 +95,17 @@ async function processExpireRequestResponse(
     const expiry = swarm[nodeKey].expiry;
     const signature = swarm[nodeKey].signature;
 
+    if (!updatedHashes || !expiry || !signature) {
+      window.log.warn(
+        `WIP: [processExpireRequestResponse] Missing arguments on ${
+          targetNode.pubkey_ed25519
+        } so we will ignore this result (${nodeKey}) and trust in the force.\n${JSON.stringify(
+          swarm[nodeKey]
+        )}`
+      );
+      continue;
+    }
+
     // eslint-disable-next-line no-await-in-loop
     const isValid = await verifyExpireMsgsResponseSignature({
       pubkey,
@@ -109,9 +119,11 @@ async function processExpireRequestResponse(
 
     if (!isValid) {
       window.log.warn(
-        'WIP: loki_message:::expireMessage - Signature verification failed!',
-        messageHashes
+        `WIP: [processExpireRequestResponse] Signature verification failed on ${
+          targetNode.pubkey_ed25519
+        }!\n${JSON.stringify(messageHashes)}`
       );
+      continue;
     }
     results[nodeKey] = { hashes: updatedHashes, expiry };
   }
@@ -169,6 +181,14 @@ async function expireOnNodes(
       const messageHash = firstExpirationResult[0];
       const expiry = firstExpirationResult[1].expiry;
 
+      if (!expiry || !messageHash) {
+        throw new Error(
+          `Something is wrong with the firstExpirationResult: ${JSON.stringify(
+            JSON.stringify(firstExpirationResult)
+          )}`
+        );
+      }
+
       window.log.debug(
         `WIP: [expireOnNodes] Success!\nHere are the results from one of the snodes.\nmessageHash: ${messageHash} \nexpiry: ${expiry} \nexpires at: ${new Date(
           expiry
@@ -177,7 +197,7 @@ async function expireOnNodes(
 
       return expiry;
     } catch (e) {
-      window?.log?.warn('WIP: [expireOnNodes] Failed to parse "swarm" result: ', e.msg);
+      window?.log?.warn('WIP: [expireOnNodes] Failed to parse "swarm" result: ', e);
     }
     return null;
   } catch (e) {
@@ -221,7 +241,7 @@ async function buildExpireRequest(
 
   const expiry = GetNetworkTime.getNowWithNetworkOffset() + expireTimer;
   window.log.debug(
-    `WIP: [buildExpireRequest] messageHash: ${messageHash} should expire at ${new Date(
+    `WIP: [buildExpireRequest]\nmessageHash: ${messageHash} should expire at ${new Date(
       expiry
     ).toUTCString()}`
   );
diff --git a/ts/util/expiringMessages.ts b/ts/util/expiringMessages.ts
index 7bf520297..9210aa6e3 100644
--- a/ts/util/expiringMessages.ts
+++ b/ts/util/expiringMessages.ts
@@ -255,7 +255,7 @@ export function setExpirationStartTimestamp(
   // TODO legacy messages support will be removed in a future release
   if (timestamp) {
     window.log.debug(
-      `WIP: [setExpirationStartTimestamp] We compare 2 timestamps for a disappearing message (${mode}): expirationStartTimestamp `,
+      `WIP: [setExpirationStartTimestamp] We compare 2 timestamps for a disappearing message (${mode}):\nexpirationStartTimestamp `,
       new Date(expirationStartTimestamp).toLocaleTimeString(),
       '\ntimestamp ',
       new Date(timestamp).toLocaleTimeString()