]> git.mxchange.org Git - friendica.git/commitdiff
Handle changed parents
authorMichael <heluecht@pirati.ca>
Sun, 24 Jul 2022 13:09:35 +0000 (13:09 +0000)
committerMichael <heluecht@pirati.ca>
Sun, 24 Jul 2022 13:09:35 +0000 (13:09 +0000)
src/Model/Post/User.php
src/Protocol/ActivityPub/Processor.php
src/Protocol/ActivityPub/Queue.php
src/Worker/Cron.php

index 9da97180688be41348a9bcfc8eb30475ee278256..7bd570699731ab1bea3267a46dfe5194bdbe306c 100644 (file)
@@ -24,7 +24,6 @@ namespace Friendica\Model\Post;
 use Friendica\Database\DBA;
 use \BadMethodCallException;
 use Friendica\Database\Database;
-use Friendica\Database\DBStructure;
 use Friendica\DI;
 
 class User
@@ -44,10 +43,6 @@ class User
                        throw new BadMethodCallException('Empty URI_id');
                }
 
-               if (DBA::exists('post-user', ['uri-id' => $uri_id, 'uid' => $uid])) {
-                       return false;
-               }
-
                $fields = DI::dbaDefinition()->truncateFieldsForTable('post-user', $data);
 
                // Additionally assign the key fields
@@ -59,6 +54,33 @@ class User
                        $fields['unseen'] = false;
                }
 
+               // Does the entry already exist?
+               if (DBA::exists('post-user', ['uri-id' => $uri_id, 'uid' => $uid])) {
+                       $postuser = DBA::selectFirst('post-user', [], ['uri-id' => $uri_id, 'uid' => $uid]);
+
+                       // We quit here, when there are obvious differences
+                       foreach (['created', 'owner-id', 'author-id', 'vid', 'network', 'private', 'wall', 'origin'] as $key) {
+                               if ($fields[$key] != $postuser[$key]) {
+                                       return 0;
+                               }
+                       }
+                       
+                       $update = [];
+                       foreach (['gravity', 'parent-uri-id', 'thr-parent-id'] as $key) {
+                               if ($fields[$key] != $postuser[$key]) {
+                                       $update[$key] = $fields[$key];
+                               }
+                       }
+
+                       // When the parents changed, we apply these changes to the existing entry
+                       if (!empty($update)) {
+                               DBA::update('post-user', $update, ['id' => $postuser['id']]);
+                               return $postuser['id'];
+                       } else {
+                               return 0;
+                       }
+               }
+
                if (!DBA::insert('post-user', $fields, Database::INSERT_IGNORE)) {
                        return 0;
                }
index 9d5f3f2f6e8150905758acad2099e6d0f875814f..d1c3994e2aee306d275ff94435d80866f8a714e1 100644 (file)
@@ -45,7 +45,9 @@ use Friendica\Protocol\Activity;
 use Friendica\Protocol\ActivityPub;
 use Friendica\Protocol\Relay;
 use Friendica\Util\DateTimeFormat;
+use Friendica\Util\HTTPSignature;
 use Friendica\Util\JsonLD;
+use Friendica\Util\Network;
 use Friendica\Util\Strings;
 use Friendica\Worker\Delivery;
 
@@ -301,6 +303,11 @@ class Processor
                        Logger::notice('Parent not found. Try to refetch it.', ['parent' => $activity['reply-to-id'], 'recursion-depth' => $recursion_depth]);
                        if ($recursion_depth < 10) {
                                $result = self::fetchMissingActivity($activity['reply-to-id'], $activity, '', Receiver::COMPLETION_AUTO);
+                               if (empty($result) && self::ActivityIsGone($activity['reply-to-id'])) {
+                                       // Recursively delete this and all depending entries
+                                       Queue::deleteById($activity['entry-id']);
+                                       return [];
+                               }
                                $fetch_by_worker = empty($result);
                        } else {
                                Logger::notice('Recursion level is too high.', ['parent' => $activity['reply-to-id'], 'recursion-depth' => $recursion_depth]);
@@ -452,6 +459,24 @@ class Processor
                return $item;
        }
 
+       /**
+        * Check if a given activity is no longer available
+        *
+        * @param string $url
+        *
+        * @return boolean
+        */
+       private static function ActivityIsGone(string $url): bool
+       {
+               $curlResult = HTTPSignature::fetchRaw($url, 0);
+
+               if (Network::isUrlBlocked($url)) {
+                       return true;
+               }
+
+               // @todo To ensure that the remote system is working correctly, we can check if the "Content-Type" contains JSON
+               return in_array($curlResult->getReturnCode(), [404]);
+       }
        /**
         * Delete items
         *
@@ -933,6 +958,9 @@ class Processor
                                $success = true;
                        } else {
                                Logger::notice('Item insertion aborted', ['uri' => $item['uri'], 'uid' => $item['uid']]);
+                               if (Item::isTooOld($item) || !Item::isValid($item)) {
+                                       Queue::remove($activity);
+                               }
                        }
 
                        if ($item['uid'] == 0) {
index 3d40d71638fb64646f0f42acbbaef5fe3ff33e37..7b91609bdbdad8fe0a6303c40d03c40107834672 100644 (file)
@@ -116,7 +116,7 @@ class Queue
         * @param integer $id
         * @return void
         */
-       private static function deleteById(int $id)
+       public static function deleteById(int $id)
        {
                $entry = DBA::selectFirst('inbox-entry', ['id', 'object-id'], ['id' => $id]);
                if (empty($entry)) {
@@ -206,7 +206,7 @@ class Queue
                $entries = DBA::select('inbox-entry', ['id', 'type', 'object-type', 'object-id', 'in-reply-to-id'], ["`wid` IS NULL"], ['order' => ['id' => true]]);
                while ($entry = DBA::fetch($entries)) {
                        // We don't need to process entries that depend on already existing entries.
-                       if (!empty($entry['in-reply-to-id']) && DBA::exists('inbox-entry', ['object-id' => $entry['in-reply-to-id']])) {
+                       if (!empty($entry['in-reply-to-id']) && DBA::exists('inbox-entry', ["`id` != ? AND `object-id` = ?", $entry['id'], $entry['in-reply-to-id']])) {
                                continue;
                        }
                        Logger::debug('Process leftover entry', $entry);
index c2109e66a3ea4bce82de5f568f4fa9c630a834be..2ace97d830e61373b5f7cc6539ab8c2570304409 100644 (file)
@@ -92,6 +92,9 @@ class Cron
                        // Remove old pending posts from the queue
                        Queue::clear();
 
+                       // Process all unprocessed entries
+                       Queue::processAll();
+
                        // Search for new contacts in the directory
                        if (DI::config()->get('system', 'synchronize_directory')) {
                                Worker::add(PRIORITY_LOW, 'PullDirectory');
@@ -129,9 +132,6 @@ class Cron
                                Worker::add(PRIORITY_LOW, 'OptimizeTables');
                        }
 
-                       // Process all unprocessed entries
-                       Queue::processAll();
-
                        // Resubscribe to relay servers
                        Relay::reSubscribe();