]> git.mxchange.org Git - friendica.git/blobdiff - src/Protocol/ActivityPub/Transmitter.php
Merge pull request #10230 from annando/oauth-login
[friendica.git] / src / Protocol / ActivityPub / Transmitter.php
index 749931c20db601ec7ef67db542e52e4a03d8634e..9773a5a48bbd1aa43ee7b511d2aefe6d263e1fbf 100644 (file)
@@ -1,6 +1,6 @@
 <?php
 /**
- * @copyright Copyright (C) 2020, Friendica
+ * @copyright Copyright (C) 2010-2021, the Friendica project
  *
  * @license GNU AGPL version 3 or any later version
  *
@@ -258,9 +258,9 @@ class Transmitter
                $condition = array_merge($condition,
                        ['author-id' => $public_contact,
                        'gravity' => [GRAVITY_PARENT, GRAVITY_COMMENT],
-                       'deleted' => false, 'visible' => true, 'moderated' => false]);
+                       'deleted' => false, 'visible' => true]);
 
-               $count = DBA::count('item', $condition);
+               $count = Post::count($condition);
 
                $data = ['@context' => ActivityPub::CONTEXT];
                $data['id'] = DI::baseUrl() . '/outbox/' . $owner['nickname'];
@@ -1045,19 +1045,19 @@ class Transmitter
        public static function createActivityFromItem(int $item_id, bool $object_mode = false)
        {
                Logger::info('Fetching activity', ['item' => $item_id]);
-               $item = Post::selectFirst([], ['id' => $item_id, 'parent-network' => Protocol::NATIVE_SUPPORT]);
+               $item = Post::selectFirst(Item::DELIVER_FIELDLIST, ['id' => $item_id, 'parent-network' => Protocol::NATIVE_SUPPORT]);
                if (!DBA::isResult($item)) {
                        return false;
                }
 
                // In case of a forum post ensure to return the original post if author and forum are on the same machine
-               if (!empty($item['forum_mode'])) {
+               if (($item['gravity'] == GRAVITY_PARENT) && !empty($item['forum_mode'])) {
                        $author = Contact::getById($item['author-id'], ['nurl']);
                        if (!empty($author['nurl'])) {
                                $self = Contact::selectFirst(['uid'], ['nurl' => $author['nurl'], 'self' => true]);
                                if (!empty($self['uid'])) {
-                                       $forum_item = Post::selectFirst([], ['uri-id' => $item['uri-id'], 'uid' => $self['uid']]);
-                                       if (DBA::isResult($item)) {
+                                       $forum_item = Post::selectFirst(Item::DELIVER_FIELDLIST, ['uri-id' => $item['uri-id'], 'uid' => $self['uid']]);
+                                       if (DBA::isResult($forum_item)) {
                                                $item = $forum_item; 
                                        }
                                }
@@ -1069,25 +1069,27 @@ class Transmitter
                        return false;
                }
 
-               $condition = ['item-uri' => $item['uri'], 'protocol' => Conversation::PARCEL_ACTIVITYPUB];
-               $conversation = DBA::selectFirst('conversation', ['source'], $condition);
-               if (!$item['origin'] && DBA::isResult($conversation)) {
-                       $data = json_decode($conversation['source'], true);
-                       if (!empty($data['type'])) {
-                               if (in_array($data['type'], ['Create', 'Update'])) {
-                                       if ($object_mode) {
-                                               unset($data['@context']);
-                                               unset($data['signature']);
-                                       }
-                                       Logger::info('Return stored conversation', ['item' => $item_id]);
-                                       return $data;
-                               } elseif (in_array('as:' . $data['type'], Receiver::CONTENT_TYPES)) {
-                                       if (!empty($data['@context'])) {
-                                               $context = $data['@context'];
-                                               unset($data['@context']);
+               if (!$item['deleted']) {
+                       $condition = ['item-uri' => $item['uri'], 'protocol' => Conversation::PARCEL_ACTIVITYPUB];
+                       $conversation = DBA::selectFirst('conversation', ['source'], $condition);
+                       if (!$item['origin'] && DBA::isResult($conversation)) {
+                               $data = json_decode($conversation['source'], true);
+                               if (!empty($data['type'])) {
+                                       if (in_array($data['type'], ['Create', 'Update'])) {
+                                               if ($object_mode) {
+                                                       unset($data['@context']);
+                                                       unset($data['signature']);
+                                               }
+                                               Logger::info('Return stored conversation', ['item' => $item_id]);
+                                               return $data;
+                                       } elseif (in_array('as:' . $data['type'], Receiver::CONTENT_TYPES)) {
+                                               if (!empty($data['@context'])) {
+                                                       $context = $data['@context'];
+                                                       unset($data['@context']);
+                                               }
+                                               unset($data['actor']);
+                                               $object = $data;
                                        }
-                                       unset($data['actor']);
-                                       $object = $data;
                                }
                        }
                }
@@ -1106,7 +1108,9 @@ class Transmitter
                        $data = [];
                }
 
-               if (($item['gravity'] == GRAVITY_ACTIVITY) && ($type != 'Undo')) {
+               if ($type == 'Delete') {
+                       $data['id'] = Item::newURI($item['uid'], $item['guid']) . '/' . $type;;
+               } elseif (($item['gravity'] == GRAVITY_ACTIVITY) && ($type != 'Undo')) {
                        $data['id'] = $item['uri'];
                } else {
                        $data['id'] = $item['uri'] . '/' . $type;
@@ -1256,53 +1260,60 @@ class Transmitter
        {
                $attachments = [];
 
-               // Currently deactivated, since it creates side effects on Mastodon and Pleroma.
-               // It will be reactivated, once this cleared.
-               /*
-               $attach_data = BBCode::getAttachmentData($item['body']);
-               if (!empty($attach_data['url'])) {
-                       $attachment = ['type' => 'Page',
-                               'mediaType' => 'text/html',
-                               'url' => $attach_data['url']];
-
-                       if (!empty($attach_data['title'])) {
-                               $attachment['name'] = $attach_data['title'];
-                       }
-
-                       if (!empty($attach_data['description'])) {
-                               $attachment['summary'] = $attach_data['description'];
+               $uriids = [$item['uri-id']];
+               $shared = BBCode::fetchShareAttributes($item['body']);
+               if (!empty($shared['guid'])) {
+                       $shared_item = Post::selectFirst(['uri-id'], ['guid' => $shared['guid']]);
+                       if (!empty($shared_item['uri-id'])) {
+                               $uriids[] = $shared_item['uri-id'];
                        }
+               }
 
-                       if (!empty($attach_data['image'])) {
-                               $imgdata = Images::getInfoFromURLCached($attach_data['image']);
-                               if ($imgdata) {
-                                       $attachment['icon'] = ['type' => 'Image',
-                                               'mediaType' => $imgdata['mime'],
-                                               'width' => $imgdata[0],
-                                               'height' => $imgdata[1],
-                                               'url' => $attach_data['image']];
+               $urls = [];
+               foreach ($uriids as $uriid) {
+                       foreach (Post\Media::getByURIId($uriid, [Post\Media::DOCUMENT, Post\Media::TORRENT]) as $attachment) {
+                               if (in_array($attachment['url'], $urls)) {
+                                       continue;
                                }
-                       }
+                               $urls[] = $attachment['url'];
 
-                       $attachments[] = $attachment;
-               }
-               */
-               foreach (Post\Media::getByURIId($item['uri-id'], [Post\Media::DOCUMENT, Post\Media::TORRENT, Post\Media::UNKNOWN]) as $attachment) {
-                       $attachments[] = ['type' => 'Document',
-                               'mediaType' => $attachment['mimetype'],
-                               'url' => $attachment['url'],
-                               'name' => $attachment['description']];
+                               $attachments[] = ['type' => 'Document',
+                                       'mediaType' => $attachment['mimetype'],
+                                       'url' => $attachment['url'],
+                                       'name' => $attachment['description']];
+                       }
                }
 
                if ($type != 'Note') {
                        return $attachments;
                }
 
-               foreach (Post\Media::getByURIId($item['uri-id'], [Post\Media::AUDIO, Post\Media::IMAGE, Post\Media::VIDEO]) as $attachment) {
-                       $attachments[] = ['type' => 'Document',
-                               'mediaType' => $attachment['mimetype'],
-                               'url' => $attachment['url'],
-                               'name' => $attachment['description']];
+               foreach ($uriids as $uriid) {
+                       foreach (Post\Media::getByURIId($uriid, [Post\Media::AUDIO, Post\Media::IMAGE, Post\Media::VIDEO]) as $attachment) {
+                               if (in_array($attachment['url'], $urls)) {
+                                       continue;
+                               }
+                               $urls[] = $attachment['url'];
+
+                               $attachments[] = ['type' => 'Document',
+                                       'mediaType' => $attachment['mimetype'],
+                                       'url' => $attachment['url'],
+                                       'name' => $attachment['description']];
+                       }
+                       // Currently deactivated, since it creates side effects on Mastodon and Pleroma.
+                       // It will be activated, once this cleared.
+                       /*
+                       foreach (Post\Media::getByURIId($uriid, [Post\Media::HTML]) as $attachment) {
+                               if (in_array($attachment['url'], $urls)) {
+                                       continue;
+                               }
+                               $urls[] = $attachment['url'];
+
+                               $attachments[] = ['type' => 'Page',
+                                       'mediaType' => $attachment['mimetype'],
+                                       'url' => $attachment['url'],
+                                       'name' => $attachment['description']];
+                       }*/
                }
 
                return $attachments;
@@ -1326,7 +1337,28 @@ class Transmitter
                        return $match[0];
                }
 
-               return '[url=' . ($data['alias'] ?: $data['url']) . ']@' . $data['nick'] . '[/url]';
+               return '[url=' . $data['url'] . ']@' . $data['nick'] . '[/url]';
+       }
+
+       /**
+        * Callback function to replace a Friendica style mention in a mention for a summary
+        *
+        * @param array $match Matching values for the callback
+        * @return string Replaced mention
+        * @throws \Friendica\Network\HTTPException\InternalServerErrorException
+        */
+       private static function mentionAddrCallback($match)
+       {
+               if (empty($match[1])) {
+                       return '';
+               }
+
+               $data = Contact::getByURL($match[1], false, ['addr']);
+               if (empty($data['addr'])) {
+                       return $match[0];
+               }
+
+               return '@' . $data['addr'];
        }
 
        /**
@@ -1404,7 +1436,7 @@ class Transmitter
         * @return array with the event data
         * @throws \Friendica\Network\HTTPException\InternalServerErrorException
         */
-       public static function createEvent($item)
+       private static function createEvent($item)
        {
                $event = [];
                $event['name'] = $item['event-summary'];
@@ -1420,6 +1452,8 @@ class Transmitter
                        $event['location'] = self::createLocation($item);
                }
 
+               $event['dfrn:adjust'] = (bool)$item['event-adjust'];
+
                return $event;
        }
 
@@ -1489,7 +1523,9 @@ class Transmitter
                if ($type == 'Note') {
                        $body = $item['raw-body'] ?? self::removePictures($body);
                } elseif (($type == 'Article') && empty($data['summary'])) {
-                       $data['summary'] = BBCode::toPlaintext(Plaintext::shorten(self::removePictures($body), 1000));
+                       $regexp = "/[@!]\[url\=([^\[\]]*)\].*?\[\/url\]/ism";
+                       $summary = preg_replace_callback($regexp, ['self', 'mentionAddrCallback'], $body);
+                       $data['summary'] = BBCode::toPlaintext(Plaintext::shorten(self::removePictures($summary), 1000));
                }
 
                if (empty($item['uid']) || !Feature::isEnabled($item['uid'], 'explicit_mentions')) {
@@ -1514,7 +1550,7 @@ class Transmitter
                        $richbody = preg_replace_callback($regexp, ['self', 'mentionCallback'], $item['body']);
                        $richbody = BBCode::removeAttachment($richbody);
 
-                       $data['contentMap'][$language] = BBCode::convert($richbody, false);
+                       $data['contentMap'][$language] = BBCode::convert($richbody, false, BBCode::EXTERNAL);
                }
 
                $data['source'] = ['content' => $item['body'], 'mediaType' => "text/bbcode"];
@@ -1645,7 +1681,7 @@ class Transmitter
                        return [];
                }
 
-               $reshared_item = Post::selectFirst([], ['guid' => $reshared['guid']]);
+               $reshared_item = Post::selectFirst(Item::DELIVER_FIELDLIST, ['guid' => $reshared['guid']]);
                if (!DBA::isResult($reshared_item)) {
                        return [];
                }