AP: We can now receive "direct messages" (aka "mails") as well

This commit is contained in:
Michael 2019-05-16 05:44:59 +00:00
parent 969b7744c9
commit 3f55f93606
2 changed files with 78 additions and 3 deletions

View File

@ -5,6 +5,7 @@
namespace Friendica\Protocol\ActivityPub; namespace Friendica\Protocol\ActivityPub;
use Friendica\Database\DBA; use Friendica\Database\DBA;
use Friendica\Content\Text\BBCode;
use Friendica\Content\Text\HTML; use Friendica\Content\Text\HTML;
use Friendica\Core\Config; use Friendica\Core\Config;
use Friendica\Core\Logger; use Friendica\Core\Logger;
@ -15,6 +16,7 @@ use Friendica\Model\Item;
use Friendica\Model\Event; use Friendica\Model\Event;
use Friendica\Model\Term; use Friendica\Model\Term;
use Friendica\Model\User; use Friendica\Model\User;
use Friendica\Model\Mail;
use Friendica\Protocol\ActivityPub; use Friendica\Protocol\ActivityPub;
use Friendica\Util\DateTimeFormat; use Friendica\Util\DateTimeFormat;
use Friendica\Util\JsonLD; use Friendica\Util\JsonLD;
@ -275,7 +277,7 @@ class Processor
$content = self::convertMentions($content); $content = self::convertMentions($content);
if (($item['thr-parent'] != $item['uri']) && ($item['gravity'] == GRAVITY_COMMENT)) { if (empty($activity['directmessage']) && ($item['thr-parent'] != $item['uri']) && ($item['gravity'] == GRAVITY_COMMENT)) {
$item_private = !in_array(0, $activity['item_receiver']); $item_private = !in_array(0, $activity['item_receiver']);
$parent = Item::selectFirst(['id', 'private', 'author-link', 'alias'], ['uri' => $item['thr-parent']]); $parent = Item::selectFirst(['id', 'private', 'author-link', 'alias'], ['uri' => $item['thr-parent']]);
if (!DBA::isResult($parent)) { if (!DBA::isResult($parent)) {
@ -323,8 +325,7 @@ class Processor
private static function postItem($activity, $item) private static function postItem($activity, $item)
{ {
/// @todo What to do with $activity['context']? /// @todo What to do with $activity['context']?
if (empty($activity['directmessage']) && ($item['gravity'] != GRAVITY_PARENT) && !Item::exists(['uri' => $item['thr-parent']])) {
if (($item['gravity'] != GRAVITY_PARENT) && !Item::exists(['uri' => $item['thr-parent']])) {
Logger::info('Parent not found, message will be discarded.', ['thr-parent' => $item['thr-parent']]); Logger::info('Parent not found, message will be discarded.', ['thr-parent' => $item['thr-parent']]);
return; return;
} }
@ -368,6 +369,11 @@ class Processor
$item['contact-id'] = Contact::getIdForURL($activity['author'], 0, true); $item['contact-id'] = Contact::getIdForURL($activity['author'], 0, true);
} }
if (!empty($activity['directmessage'])) {
self::postMail($activity, $item);
continue;
}
if ($activity['object_type'] == 'as:Event') { if ($activity['object_type'] == 'as:Event') {
self::createEvent($activity, $item); self::createEvent($activity, $item);
} }
@ -395,6 +401,69 @@ class Processor
} }
} }
/**
* Creates an mail post
*
* @param array $activity Activity data
* @param array $item item array
* @throws \Friendica\Network\HTTPException\InternalServerErrorException
* @throws \ImagickException
*/
private static function postMail($activity, $item)
{
if (($item['gravity'] != GRAVITY_PARENT) && !DBA::exists('mail', ['uri' => $item['thr-parent'], 'uid' => $item['uid']])) {
Logger::info('Parent not found, mail will be discarded.', ['uid' => $item['uid'], 'uri' => $item['thr-parent']]);
return false;
}
Logger::info('Direct Message', $item);
$msg = [];
$msg['uid'] = $item['uid'];
$msg['contact-id'] = $item['contact-id'];
$contact = Contact::getById($item['contact-id'], ['name', 'url', 'photo']);
$msg['from-name'] = $contact['name'];
$msg['from-url'] = $contact['url'];
$msg['from-photo'] = $contact['photo'];
$msg['uri'] = $item['uri'];
$msg['created'] = $item['created'];
$parent = DBA::selectFirst('mail', ['parent-uri', 'title'], ['uri' => $item['thr-parent']]);
if (DBA::isResult($parent)) {
$msg['parent-uri'] = $parent['parent-uri'];
$msg['title'] = $parent['title'];
} else {
$msg['parent-uri'] = $item['thr-parent'];
if (!empty($item['title'])) {
$msg['title'] = $item['title'];
} elseif (!empty($item['content-warning'])) {
$msg['title'] = $item['content-warning'];
} else {
// Trying to generate a title out of the body
$title = $item['body'];
while (preg_match('#^(@\[url=([^\]]+)].*?\[\/url]\s)(.*)#is', $title, $matches)) {
$title = $matches[3];
}
$title = trim(HTML::toPlaintext(BBCode::convert($title, false, 2, true), 0));
if (strlen($title) > 20) {
$title = substr($title, 0, 20) . '...';
}
$msg['title'] = $title;
}
}
$msg['body'] = $item['body'];
Mail::insert($msg);
}
/** /**
* Fetches missing posts * Fetches missing posts
* *

View File

@ -207,6 +207,7 @@ class Receiver
return []; return [];
} }
$object_data['object_id'] = $object_id; $object_data['object_id'] = $object_id;
$object_data['directmessage'] = JsonLD::fetchElement($activity, 'litepub:directMessage');
// We had been able to retrieve the object data - so we can trust the source // We had been able to retrieve the object data - so we can trust the source
$trust_source = true; $trust_source = true;
@ -935,6 +936,11 @@ class Receiver
$object_data['receiver'] = self::getReceivers($object, $object_data['actor'], $object_data['tags']); $object_data['receiver'] = self::getReceivers($object, $object_data['actor'], $object_data['tags']);
// Test if it is an answer to a mail
if (DBA::exists('mail', ['uri' => $object_data['reply-to-id']])) {
$object_data['directmessage'] = true;
}
// Common object data: // Common object data:
// Unhandled // Unhandled