PluginProbe
FluentCommunity – Ultra-Fast High-Performance Social Network, Community, LMS & Online Courses / 2.8.0
FluentCommunity – Ultra-Fast High-Performance Social Network, Community, LMS & Online Courses v2.8.0
2.10.0 2.10.01 2.9.1 2.9.0 2.8.1 2.8.0 2.7.7 2.7.5 2.7.0 2.6.01 2.6.0 2.5.0 2.4.01 trunk 1.0.90 1.0.91 1.0.92 1.0.93 1.0.94 1.0.95 1.0.96 1.0.97 1.0.98 1.0.99 1.1.0 All 77 releases
fluent-community / app / Http / Controllers / CommentsController.php

CommentsController.php in FluentCommunity – Ultra-Fast High-Performance Social Network, Community, LMS & Online Courses 2.8.0, at app/Http/Controllers/CommentsController.php

737 lines 27.1 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2
3 namespace FluentCommunity\App\Http\Controllers;
4
5 use FluentCommunity\App\Models\Media;
6 use FluentCommunity\App\Models\User;
7 use FluentCommunity\App\Services\CustomSanitizer;
8 use FluentCommunity\App\Services\FeedsHelper;
9 use FluentCommunity\App\Services\Helper;
10 use FluentCommunity\App\Services\ProfileHelper;
11 use FluentCommunity\Framework\Http\Request\Request;
12 use FluentCommunity\App\Models\Comment;
13 use FluentCommunity\App\Models\Feed;
14 use FluentCommunity\App\Models\Reaction;
15 use FluentCommunity\Framework\Support\Arr;
16
17 class CommentsController extends Controller
18 {
19 public function getComments(Request $request, $feed_id)
20 {
21 $feed = Feed::withoutGlobalScopes()
22 ->byUserAccess(get_current_user_id())
23 ->findOrFail($feed_id);
24
25 if ($feed->status != 'published' && !$feed->hasEditAccess($this->getUserId())) {
26 return $this->sendError([
27 'message' => __('Sorry, you do not have permission to view this post', 'fluent-community')
28 ], 404);
29 }
30
31 $canViewComments = apply_filters('fluent_community/can_view_comments_' . $feed->type, true, $feed);
32
33 if (!$canViewComments) {
34 return [
35 'comments' => []
36 ];
37 }
38
39 $comments = Comment::where('post_id', $feed->id)
40 ->byContentModerationAccessStatus($this->getUser())
41 ->orderBy('created_at', 'asc')
42 ->with([
43 'xprofile' => function ($q) {
44 $q->select(ProfileHelper::getXProfilePublicFields());
45 }
46 ])
47 ->whereHas('xprofile', function ($q) {
48 $q->where('status', 'active');
49 })
50 ->get();
51
52 $comments = apply_filters('fluent_community/comments_query_response', $comments, $request->all());
53
54 $userId = $this->getUserId();
55
56 if ($userId) {
57 $likedIds = FeedsHelper::getLikedIdsByUserFeedId($feed->id, get_current_user_id());
58 if ($likedIds) {
59 $comments->each(function ($comment) use ($likedIds) {
60 if (in_array($comment->id, $likedIds)) {
61 $comment->liked = 1;
62 }
63 });
64 }
65 }
66
67 $data = [
68 'comments' => $comments
69 ];
70
71 return apply_filters('fluent_community/comments_api_response', $data, $request->all());
72 }
73
74 public function store(Request $request, $feedId)
75 {
76 $user = $this->getUser(true);
77 do_action('fluent_community/check_rate_limit/create_comment', $user);
78
79 $text = $this->validateCommentText($request->all());
80 $feed = Feed::withoutGlobalScopes()->findOrFail($feedId);
81
82 if ($feed->status != 'published') {
83 return $this->sendError([
84 'message' => __('This post is not published yet', 'fluent-community')
85 ]);
86 }
87
88 $this->verifyCreateCommentPermission($feed);
89
90 $requestData = $request->all();
91
92 // Check for duplicate (only for comments with text)
93 if ($text) {
94 $skipDuplicateCheck = apply_filters('fluent_community/disable_duplicate_comment_check', false, get_current_user_id(), $feed->id);
95 if (!$skipDuplicateCheck) {
96 $exist = Comment::where('user_id', get_current_user_id())
97 ->where('message', $text)
98 ->where('post_id', $feed->id)
99 ->first();
100
101 if ($exist) {
102 return $this->sendError([
103 'message' => __('No duplicate comment please!', 'fluent-community')
104 ]);
105 }
106 }
107 }
108
109 [$markdown, $inlineMedias] = FeedsHelper::replaceImageUrlsWithRealMediaArchive($text);
110 $mentions = FeedsHelper::getMentions($markdown, $feed->space_id, true);
111 $commentHtml = $this->generateCommentHtml($markdown, $mentions);
112
113 $commentData = $this->prepareCommentData($feed->id, $text, $commentHtml);
114
115 if (!empty($requestData['parent_id'])) {
116 $parentId = (int)$requestData['parent_id'];
117 $parentComment = Comment::where('id', $parentId)
118 ->where('post_id', $feed->id)
119 ->first();
120
121 if (!$parentComment) {
122 return $this->sendError([
123 'message' => __('Invalid parent comment', 'fluent-community')
124 ]);
125 }
126
127 $commentData['parent_id'] = $parentId;
128 }
129
130 [$commentData, $mediaItems] = $this->prepareCommentMedia($commentData, $requestData);
131
132 $commentData['is_admin'] = $user->hasSpacePermission('community_moderator', $feed->space);
133
134 if ($mentionUserIds = Arr::get($mentions, 'user_ids', [])) {
135 $commentData['meta']['mentioned_user_ids'] = $mentionUserIds;
136 }
137
138 do_action('fluent_community/before_comment_create', $commentData, $feed);
139
140 $commentData = apply_filters('fluent_community/comment/comment_data', $commentData, $feed);
141
142 $comment = Comment::create($commentData);
143
144 $feed->comments_count = $feed->comments_count + 1;
145 $feed->save();
146
147
148 // Merge and save all media in one loop
149 $mediaItems = $mediaItems ? (is_array($mediaItems) ? $mediaItems : [$mediaItems]) : [];
150
151 if ($inlineMedias) {
152 $mediaItems = array_merge($mediaItems, $inlineMedias);
153 }
154
155 if ($mediaItems) {
156 foreach ($mediaItems as $media) {
157 $media->fill([
158 'is_active' => 1,
159 'feed_id' => $feed->id,
160 'object_source' => 'comment',
161 'sub_object_id' => $comment->id
162 ]);
163 $media->save();
164 }
165 }
166
167 $this->loadCommentRelations($comment);
168
169 if ($comment->status != 'published') {
170 do_action('fluent_community/comment/new_comment_' . $comment->status, $comment, $feed);
171 /* translators: %$s is replaced by the status of the comment */
172 $message = sprintf(__('Your comment has been marked as %s', 'fluent-community'), $comment->status);
173 $response = [
174 'comment' => $comment,
175 'message' => $message
176 ];
177 return apply_filters('fluent_community/comment/new_comment_response', $response, $comment);
178 }
179
180 do_action('fluent_community/comment_added_' . $feed->type, $comment, $feed);
181 do_action('fluent_community/comment_added', $comment, $feed, Arr::get($mentions, 'users', []));
182
183 return [
184 'comment' => $comment,
185 'message' => __('Comment has been added', 'fluent-community'),
186 ];
187 }
188
189 public function update(Request $request, $feedId, $commentId)
190 {
191 $text = $this->validateCommentText($request->all());
192
193 $feed = Feed::withoutGlobalScopes()->findOrFail($feedId);
194 $this->verifySpacePermission($feed);
195
196 $requestData = $request->all();
197 $comment = Comment::findOrFail($commentId);
198
199 if ($comment->post_id != $feed->id) {
200 return $this->sendError([
201 'message' => __('Invalid comment', 'fluent-community')
202 ]);
203 }
204
205 $user = $this->getUser(true);
206
207 $requestData['is_admin'] = $user->hasPermissionOrInCurrentSpace('community_moderator', $feed->space);
208
209 if ($comment->user_id != get_current_user_id() && !$user->can('edit_any_comment', $feed->space)) {
210 return $this->sendError([
211 'message' => __('You are not allowed to edit this comment', 'fluent-community')
212 ]);
213 }
214
215 [$markdown, $inlineMedias] = FeedsHelper::replaceImageUrlsWithRealMediaArchive($text, $feed);
216
217 $mentions = FeedsHelper::getMentions($markdown, $feed->space_id);
218
219 $commentHtml = $this->generateCommentHtml($markdown, $mentions);
220
221 $commentData = $this->prepareCommentData($feed->id, $text, $commentHtml);
222
223 [$commentData, $mediaItems] = $this->prepareCommentMedia($commentData, $requestData, $comment);
224
225 $commentData = apply_filters('fluent_community/comment/update_comment_data', $commentData, $feed, $requestData, $comment);
226
227 $comment->fill($commentData);
228
229 $dirty = $comment->getDirty();
230
231 if ($dirty) {
232 $comment->save();
233 }
234
235 // Merge and save all media in one loop
236 $mediaItems = $mediaItems ? (is_array($mediaItems) ? $mediaItems : [$mediaItems]) : [];
237
238 if ($inlineMedias) {
239 $mediaItems = array_merge($mediaItems, $inlineMedias);
240 }
241
242 $allMediaIds = [];
243
244 if ($mediaItems) {
245 foreach ($mediaItems as $media) {
246 $media->fill([
247 'is_active' => 1,
248 'feed_id' => $feed->id,
249 'object_source' => 'comment',
250 'sub_object_id' => $comment->id
251 ]);
252 $media->save();
253 $allMediaIds[] = $media->id;
254 }
255 }
256
257 // Remove old media not in current list
258 $otherMedias = Media::where('object_source', 'comment')
259 ->when($allMediaIds, function ($q) use ($allMediaIds) {
260 $q->whereNotIn('id', $allMediaIds);
261 })
262 ->where('sub_object_id', $comment->id)
263 ->get();
264
265 if (!$otherMedias->isEmpty()) {
266 do_action('fluent_community/comment/media_deleted', $otherMedias);
267 }
268
269 $this->loadCommentRelations($comment);
270
271 if ($dirty) {
272 do_action('fluent_community/comment_updated', $comment, $feed);
273 do_action('fluent_community/comment_updated_' . $feed->type, $comment, $feed);
274 }
275
276 return [
277 'comment' => $comment,
278 'message' => __('Comment has been updated', 'fluent-community'),
279 ];
280 }
281
282 public function patchComment(Request $request, $feedId, $commentId)
283 {
284 $feed = Feed::withoutGlobalScopes()->findOrFail($feedId);
285
286 $comment = Comment::findOrFail($commentId);
287
288 if ($comment->post_id != $feed->id) {
289 return $this->sendError([
290 'message' => __('Invalid comment', 'fluent-community')
291 ]);
292 }
293
294 $user = $this->getUser(true);
295
296 $isMod = $user && $user->hasPermissionOrInCurrentSpace('community_moderator', $feed->space);
297 $isAdmin = $user && $user->hasPermissionOrInCurrentSpace('community_admin', $feed->space);
298
299 if (!$isMod && !$isAdmin) {
300 return $this->sendError([
301 'message' => __('You do not have permission to perform this action', 'fluent-community')
302 ]);
303 }
304
305 $allData = $request->all();
306 $validKeys = ['is_sticky'];
307
308 $data = Arr::only($allData, $validKeys);
309
310 $data = array_map('intval', $data);
311
312 if (isset($data['is_sticky'])) {
313 if ($comment->parent_id) {
314 return $this->sendError([
315 'message' => __('You cannot pin a reply comment', 'fluent-community')
316 ]);
317 }
318
319 $data['is_sticky'] = $data['is_sticky'] ? 1 : 0;
320 if ($data['is_sticky']) {
321 Comment::where('post_id', $feed->id)->update(['is_sticky' => 0]);
322 }
323 }
324
325 if ($data) {
326 $comment->fill($data);
327 $dirty = $comment->getDirty();
328 if ($dirty) {
329 $comment->save();
330 do_action('fluent_community/comment/updated', $comment, $dirty);
331 }
332 }
333
334 return apply_filters('fluent_community/comment/patch_comment_response', [
335 'comment' => $comment,
336 'message' => __('Comment updated', 'fluent-community')
337 ], $comment, $feed, $request->all());
338 }
339
340 private function prepareCommentMedia($commentData, $requestData, $exisitngComment = null)
341 {
342 $mediaImages = Arr::get($requestData, 'media_images', []);
343
344 if ($mediaImages) {
345 if ($exisitngComment) {
346 $mediaItems = [];
347 $mediaData = [];
348 foreach ($mediaImages as $mediaImage) {
349 $id = Arr::get($mediaImage, 'media_id');
350 if ($id) {
351 $media = Media::where('sub_object_id', $exisitngComment->id)
352 ->where('object_source', 'comment')
353 ->find($id);
354 } else {
355 $media = Helper::getMediaFromUrl($mediaImage);
356 }
357
358 if ($media) {
359 $mediaItems[] = $media;
360 $mediaData[] = [
361 'media_id' => $media->id,
362 'url' => $media->public_url,
363 'type' => 'image',
364 'width' => Arr::get($media->settings, 'width'),
365 'height' => Arr::get($media->settings, 'height'),
366 'provider' => Arr::get($media->settings, 'provider', 'uploader')
367 ];
368 }
369 }
370 $commentData['meta']['media_items'] = $mediaData;
371 return [$commentData, $mediaItems];
372 }
373
374 $uploadedImages = Helper::getMediaByProvider($mediaImages);
375 if ($uploadedImages) {
376 $mediaItems = Helper::getMediaItemsFromUrl($uploadedImages);
377 if ($mediaItems) {
378 $mediaPreviews = [];
379 foreach ($mediaItems as $mediaItem) {
380 $mediaData = [
381 'media_id' => $mediaItem->id,
382 'url' => $mediaItem->public_url,
383 'type' => 'image',
384 'width' => Arr::get($mediaItem->settings, 'width'),
385 'height' => Arr::get($mediaItem->settings, 'height'),
386 'provider' => Arr::get($mediaItem->settings, 'provider', 'uploader')
387 ];
388
389 $mediaPreviews[] = array_filter($mediaData);
390 }
391 $commentData['meta']['media_items'] = $mediaPreviews;
392 return [$commentData, $mediaItems];
393 }
394 }
395 }
396
397 if (empty($requestData['meta']['media_preview']['image'])) {
398 return [$commentData, []];
399 }
400
401 if ($exisitngComment) {
402 $image = sanitize_url(Arr::get($requestData, 'meta.media_preview.image', ''));
403 $existingMedia = Media::where('media_url', $image)
404 ->where('object_source', 'comment')
405 ->where('sub_object_id', $exisitngComment->id)
406 ->first();
407
408 if ($existingMedia) {
409 $commentData['meta'] = $exisitngComment->meta;
410 return [$commentData, [$existingMedia]];
411 }
412 }
413
414 // type/provider reach :class bindings and width/height a :style binding in
415 // _MediaPreview.vue. Neither is an executable sink, but the stored values are
416 // request-supplied so they are normalised here rather than trusted.
417 $commentData['meta']['media_preview'] = array_filter([
418 'image' => sanitize_url(Arr::get($requestData, 'meta.media_preview.image', '')),
419 'type' => sanitize_text_field(Arr::get($requestData, 'meta.media_preview.type', 'image')),
420 'provider' => sanitize_text_field(Arr::get($requestData, 'meta.media_preview.provider', '')),
421 'height' => (int) Arr::get($requestData, 'meta.media_preview.height', 0),
422 'width' => (int) Arr::get($requestData, 'meta.media_preview.width', 0),
423 ]);
424
425 return [$commentData, []];
426 }
427
428 private function validateCommentText($data)
429 {
430 $text = trim(Arr::get($data, 'comment'));
431 $text = CustomSanitizer::unslashMarkdown($text);
432
433 // Decode HTML entities (e.g., &#x20; for space) and strip all whitespace for validation
434 $textForValidation = html_entity_decode($text, ENT_QUOTES | ENT_HTML5, 'UTF-8');
435 $textForValidation = preg_replace('/\s+/u', '', $textForValidation);
436
437 $hasMedia = Arr::get($data, 'media_images', []) || Arr::get($data, 'meta.media_preview.image', false);
438
439 $isReply = !empty($data['parent_id']);
440 if (!$textForValidation && !$hasMedia) {
441 if ($isReply) {
442 throw new \Exception(esc_html__('Reply cannot be empty.', 'fluent-community'), 422);
443 } else {
444 throw new \Exception(esc_html__('Comment cannot be empty.', 'fluent-community'), 422);
445 }
446 }
447
448 $maxCommentLength = apply_filters('fluent_community/max_comment_char_length', 10000);
449 if ($text && strlen($text) > $maxCommentLength) {
450 /* translators: %s is the maximum allowed character count */
451 throw new \Exception(esc_html(sprintf(__('The comment is too long. Please keep it under %s characters.', 'fluent-community'), number_format($maxCommentLength))), 422);
452 }
453
454 return $text;
455 }
456
457 private function verifyCreateCommentPermission($feed)
458 {
459 if (Arr::get($feed->meta, 'comments_disabled') === 'yes') {
460 throw new \Exception(esc_html__('Comments are disabled for this post', 'fluent-community'));
461 }
462
463 $this->verifySpacePermission($feed);
464 }
465
466 private function verifySpacePermission($feed)
467 {
468 if ($feed->space_id && $feed->space) {
469 $user = $this->getUser(true);
470 $user->verifySpacePermission('can_comment', $feed->space);
471
472 if ($feed->space->type == 'course' && Arr::get($feed->space->settings, 'disable_comments') === 'yes') {
473 throw new \Exception(esc_html__('Comments are disabled for this course', 'fluent-community'));
474 }
475 }
476 }
477
478 private function generateCommentHtml($text, $mentions)
479 {
480 $htmlText = $mentions ? $mentions['text'] : $text;
481 return wp_kses_post(FeedsHelper::mdToHtml($htmlText));
482 }
483
484 private function prepareCommentData($feedId, $text, $commentHtml)
485 {
486 return [
487 'post_id' => $feedId,
488 'message' => $text,
489 'message_rendered' => $commentHtml,
490 'type' => 'comment',
491 'meta' => [],
492 ];
493 }
494
495 private function loadCommentRelations($comment)
496 {
497 $comment->load('media');
498 $comment->load([
499 'xprofile' => function ($q) {
500 $q->select(ProfileHelper::getXProfilePublicFields());
501 }
502 ]);
503 }
504
505 public function addOrRemovePostReact(Request $request, $feed_id)
506 {
507 $userId = get_current_user_id();
508 $feed = Feed::withoutGlobalScopes()->byUserAccess($userId)->findOrFail($feed_id);
509 $type = $request->get('react_type', 'like');
510 $type = in_array($type, ['like', 'bookmark'], true) ? $type : 'like';
511 $willRemove = $request->get('remove');
512
513 if ($feed->status != 'published') {
514 return $this->sendError([
515 'message' => __('This post is not published yet', 'fluent-community')
516 ]);
517 }
518
519 if (!$willRemove && (int) $userId === (int) $feed->user_id && apply_filters('fluent_community/disable_self_post_react', false, $feed)) {
520 return $this->sendError([
521 'message' => __('You cannot react to your own post', 'fluent-community')
522 ]);
523 }
524
525 $react = Reaction::where('user_id', $userId)
526 ->where('object_id', $feed->id)
527 ->where('type', $type)
528 ->objectType('feed')
529 ->first();
530
531 if ($willRemove) {
532 if ($react) {
533 $react->delete();
534 if ($type == 'like') {
535 $feed->reactions_count = $feed->reactions_count - 1;
536 $feed->timestamps = false; // Don't update the updated_at timestamp
537 $feed->save();
538 do_action('fluent_community/feed/react_removed', $feed);
539 }
540 }
541
542 return [
543 'message' => __('Reaction has been removed', 'fluent-community'),
544 'new_count' => $feed->reactions_count
545 ];
546 }
547
548 if ($react) {
549 return [
550 'message' => __('You have already reacted to this post', 'fluent-community'),
551 'new_count' => $feed->reactions_count
552 ];
553 }
554
555 $react = Reaction::create([
556 'user_id' => get_current_user_id(),
557 'object_id' => $feed->id,
558 'type' => $type,
559 'object_type' => 'feed'
560 ]);
561
562 if ($type == 'like') {
563 $feed->reactions_count = $feed->reactions_count + 1;
564 $feed->timestamps = false; // Don't update the updated_at timestamp
565 $feed->save();
566
567 $react->load('xprofile');
568 do_action('fluent_community/feed/react_added', $react, $feed);
569 }
570
571 return [
572 'message' => __('Reaction has been added', 'fluent-community'),
573 'new_count' => $feed->reactions_count
574 ];
575 }
576
577 public function deleteComment(Request $request, $feedId, $commentId)
578 {
579 $feed = Feed::withoutGlobalScopes()->findOrFail($feedId);
580 $comment = Comment::findOrFail($commentId);
581
582 if ($comment->post_id != $feed->id) {
583 return $this->sendError([
584 'message' => __('Invalid comment', 'fluent-community')
585 ]);
586 }
587
588 $user = User::find(get_current_user_id());
589 if ($comment->user_id != get_current_user_id() && !$user->can('delete_any_comment', $feed->space)) {
590 return $this->sendError([
591 'message' => __('You are not allowed to delete this comment', 'fluent-community')
592 ]);
593 }
594
595 do_action('fluent_community/before_comment_delete', $comment);
596
597 if ($comment->media) {
598 do_action('fluent_community/comment/media_deleted', $comment->media);
599 }
600
601 $comment->delete();
602
603 $feed->comments_count = Comment::where('post_id', $feed->id)->count();
604 $feed->timestamps = false; // Don't update the updated_at timestamp
605 $feed->save();
606
607 do_action('fluent_community/comment_deleted_' . $feed->type, $commentId, $feed);
608 do_action('fluent_community/comment_deleted', $commentId, $feed);
609
610 return [
611 'message' => __('Selected comment has been deleted', 'fluent-community')
612 ];
613 }
614
615 public function toggleReaction(Request $request, $feedId, $commentId)
616 {
617 $feed = Feed::withoutGlobalScopes()->byUserAccess(get_current_user_id())->findOrFail($feedId);
618 $comment = Comment::findOrFail($commentId);
619
620 if ($comment->post_id != $feed->id) {
621 return $this->sendError([
622 'message' => __('Invalid comment', 'fluent-community')
623 ]);
624 }
625
626 $user = User::findOrFail(get_current_user_id());
627
628 if ($feed->space_id) {
629 $user->verifySpacePermission('registered', $feed->space);
630 }
631
632 $userId = get_current_user_id();
633 $reactionState = !!$request->get('state', false);
634
635 if ($reactionState && (int) $userId === (int) $comment->user_id && apply_filters('fluent_community/disable_self_comment_react', false, $feed)) {
636 return $this->sendError([
637 'message' => __('You cannot react to your own comment', 'fluent-community')
638 ]);
639 }
640
641 if ($reactionState) {
642 // add or update the reaction
643 $reaction = Reaction::firstOrCreate([
644 'user_id' => get_current_user_id(),
645 'object_id' => $comment->id,
646 'object_type' => 'comment',
647 'parent_id' => $feed->id
648 ]);
649
650 if ($reaction->wasRecentlyCreated) {
651 $comment->reactions_count = $comment->reactions_count + 1;
652 $comment->save();
653 do_action('fluent_community/comment/react_added', $reaction, $comment, $feed);
654 }
655 } else {
656 // remove the reaction
657 $deleted = Reaction::where('user_id', get_current_user_id())
658 ->where('object_id', $comment->id)
659 ->where('object_type', 'comment')
660 ->delete();
661
662 if ($deleted) {
663 $comment->reactions_count = $comment->reactions_count - 1;
664 $comment->save();
665 do_action('fluent_community/comment/react_removed', $comment, $feed);
666 }
667 }
668
669 return [
670 'message' => __('Reaction has been toggled', 'fluent-community'),
671 'reactions_count' => $comment->reactions_count,
672 'liked' => $reactionState
673 ];
674 }
675
676 public function show(Request $request, $id)
677 {
678
679 $testComment = Comment::query()->findOrFail($id);
680
681 $comment = Comment::byContentModerationAccessStatus($this->getUser(), $testComment->space)
682 ->with([
683 'xprofile' => function ($q) {
684 return $q->select(ProfileHelper::getXProfilePublicFields());
685 }
686 ])->findOrFail($id);
687
688 // Just to verify the permission
689 Feed::withoutGlobalScopes()
690 ->byUserAccess($this->getUserId())
691 ->findOrFail($comment->post_id);
692
693 if ($request->get('context') == 'edit') {
694 $meta = $comment->meta;
695 unset($comment->meta);
696 $images = Arr::get($meta, 'media_items', []);
697 if ($images) {
698 $comment->media_images = $images;
699 } else {
700 $preview = Arr::get($meta, 'media_preview', []);
701 if ($preview) {
702 $previewUrl = Arr::get($preview, 'image');
703 $provider = Arr::get($preview, 'provider');
704 if ($previewUrl && $provider == 'uploader') {
705 $media = Media::where('media_url', $previewUrl)
706 ->where('object_source', 'comment')
707 ->where('sub_object_id', $comment->id)
708 ->first();
709 if ($media) {
710 $comment->media_images = [
711 [
712 'media_id' => $media->id,
713 'url' => $media->public_url,
714 'type' => $media->media_type,
715 'width' => Arr::get($media->settings, 'width'),
716 'height' => Arr::get($media->settings, 'height'),
717 'provider' => Arr::get($media->settings, 'provider', 'uploader')
718 ]
719 ];
720 }
721 } else {
722 $comment->meta = [
723 'media_preview' => $preview
724 ];
725 }
726 }
727 }
728 }
729
730 $data = [
731 'comment' => $comment
732 ];
733
734 return apply_filters('fluent_community/comment_api_response', $data, $request->all());
735 }
736 }
737