1
0
Fork 0
mirror of https://github.com/muerwre/vault-frontend.git synced 2025-04-25 04:46:40 +07:00

let users like comments

This commit is contained in:
Fedor Katurov 2023-11-01 20:56:47 +06:00
parent 822f51f5de
commit bd802ede10
22 changed files with 332 additions and 154 deletions

View file

@ -1,11 +1,33 @@
import { useCallback } from 'react';
import { useCallback, useRef } from 'react';
import { apiLockComment, apiPostComment } from '~/api/node';
import { CancelTokenSource } from 'axios';
import axios from 'axios';
import { apiLikeComment, apiLockComment, apiPostComment } from '~/api/node';
import { useGetComments } from '~/hooks/comments/useGetComments';
import { IComment } from '~/types';
import { showErrorToast } from '~/utils/errors/showToast';
const updateComment =
(id: number, data: Partial<IComment>) => (pages?: IComment[][]) =>
pages?.map((comments) =>
comments.map((comment) =>
comment.id === id ? { ...comment, ...data } : comment,
),
);
const transformComment =
(id: number, cb: (val: IComment) => IComment) => (pages?: IComment[][]) =>
pages?.map((comments) =>
comments.map((comment) => (comment.id === id ? cb(comment) : comment)),
);
const insertComment = (data: IComment) => (pages?: IComment[][]) =>
pages?.map((list, index) => (index === 0 ? [data, ...list] : list));
export const useNodeComments = (nodeId: number, fallbackData?: IComment[]) => {
const likeAbortController = useRef<CancelTokenSource>();
const {
comments,
isLoading,
@ -17,7 +39,7 @@ export const useNodeComments = (nodeId: number, fallbackData?: IComment[]) => {
} = useGetComments(nodeId, fallbackData);
const onDelete = useCallback(
async (id: IComment['id'], isLocked: boolean) => {
async (id: number, isLocked: boolean) => {
try {
const { deleted_at } = await apiLockComment({ id, nodeId, isLocked });
@ -25,15 +47,7 @@ export const useNodeComments = (nodeId: number, fallbackData?: IComment[]) => {
return;
}
await mutate(
(prev) =>
prev?.map((list) =>
list.map((comment) =>
comment.id === id ? { ...comment, deleted_at } : comment,
),
),
false,
);
await mutate(updateComment(id, { deleted_at }), false);
} catch (error) {
showErrorToast(error);
}
@ -51,34 +65,57 @@ export const useNodeComments = (nodeId: number, fallbackData?: IComment[]) => {
// Comment was created
if (!comment.id) {
await mutate(
data.map((list, index) =>
index === 0 ? [result.comment, ...list] : list,
),
false,
);
return result.comment;
await mutate(insertComment(result.comment), false);
} else {
await mutate(updateComment(comment.id, result.comment), false);
}
await mutate(
(prev) =>
prev?.map((list) =>
list.map((it) =>
it.id === result.comment.id ? { ...it, ...result.comment } : it,
),
),
false,
);
return result.comment;
},
[data, mutate, nodeId],
);
const sendLikeRequest = useCallback(
async (id: number, liked: boolean) => {
if (likeAbortController.current) {
likeAbortController.current.cancel();
}
likeAbortController.current = axios.CancelToken.source();
await apiLikeComment(
nodeId,
id,
{ liked },
{ cancelToken: likeAbortController.current?.token },
);
likeAbortController.current = undefined;
},
[nodeId],
);
const onLike = useCallback(
async (id: number, liked: boolean) => {
const increment = liked ? 1 : -1;
await mutate(
transformComment(id, (val) => ({
...val,
liked,
like_count: (val.like_count ?? 0) + increment,
})),
false,
);
sendLikeRequest(id, liked).catch(showErrorToast);
},
[mutate, sendLikeRequest],
);
return {
onLoadMoreComments,
onDelete,
onLike,
comments,
hasMore,
isLoading,