diff --git a/client/src/components/Toast/ToastContainer.tsx b/client/src/components/Toast/ToastContainer.tsx
index 781ecdc5..8cdd0f29 100644
--- a/client/src/components/Toast/ToastContainer.tsx
+++ b/client/src/components/Toast/ToastContainer.tsx
@@ -1,3 +1,4 @@
+import { AnimatePresence } from "framer-motion";
import { useToastStore } from "@stores/useToastStore";
import { Toast } from "./Toast";
import { ToastContainerStyle } from "./ToastContainer.style";
@@ -7,14 +8,16 @@ export const ToastContainer = () => {
return (
- {toasts.map((toast) => (
-
removeToast(toast.id)}
- />
- ))}
+
+ {toasts.map((toast) => (
+ removeToast(toast.id)}
+ />
+ ))}
+
);
};
diff --git a/client/src/components/sidebar/Sidebar.tsx b/client/src/components/sidebar/Sidebar.tsx
index fb9077be..a9bb76a7 100644
--- a/client/src/components/sidebar/Sidebar.tsx
+++ b/client/src/components/sidebar/Sidebar.tsx
@@ -7,7 +7,6 @@ import { useModal } from "@components/modal/useModal";
import { MAX_VISIBLE_PAGE } from "@src/constants/page";
import { AuthButton } from "@src/features/auth/AuthButton";
import { useSocketStore } from "@src/stores/useSocketStore";
-import { useToastStore } from "@src/stores/useToastStore";
import { Page } from "@src/types/page";
import { useIsSidebarOpen, useSidebarActions } from "@stores/useSidebarStore";
import { animation, contentVariants, sidebarVariants } from "./Sidebar.animation";
@@ -43,7 +42,6 @@ export const Sidebar = ({
const { isOpen, openModal, closeModal } = useModal();
const { sendPageDeleteOperation, clientId } = useSocketStore();
- const { addToast } = useToastStore();
const [isDeleteModalOpen, setIsDeleteModalOpen] = useState(false);
const [pageToDelete, setPageToDelete] = useState(null);
@@ -69,11 +67,10 @@ export const Sidebar = ({
return;
}
- addToast(`페이지(${pageToDelete!.title})가 삭제되었습니다.`);
-
sendPageDeleteOperation({
type: "pageDelete",
workspaceId: "default",
+ pageTitle: pageToDelete!.title,
pageId,
clientId,
});
diff --git a/client/src/features/workSpace/hooks/usePagesManage.ts b/client/src/features/workSpace/hooks/usePagesManage.ts
index 94299d5b..9aeec259 100644
--- a/client/src/features/workSpace/hooks/usePagesManage.ts
+++ b/client/src/features/workSpace/hooks/usePagesManage.ts
@@ -8,6 +8,7 @@ import { Page as CRDTPage } from "@noctaCrdt/Page";
import { WorkSpace } from "@noctaCrdt/WorkSpace";
import { useEffect, useState, useRef, useCallback } from "react";
import { useSocketStore } from "@src/stores/useSocketStore";
+import { useToastStore } from "@src/stores/useToastStore";
import { Page } from "@src/types/page";
const PAGE_OFFSET = 60;
@@ -17,6 +18,7 @@ export const usePagesManage = (workspace: WorkSpace | null, clientId: number | n
const { subscribeToPageOperations, sendPageCreateOperation, sendPageUpdateOperation } =
useSocketStore();
const subscriptionRef = useRef(false);
+ const { addToast } = useToastStore();
useEffect(() => {
if (!workspace) return;
if (subscriptionRef.current) return;
@@ -52,6 +54,7 @@ export const usePagesManage = (workspace: WorkSpace | null, clientId: number | n
addPage(newPage);
},
onRemotePageDelete: (operation) => {
+ addToast(`${operation.clientId}번 유저가 페이지(${operation.pageTitle})를 삭제하였습니다.`);
workspace.remotePageDelete?.({
pageId: operation.pageId,
workspaceId: operation.workspaceId,
diff --git a/client/src/stores/useToastStore.ts b/client/src/stores/useToastStore.ts
index 2be5146a..56758a24 100644
--- a/client/src/stores/useToastStore.ts
+++ b/client/src/stores/useToastStore.ts
@@ -9,10 +9,19 @@ interface ToastStore {
export const useToastStore = create((set) => ({
toasts: [],
- addToast: (message, duration = 3000) =>
+ addToast: (message, duration = 3000) => {
+ const id = Date.now();
set((state) => ({
- toasts: [...state.toasts, { id: Date.now(), message, duration }],
- })),
+ toasts: [...state.toasts, { id, message, duration }],
+ }));
+ // duration 후에 자동으로 해당 toast 제거
+ setTimeout(() => {
+ set((state) => ({
+ toasts: state.toasts.filter((toast) => toast.id !== id),
+ }));
+ }, duration);
+ },
+
removeToast: (id) =>
set((state) => ({
toasts: state.toasts.filter((toast) => toast.id !== id),