delete comment / reply working

This commit is contained in:
isUnknown 2024-10-30 16:32:13 +01:00
parent 58c08690f8
commit ac48b4166a
5 changed files with 131 additions and 59 deletions

View file

@ -19,53 +19,15 @@ Comments:
file: file:
uuid: file://s0lNtRA0Z7ybTCWG uuid: file://s0lNtRA0Z7ybTCWG
pageIndex: 1 pageIndex: 1
replies: replies: [ ]
- text: Un certain commentaire
page:
uri: projects/miss-dior-blooming-bouquet
title: Miss Dior Blooming Bouquet
file:
uuid: file://s0lNtRA0Z7ybTCWG
pageIndex: 1
replies: [ ]
text: Test de réponse
author:
name: Adrien Payet
email: adrien.payet@outlook.com
uuid: user://WWjXgPWk
role: admin
date: 2024-10-30T12:26:44+01:00
id: m2vskcko
type: comment
isRead: false
parentId: m2vsk6jn
-
page:
uri: projects/miss-dior-blooming-bouquet
title: Miss Dior Blooming Bouquet
file:
uuid: file://s0lNtRA0Z7ybTCWG
pageIndex: 1
replies: [ ]
text: deuxième réponse
author:
name: Adrien Payet
email: adrien.payet@outlook.com
uuid: user://WWjXgPWk
role: admin
date: 2024-10-30T12:27:42+01:00
id: m2vslkxg
type: comment
isRead: false
parentId: m2vsk6jn
text: Un premier commentaire
author: author:
name: Adrien Payet name: Adrien Payet
email: adrien.payet@outlook.com email: adrien.payet@outlook.com
uuid: user://WWjXgPWk uuid: user://WWjXgPWk
role: admin role: admin
date: 2024-10-30T12:26:37+01:00 date: 2024-10-30T16:26:22+01:00
id: m2vsk6jn id: m2w14iph
type: comment type: comment
isRead: false isRead: false
position: position:

View file

@ -7,14 +7,50 @@ return [
$json = file_get_contents('php://input'); $json = file_get_contents('php://input');
$data = json_decode($json); $data = json_decode($json);
$page = page($data->pageUri); $page = page($data->page->uri);
$file = $page->file($data->fileName); $file = $page->file($data->file->uuid);
$user = kirby()->user($data->userUuid); $isReply = $data->parentId ?? false;
$comments = $file->comments()->isEmpty() == true ? [] : Yaml::decode($file->comments()->value()); $comments = $file->comments()->isEmpty() == true ? [] : Yaml::decode($file->comments()->value());
unset($comments[$data->id] ); foreach ($comments as $key => &$comment) {
if ($isReply) {
if ($comment['id'] === $data->parentId) {
foreach ($comment['replies'] as $replyKey => $reply) {
if ($reply['id'] === $data->id) {
unset($comment['replies'][$replyKey]);
$comment['replies'] = array_values($comment['replies']);
}
}
}
} else {
if ($comment['id'] === $data->id) {
unset($comments[$key]);
}
}
}
$comments = array_values($comments); // Réindexe les commentaires
foreach (kirby()->users() as $user) {
try {
$notifications = $user->notifications()->isNotEmpty()
? Yaml::decode($user->notifications()->value())
: [];
foreach ($notifications as $key => $notification) {
if ($notification['id'] === $data->id) {
unset($notifications[$key]);
}
}
$user->update([
'notifications' => $notifications
]);
} catch (\Throwable $th) {
throw new Exception("Error updating notifications: " . $th->getMessage() . ' line ' . $th->getLine(), 1);
}
}
$newFile = $file->update([ $newFile = $file->update([
'comments' => $comments 'comments' => $comments

View file

@ -8,20 +8,36 @@
</template> </template>
<span class="comment__page">Page {{ comment.file.pageIndex }}</span> <span class="comment__page">Page {{ comment.file.pageIndex }}</span>
<time class="comment__date" :datetime="dayjs(comment.date).format('YYYY-MM-DD')">{{ <time
formatDate(comment.date) class="comment__date"
}}</time> :datetime="dayjs(comment.date).format('YYYY-MM-DD')"
>{{ formatDate(comment.date) }}</time
>
</p> </p>
</header> </header>
<p class="comment__body"> <p class="comment__body">
{{ comment.text }} {{ comment.text }}
</p> </p>
<footer v-if="comment.replies?.length > 0" class="comment__replies"> <footer class="comment__replies">
<p>{{ comment.replies.length }} réponse{{ comment.replies.length > 1 ? 's' : '' }}</p> <p v-if="comment.replies?.length > 0">
<!-- TODO: n'afficher que s'il s'agit du commentaire de l'utilisateur actuellement connecté --> {{ comment.replies.length }} réponse{{
<div class="comment__ctas | mt-8"> comment.replies.length > 1 ? "s" : ""
<button class="btn btn--transparent btn--icon btn--sm" data-icon="edit"><span class="sr-only">Éditer</span></button> }}
<button class="btn btn--transparent btn--icon btn--sm" data-icon="delete"><span class="sr-only">Supprimer</span></button> </p>
<div
v-if="comment.author.uuid === user.uuid"
class="comment__ctas | mt-8"
>
<button class="btn btn--transparent btn--icon btn--sm" data-icon="edit">
<span class="sr-only">Éditer</span>
</button>
<button
class="btn btn--transparent btn--icon btn--sm"
data-icon="delete"
@click="deleteComment($event, comment)"
>
<span class="sr-only">Supprimer</span>
</button>
</div> </div>
</footer> </footer>
</article> </article>
@ -30,6 +46,8 @@
<script setup> <script setup>
import dayjs from "dayjs"; import dayjs from "dayjs";
import "dayjs/locale/fr"; import "dayjs/locale/fr";
import { useUserStore } from "../../stores/user";
import { useApiStore } from "../../stores/api";
dayjs.locale("fr"); dayjs.locale("fr");
@ -38,6 +56,11 @@ const { comment, commentIndex } = defineProps({
commentIndex: Number, commentIndex: Number,
}); });
const emits = defineEmits(["update:file", "close:comment"]);
const { user } = useUserStore();
const api = useApiStore();
// Functions // Functions
function setStatus(comment) { function setStatus(comment) {
try { try {
@ -80,6 +103,15 @@ async function readNotification(notificationId) {
user.notifications = newNotifications; user.notifications = newNotifications;
} }
async function deleteComment(event, comment) {
event.stopPropagation();
const newFile = await api.deleteComment(comment);
emits("update:file", newFile);
if (comment.parentId) {
emits("close:comment");
}
}
</script> </script>
<style scoped> <style scoped>

View file

@ -10,6 +10,8 @@
:commentIndex="comments.length - commentIndex" :commentIndex="comments.length - commentIndex"
:key="comment.id" :key="comment.id"
@click="openedComment = comment" @click="openedComment = comment"
@update:file="changeFile"
@close:comment="closeComment"
/> />
</template> </template>
<template v-else> <template v-else>
@ -23,13 +25,20 @@
> >
<span>Retour à la liste</span> <span>Retour à la liste</span>
</button> </button>
<Comment :comment="openedComment" data-opened="true" /> <Comment
:comment="openedComment"
data-opened="true"
@update:file="changeFile"
@close:comment="closeComment"
/>
<div v-if="sortedReplies.length > 0" class="replies | flow"> <div v-if="sortedReplies.length > 0" class="replies | flow">
<Comment <Comment
v-for="(reply, commentIndex) in sortedReplies" v-for="(reply, commentIndex) in sortedReplies"
:comment="reply" :comment="reply"
:commentIndex="sortedReplies.length - commentIndex" :commentIndex="sortedReplies.length - commentIndex"
:key="reply.id" :key="reply.id"
@update:file="changeFile"
@close:comment="closeComment"
/> />
</div> </div>
</template> </template>
@ -154,6 +163,15 @@ async function addComment(newComment) {
isAddOpen.value = false; isAddOpen.value = false;
emits("update:file", newFile); emits("update:file", newFile);
} }
function changeFile(newFile) {
console.log(newFile);
emits("update:file", newFile);
}
function closeComment() {
openedComment.value = null;
}
</script> </script>
<style> <style>

View file

@ -144,6 +144,29 @@ export const useApiStore = defineStore("api", () => {
} }
} }
async function deleteComment(comment) {
const headers = {
method: "POST",
body: JSON.stringify(comment),
};
try {
const response = await fetch("/delete-comment.json", headers);
if (!response.ok) {
throw new Error(`HTTP error! status: ${response.status}`);
}
const newFile = await response.json();
return newFile;
} catch (error) {
console.error(
"Une erreur s'est produite lors de la suppression du commentaire :",
comment,
error
);
throw error;
}
}
async function replyComment(comment) { async function replyComment(comment) {
const headers = { const headers = {
method: "POST", method: "POST",
@ -198,6 +221,7 @@ export const useApiStore = defineStore("api", () => {
fetchData, fetchData,
fetchRoute, fetchRoute,
addComment, addComment,
deleteComment,
replyComment, replyComment,
readNotification, readNotification,
}; };