Files
frontend/app/(main)/page.tsx
T
Thanh Quy- wolf 0842960888 feat: enhance login functionality and add staff creation page
- Update LoginForm to handle staff role and redirect accordingly.
- Improve ProductsTab UI for better visibility when no products are found.
- Refactor ShiftCreateModal to use custom TimeInput component for better time handling.
- Add parseShiftDate utility in ShiftDetailModal for improved date parsing.
- Modify ShiftContext to handle shift deletion with proper error handling.
- Introduce feature-workflow-tracer skill for tracing feature workflows in the codebase.
- Add learning-assistant skill to support users in understanding concepts and code.
- Implement CreateStaffPage for manager to create new staff accounts with validation and error handling.
2026-05-14 16:51:21 +07:00

119 lines
3.8 KiB
TypeScript

"use client";
import { SearchBar } from "@/components/molecules/search-bar";
import { ProductGrid } from "@/components/organisms/product-grid";
import { useAuth } from "@/lib/auth-context";
import { eateryClient } from "@/lib/apollo-clients";
import { allEateriesQuery } from "@/lib/types";
import { gql } from "@apollo/client";
import { useQuery } from "@apollo/client/react";
import { useRouter } from "next/navigation";
import { useEffect, useState } from "react";
const GET_EATERY_COUNT = gql`
{
allEateries {
id
}
}
`;
function StaffHomePage() {
const [isSidebarOpen, setIsSidebarOpen] = useState(false);
const [searchQuery, setSearchQuery] = useState("");
useEffect(() => {
const mq = window.matchMedia("(min-width: 1024px)");
// eslint-disable-next-line react-hooks/set-state-in-effect
setIsSidebarOpen(mq.matches);
const handler = (e: MediaQueryListEvent) => setIsSidebarOpen(e.matches);
mq.addEventListener("change", handler);
return () => mq.removeEventListener("change", handler);
}, []);
return (
<div className="bg-background flex min-h-[calc(100vh-var(--spacing-header-height))] flex-col items-start">
{/* ── Body — same as Customer ── */}
<main className="min-w-0 w-full flex-1 px-4 py-6 md:px-6 lg:px-8">
<div className="mb-5 flex flex-col justify-between gap-3 sm:flex-row sm:items-center">
<SearchBar
value={searchQuery}
onChange={(q) => setSearchQuery(q)}
onClear={() => setSearchQuery("")}
placeholder="Search items..."
className="sm:max-w-xs"
/>
</div>
<ProductGrid searchQuery={searchQuery} isSidebarOpen={isSidebarOpen} />
</main>
</div>
);
}
export default function Home() {
const router = useRouter();
const { user, isInitialized } = useAuth();
const [isSidebarOpen, setIsSidebarOpen] = useState(false);
const [searchQuery, setSearchQuery] = useState("");
const { data, loading, error } = useQuery<allEateriesQuery>(
GET_EATERY_COUNT,
{
client: eateryClient,
fetchPolicy: "no-cache",
skip: user?.role === "staff",
},
);
useEffect(() => {
if (!loading && data) {
console.log(data);
const count = data.allEateries.length ?? 0;
if (count === 0) {
router.push("/manager-signup");
}
}
}, [data, loading, router]);
useEffect(() => {
const mq = window.matchMedia("(min-width: 1024px)");
// eslint-disable-next-line react-hooks/set-state-in-effect
setIsSidebarOpen(mq.matches);
const handler = (e: MediaQueryListEvent) => setIsSidebarOpen(e.matches);
mq.addEventListener("change", handler);
return () => mq.removeEventListener("change", handler);
}, []);
if (!isInitialized) return <div>Loading...</div>;
if (user?.role === "staff") return <StaffHomePage />;
if (loading) return <div>Loading...</div>;
if (error) return <div>Error: {error.message}</div>;
return (
<div className="bg-background flex min-h-[calc(100vh-var(--spacing-header-height))] items-start">
{/* ── Main content ── */}
<main className="min-w-0 flex-1 px-4 py-6 md:px-6 lg:px-8">
{/* ── Section heading + search bar ── */}
<div className="mb-5 flex flex-col justify-between gap-3 sm:flex-row sm:items-center">
<SearchBar
value={searchQuery}
onChange={(q) => {
setSearchQuery(q);
}}
onClear={() => setSearchQuery("")}
placeholder="Search items..."
className="sm:max-w-xs"
/>
</div>
{/* ── Product grid (organism handles mobile category menu + grid) ── */}
<ProductGrid searchQuery={searchQuery} isSidebarOpen={isSidebarOpen} />
</main>
</div>
);
}