X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=mod%2Fitem.php;h=66ab1c210b9d2acaaa55b2f3fa3d04d21e527193;hb=1fdd0f915250517e254adb5165b394f03721cd87;hp=808641132e2908da951291cd0ed7ee846e07e54b;hpb=0d56f156f7103ca15221d97fefb67696b837e33c;p=friendica.git diff --git a/mod/item.php b/mod/item.php index 808641132e..66ab1c210b 100644 --- a/mod/item.php +++ b/mod/item.php @@ -19,7 +19,7 @@ * * This is the POST destination for most all locally posted * text stuff. This function handles status, wall-to-wall status, - * local comments, and remote coments that are posted on this site + * local comments, and remote comments that are posted on this site * (as opposed to being delivered in a feed). * Also processed here are posts and comments coming through the * statusnet/twitter API. @@ -29,6 +29,7 @@ */ use Friendica\App; +use Friendica\Content\Conversation; use Friendica\Content\Text\BBCode; use Friendica\Core\Hook; use Friendica\Core\Logger; @@ -40,29 +41,19 @@ use Friendica\DI; use Friendica\Model\Contact; use Friendica\Model\Item; use Friendica\Model\ItemURI; -use Friendica\Model\Photo; use Friendica\Model\Post; -use Friendica\Model\Tag; use Friendica\Network\HTTPException; -use Friendica\Object\EMail\ItemCCEMail; -use Friendica\Protocol\Activity; use Friendica\Util\DateTimeFormat; function item_post(App $a) { $uid = DI::userSession()->getLocalUserId(); - if (!DI::userSession()->isAuthenticated() || !$uid) { + if (!$uid) { throw new HTTPException\ForbiddenException(); } if (!empty($_REQUEST['dropitems'])) { - $arr_drop = explode(',', $_REQUEST['dropitems']); - foreach ($arr_drop as $item) { - Item::deleteForUser(['id' => $item], $uid); - } - - $json = ['success' => 1]; - System::jsonExit($json); + item_drop($uid, $_REQUEST['dropitems']); } Hook::callAll('post_local_start', $_REQUEST); @@ -76,68 +67,107 @@ function item_post(App $a) { * after it's been previewed */ if (!$preview && !empty($_REQUEST['post_id_random'])) { - if (!empty($_SESSION['post-random']) && $_SESSION['post-random'] == $_REQUEST['post_id_random']) { + if (DI::session()->get('post-random') == $_REQUEST['post_id_random']) { Logger::warning('duplicate post'); item_post_return(DI::baseUrl(), $return_path); } else { - $_SESSION['post-random'] = $_REQUEST['post_id_random']; + DI::session()->set('post-random', $_REQUEST['post_id_random']); } } - $post_id = intval($_REQUEST['post_id'] ?? 0); - - // is this an edited post? - if ($post_id > 0) { - $orig_post = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $post_id]); + if (empty($_REQUEST['post_id'])) { + item_insert($uid, $_REQUEST, $preview, $return_path); } else { - $orig_post = null; + item_edit($uid, $_REQUEST, $preview, $return_path); } +} - $emailcc = trim($_REQUEST['emailcc'] ?? ''); - - $post = ['uid' => $uid]; +function item_drop(int $uid, string $dropitems) +{ + $arr_drop = explode(',', $dropitems); + foreach ($arr_drop as $item) { + Item::deleteForUser(['id' => $item], $uid); + } - $post = DI::contentItem()->initializePost($post); + System::jsonExit(['success' => 1]); +} - $post['self'] = true; - $post['api_source'] = false; - $post['edit'] = $orig_post; - $post['file'] = ''; - $post['attach'] = ''; - $post['inform'] = ''; - $post['postopts'] = ''; - - $post['wall'] = $_REQUEST['wall'] ?? true; - $post['post-type'] = $_REQUEST['post_type'] ?? ''; - $post['title'] = trim($_REQUEST['title'] ?? ''); - $post['body'] = $_REQUEST['body'] ?? ''; - $post['location'] = trim($_REQUEST['location'] ?? ''); - $post['coord'] = trim($_REQUEST['coord'] ?? ''); - $post['parent'] = intval($_REQUEST['parent'] ?? 0); - $post['pubmail'] = $_REQUEST['pubmail_enable'] ?? false; - $post['created'] = $_REQUEST['created_at'] ?? DateTimeFormat::utcNow(); - $post['edited'] = $post['changed'] = $post['commented'] = $post['created']; - $post['app'] = ''; - - if ($post['parent']) { - if ($post['parent']) { - $parent_item = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $post['parent']]); +function item_edit(int $uid, array $request, bool $preview, string $return_path) +{ + $post = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $request['post_id'], 'uid' => $uid]); + if (!DBA::isResult($post)) { + if ($return_path) { + DI::sysmsg()->addNotice(DI::l10n()->t('Unable to locate original post.')); + DI::baseUrl()->redirect($return_path); } + throw new HTTPException\NotFoundException(DI::l10n()->t('Unable to locate original post.')); + } - // if this isn't the top-level parent of the conversation, find it - if (DBA::isResult($parent_item)) { - // The URI and the contact is taken from the direct parent which needn't to be the top parent - $post['thr-parent'] = $parent_item['uri']; - $toplevel_item = $parent_item; + $post['edit'] = $post; + $post['file'] = Post\Category::getTextByURIId($post['uri-id'], $post['uid']); + Post\Media::deleteByURIId($post['uri-id'], [Post\Media::AUDIO, Post\Media::VIDEO, Post\Media::IMAGE, Post\Media::HTML]); + $post = item_process($post, $request, $preview, $return_path); + + $fields = [ + 'title' => $post['title'], + 'body' => $post['body'], + 'attach' => $post['attach'], + 'file' => $post['file'], + 'location' => $post['location'], + 'coord' => $post['coord'], + 'edited' => DateTimeFormat::utcNow(), + 'changed' => DateTimeFormat::utcNow() + ]; + + $fields['body'] = Item::setHashtags($fields['body']); + + $quote_uri_id = Item::getQuoteUriId($fields['body'], $post['uid']); + if (!empty($quote_uri_id)) { + $fields['quote-uri-id'] = $quote_uri_id; + $fields['body'] = BBCode::removeSharedData($post['body']); + } + + Item::update($fields, ['id' => $post['id']]); + Item::updateDisplayCache($post['uri-id']); + + if ($return_path) { + DI::baseUrl()->redirect($return_path); + } + + throw new HTTPException\OKException(DI::l10n()->t('Post updated.')); +} + +function item_insert(int $uid, array $request, bool $preview, string $return_path) +{ + $post = ['uid' => $uid]; + $post = DI::contentItem()->initializePost($post); + + $post['edit'] = null; + $post['post-type'] = $request['post_type'] ?? ''; + $post['wall'] = $request['wall'] ?? true; + $post['pubmail'] = $request['pubmail_enable'] ?? false; + $post['created'] = $request['created_at'] ?? DateTimeFormat::utcNow(); + $post['edited'] = $post['changed'] = $post['commented'] = $post['created']; + $post['app'] = ''; + $post['inform'] = ''; + $post['postopts'] = ''; + $post['file'] = ''; + + if (!empty($request['parent'])) { + $parent_item = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $request['parent']]); + if ($parent_item) { + // if this isn't the top-level parent of the conversation, find it if ($parent_item['gravity'] != Item::GRAVITY_PARENT) { - $toplevel_item = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $toplevel_item['parent']]); + $toplevel_item = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $parent_item['parent']]); + } else { + $toplevel_item = $parent_item; } } - if (!DBA::isResult($toplevel_item)) { - DI::sysmsg()->addNotice(DI::l10n()->t('Unable to locate original post.')); + if (empty($toplevel_item)) { if ($return_path) { + DI::sysmsg()->addNotice(DI::l10n()->t('Unable to locate original post.')); DI::baseUrl()->redirect($return_path); } throw new HTTPException\NotFoundException(DI::l10n()->t('Unable to locate original post.')); @@ -148,13 +178,11 @@ function item_post(App $a) { if ($toplevel_item['uid'] == 0) { $stored = Item::storeForUserByUriId($toplevel_item['uri-id'], $post['uid'], ['post-reason' => Item::PR_ACTIVITY]); Logger::info('Public item stored for user', ['uri-id' => $toplevel_item['uri-id'], 'uid' => $post['uid'], 'stored' => $stored]); - if ($stored) { - $toplevel_item = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $stored]); - } } $post['parent'] = $toplevel_item['id']; $post['gravity'] = Item::GRAVITY_COMMENT; + $post['thr-parent'] = $parent_item['uri']; $post['wall'] = $toplevel_item['wall']; } else { $parent_item = []; @@ -163,28 +191,57 @@ function item_post(App $a) { $post['thr-parent'] = $post['uri']; } - $post = DI::contentItem()->getACL($post, $parent_item, $_REQUEST); + $post = DI::contentItem()->getACL($post, $parent_item, $request); $post['pubmail'] = $post['pubmail'] && !$post['private']; - if (!empty($orig_post)) { - $post['uri'] = $orig_post['uri']; - $post['file'] = Post\Category::getTextByURIId($orig_post['uri-id'], $orig_post['uid']); - } + $post = item_process($post, $request, $preview, $return_path); + + $post_id = Item::insert($post); + if (!$post_id) { + if ($return_path) { + DI::sysmsg()->addNotice(DI::l10n()->t('Item wasn\'t stored.')); + DI::baseUrl()->redirect($return_path); + } - $post = DI::contentItem()->addCategories($post, $_REQUEST['category'] ?? ''); + throw new HTTPException\InternalServerErrorException(DI::l10n()->t('Item wasn\'t stored.')); + } - if (!$preview) { - if (Photo::setPermissionFromBody($post['body'], $post['uid'], $post['contact-id'], $post['allow_cid'], $post['allow_gid'], $post['deny_cid'], $post['deny_gid'])) { - $post['object-type'] = Activity\ObjectType::IMAGE; + $post = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $post_id]); + if (!$post) { + Logger::error('Item couldn\'t be fetched.', ['post_id' => $post_id]); + if ($return_path) { + DI::baseUrl()->redirect($return_path); } - $post = DI::contentItem()->moveAttachmentsFromBodyToAttach($post); + throw new HTTPException\InternalServerErrorException(DI::l10n()->t('Item couldn\'t be fetched.')); } + $recipients = explode(',', $request['emailcc'] ?? ''); + + DI::contentItem()->postProcessPost($post, $recipients); + + Logger::debug('post_complete'); + + item_post_return(DI::baseUrl(), $return_path); + // NOTREACHED +} + +function item_process(array $post, array $request, bool $preview, string $return_path): array +{ + $post['self'] = true; + $post['api_source'] = false; + $post['attach'] = ''; + $post['title'] = trim($request['title'] ?? ''); + $post['body'] = $request['body'] ?? ''; + $post['location'] = trim($request['location'] ?? ''); + $post['coord'] = trim($request['coord'] ?? ''); + + $post = DI::contentItem()->addCategories($post, $request['category'] ?? ''); + // Add the attachment to the body. - if (!empty($_REQUEST['has_attachment'])) { - $post['body'] .= DI::contentItem()->storeAttachmentFromRequest($_REQUEST); + if (!empty($request['has_attachment'])) { + $post['body'] .= DI::contentItem()->storeAttachmentFromRequest($request); } $post = DI::contentItem()->finalizePost($post); @@ -194,53 +251,48 @@ function item_post(App $a) { System::jsonExit(['preview' => '']); } - DI::sysmsg()->addNotice(DI::l10n()->t('Empty post discarded.')); if ($return_path) { + DI::sysmsg()->addNotice(DI::l10n()->t('Empty post discarded.')); DI::baseUrl()->redirect($return_path); } throw new HTTPException\BadRequestException(DI::l10n()->t('Empty post discarded.')); } - // Check for hashtags in the body and repair or add hashtag links - if ($preview || $orig_post) { - $post['body'] = Item::setHashtags($post['body']); - } - // preview mode - prepare the body for display and send it via json if ($preview) { - // We set the datarray ID to -1 because in preview mode the dataray - // doesn't have an ID. - $post['id'] = -1; - $post['uri-id'] = -1; + // We have to preset some fields, so that the conversation can be displayed + $post['id'] = -1; + $post['uri-id'] = -1; $post['author-network'] = Protocol::DFRN; $post['author-updated'] = ''; - $post['author-gsid'] = 0; - $post['author-uri-id'] = ItemURI::getIdByURI($post['author-link']); - $post['owner-updated'] = ''; - $post['has-media'] = false; - $post['quote-uri-id'] = Item::getQuoteUriId($post['body'], $post['uid']); - $post['body'] = BBCode::removeSharedData($post['body']); - $post['writable'] = true; + $post['author-gsid'] = 0; + $post['author-uri-id'] = ItemURI::getIdByURI($post['author-link']); + $post['owner-updated'] = ''; + $post['has-media'] = false; + $post['quote-uri-id'] = Item::getQuoteUriId($post['body'], $post['uid']); + $post['body'] = BBCode::removeSharedData(Item::setHashtags($post['body'])); + $post['writable'] = true; - $o = DI::conversation()->create([$post], 'search', false, true); + $o = DI::conversation()->create([$post], Conversation::MODE_SEARCH, false, true); System::jsonExit(['preview' => $o]); } Hook::callAll('post_local',$post); - if (!empty($_REQUEST['scheduled_at'])) { - $scheduled_at = DateTimeFormat::convert($_REQUEST['scheduled_at'], 'UTC', $a->getTimeZone()); + unset($post['edit']); + unset($post['self']); + unset($post['api_source']); + + if (!empty($request['scheduled_at'])) { + $scheduled_at = DateTimeFormat::convert($request['scheduled_at'], 'UTC', DI::app()->getTimeZone()); if ($scheduled_at > DateTimeFormat::utcNow()) { unset($post['created']); unset($post['edited']); unset($post['commented']); unset($post['received']); unset($post['changed']); - unset($post['edit']); - unset($post['self']); - unset($post['api_source']); Post\Delayed::add($post['uri'], $post, Worker::PRIORITY_HIGH, Post\Delayed::PREPARED_NO_HOOK, $scheduled_at); item_post_return(DI::baseUrl(), $return_path); @@ -254,90 +306,14 @@ function item_post(App $a) { } $json = ['cancel' => 1]; - if (!empty($_REQUEST['jsreload'])) { - $json['reload'] = DI::baseUrl() . '/' . $_REQUEST['jsreload']; + if (!empty($request['jsreload'])) { + $json['reload'] = DI::baseUrl() . '/' . $request['jsreload']; } System::jsonExit($json); } - $post['uri-id'] = ItemURI::getIdByURI($post['uri']); - - $quote_uri_id = Item::getQuoteUriId($post['body'], $post['uid']); - if (!empty($quote_uri_id)) { - $post['quote-uri-id'] = $quote_uri_id; - $post['body'] = BBCode::removeSharedData($post['body']); - } - - if ($orig_post) { - $fields = [ - 'title' => $post['title'], - 'body' => $post['body'], - 'attach' => $post['attach'], - 'file' => $post['file'], - 'edited' => DateTimeFormat::utcNow(), - 'changed' => DateTimeFormat::utcNow() - ]; - - Item::update($fields, ['id' => $post_id]); - Item::updateDisplayCache($post['uri-id']); - - if ($return_path) { - DI::baseUrl()->redirect($return_path); - } - - throw new HTTPException\OKException(DI::l10n()->t('Post updated.')); - } - - unset($post['edit']); - unset($post['self']); - unset($post['api_source']); - - $post_id = Item::insert($post); - if (!$post_id) { - DI::sysmsg()->addNotice(DI::l10n()->t('Item wasn\'t stored.')); - if ($return_path) { - DI::baseUrl()->redirect($return_path); - } - - throw new HTTPException\InternalServerErrorException(DI::l10n()->t('Item wasn\'t stored.')); - } - - $post = Post::selectFirst(Item::ITEM_FIELDLIST, ['id' => $post_id]); - if (!DBA::isResult($post)) { - Logger::error('Item couldn\'t be fetched.', ['post_id' => $post_id]); - if ($return_path) { - DI::baseUrl()->redirect($return_path); - } - - throw new HTTPException\InternalServerErrorException(DI::l10n()->t('Item couldn\'t be fetched.')); - } - - if (!\Friendica\Content\Feature::isEnabled($post['uid'], 'explicit_mentions') && ($post['gravity'] == Item::GRAVITY_COMMENT)) { - Tag::createImplicitMentions($post['uri-id'], $post['thr-parent-id']); - } - - Hook::callAll('post_local_end', $post); - - $recipients = explode(',', $emailcc); - if (count($recipients)) { - foreach ($recipients as $recipient) { - $address = trim($recipient); - if (!strlen($address)) { - continue; - } - - $author = DBA::selectFirst('contact', ['thumb'], ['uid' => $uid, 'self' => true]); - - DI::emailer()->send(new ItemCCEMail(DI::app(), DI::l10n(), DI::baseUrl(), - $post, $address, $author['thumb'] ?? '')); - } - } - - Logger::debug('post_complete'); - - item_post_return(DI::baseUrl(), $return_path); - // NOTREACHED + return $post; } function item_post_return($baseurl, $return_path) @@ -392,6 +368,22 @@ function item_content(App $a) Contact\User::setBlocked($item['author-id'], DI::userSession()->getLocalUserId(), true); + if (DI::mode()->isAjax()) { + // ajax return: [, 0 (no perm) | ] + System::jsonExit([intval($args->get(2)), DI::userSession()->getLocalUserId()]); + } else { + item_redirect_after_action($item, $args->get(3)); + } + break; + + case 'ignore': + $item = Post::selectFirstForUser(DI::userSession()->getLocalUserId(), ['guid', 'author-id', 'parent', 'gravity'], ['id' => $args->get(2)]); + if (empty($item['author-id'])) { + throw new HTTPException\NotFoundException('Item not found'); + } + + Contact\User::setIgnored($item['author-id'], DI::userSession()->getLocalUserId(), true); + if (DI::mode()->isAjax()) { // ajax return: [, 0 (no perm) | ] System::jsonExit([intval($args->get(2)), DI::userSession()->getLocalUserId()]);