/** * @param PrepareApiData $event */ public function loadTagsRelationship(PrepareApiData $event) { // Expose the complete tag list to clients by adding it as a // relationship to the /api/forum endpoint. Since the Forum model // doesn't actually have a tags relationship, we will manually load and // assign the tags data to it using an event listener. if ($event->isController(ShowForumController::class)) { $event->data['tags'] = Tag::whereVisibleTo($event->actor)->with('lastDiscussion')->get(); } }
/** * @param PrepareApiData $event */ public function addMetaTags(PrepareApiData $event) { if ($this->clientView && ($this->openGraph || $this->twitterCard)) { $data = []; switch (true) { case $event->isController(ShowDiscussionController::class): $data['url'] = $this->urlGenerator->toRoute('discussion', ['id' => $event->data->id . '-' . $event->data->slug]); $data['title'] = $this->plainText($event->data->title, 80); $post_id = $event->request->getQueryParams()['page']['near']; if ($post_id === null) { $data['description'] = $event->data->startPost ? $this->plainText($event->data->startPost->content, 150) : ''; } else { $post = array_key_exists((int) $post_id - 1, $event->data->posts) ? $event->data->posts[(int) $post_id - 1] : null; $data['url'] .= '/' . $post_id; if ($post) { $data['description'] = $this->plainText($post->content, 150); } else { $data['description'] = $event->data->startPost ? $this->plainText($event->data->startPost->content, 150) : ''; } } break; // case $event->isController(ListDiscussionsController::class): // $data['url'] = $this->urlGenerator->toRoute('user', ['username' => $event->data->username]); // $data['title'] = $this->plainText($event->data->username, 80); // $data['description'] = $event->data->bio ? $this->plainText($event->data->bio, 150) : ''; // break; // case $event->isController(ShowUserController::class): // $data['url'] = $this->urlGenerator->toRoute('user', ['username' => $event->data->username]); // $data['title'] = $this->plainText($event->data->username, 80); // $data['description'] = $event->data->bio ? $this->plainText($event->data->bio, 150) : ''; // break; // case $event->isController(ListDiscussionsController::class): // $data['url'] = $this->urlGenerator->toRoute('user', ['username' => $event->data->username]); // $data['title'] = $this->plainText($event->data->username, 80); // $data['description'] = $event->data->bio ? $this->plainText($event->data->bio, 150) : ''; // break; // case $event->isController(ShowUserController::class): // $data['url'] = $this->urlGenerator->toRoute('user', ['username' => $event->data->username]); // $data['title'] = $this->plainText($event->data->username, 80); // $data['description'] = $event->data->bio ? $this->plainText($event->data->bio, 150) : ''; // break; default: break; } $this->addOpenGraph($data); $this->addTwitterCard($data); } }
/** * @param PrepareApiData $event */ public function prepareApiData(PrepareApiData $event) { // For any API action that allows the 'flags' relationship to be // included, we need to preload this relationship onto the data (Post // models) so that we can selectively expose only the flags that the // user has permission to view. if ($event->isController(Controller\ShowDiscussionController::class)) { $posts = $event->data->getRelation('posts'); } if ($event->isController(Controller\ListPostsController::class)) { $posts = $event->data->all(); } if ($event->isController(Controller\ShowPostController::class)) { $posts = [$event->data]; } if ($event->isController(CreateFlagController::class)) { $posts = [$event->data->post]; } if (isset($posts)) { $actor = $event->request->getAttribute('actor'); $postsWithPermission = []; foreach ($posts as $post) { if (is_object($post)) { $post->setRelation('flags', null); if ($actor->can('viewFlags', $post->discussion)) { $postsWithPermission[] = $post; } } } if (count($postsWithPermission)) { (new Collection($postsWithPermission))->load('flags', 'flags.user'); } } }
/** * @param PrepareApiData $event */ public function PrepareApiData(PrepareApiData $event) { if ($event->isController(ShowForumController::class)) { $event->data['links'] = Link::get(); } }
/** * Apply visibility permissions to API data. * * Each post in an API document has a relationship with posts that have * mentioned it (mentionedBy). This listener will manually filter these * additional posts so that the user can't see any posts which they don't * have access to. * * @param PrepareApiData $event */ public function filterVisiblePosts(PrepareApiData $event) { // Firstly we gather a list of posts contained within the API document. // This will vary according to the API endpoint that is being accessed. if ($event->isController(ShowDiscussionController::class)) { $posts = $event->data->posts; } elseif ($event->isController(ShowPostController::class)) { $posts = [$event->data]; } elseif ($event->isController(ListPostsController::class)) { $posts = $event->data; } if (isset($posts)) { $posts = array_filter((array) $posts, 'is_object'); $ids = []; // Once we have the posts, construct a list of the IDs of all of // the posts that they have been mentioned in. We can then filter // this list of IDs to weed out all of the ones which the user is // not meant to see. foreach ($posts as $post) { $ids = array_merge($ids, $post->mentionedBy->pluck('id')->all()); } $ids = $this->posts->filterVisibleIds($ids, $event->actor); // Finally, go back through each of the posts and filter out any // of the posts in the relationship data that we now know are // invisible to the user. foreach ($posts as $post) { $post->setRelation('mentionedBy', $post->mentionedBy->filter(function ($post) use($ids) { return array_search($post->id, $ids) !== false; })); } } }