import {
    Button,
    Container,
    Flex,
    Heading,
    SkeletonText,
    Table,
    TableContainer,
    Tbody,
    Td,
    Th,
    Thead,
    Tr,
} from "@chakra-ui/react"
import { useQuery, useQueryClient } from "@tanstack/react-query"
import { createFileRoute, useNavigate } from "@tanstack/react-router"
import { useEffect } from "react"
import { z } from "zod"
import moment from 'moment';
import { ClientMessagesService } from "../../client"
import ActionsMenu from "../../components/Common/ActionsMenu"


const messagesSearchSchema = z.object({
    page: z.number().catch(1),
})

export const Route = createFileRoute("/_layout/clientMessages")({
    component: Messages,
    validateSearch: (search) => messagesSearchSchema.parse(search),
})

const PER_PAGE = 100

function getMessagesQueryOptions({ page }: { page: number }) {
    return {
        queryFn: () =>
            ClientMessagesService.readMessages({ skip: (page - 1) * PER_PAGE, limit: PER_PAGE }),
        queryKey: ["messages", { page }],
    }
}

function MessagesTable() {
    const queryClient = useQueryClient()
    const { page } = Route.useSearch()
    const navigate = useNavigate({ from: Route.fullPath })
    const setPage = (page: number) =>
        navigate({ search: (prev) => ({ ...prev, page }) })

    const {
        data: messages,
        isPending,
        isPlaceholderData,
    } = useQuery({
        ...getMessagesQueryOptions({ page }),
        placeholderData: (prevData) => prevData,
    })

    const hasNextPage = !isPlaceholderData && messages?.data.length === PER_PAGE
    const hasPreviousPage = page > 1
    messages?.data.sort((a, b) => new Date(b.created_at).getTime() - new Date(a.created_at).getTime())
    useEffect(() => {
        if (hasNextPage) {
            queryClient.prefetchQuery(getMessagesQueryOptions({ page: page + 1 }))
        }
    }, [page, queryClient, hasNextPage])

    return (
        <>
            <TableContainer>
                <Table size={{ base: "sm", md: "md" }}>
                    <Thead>
                        <Tr>
                            <Th>id</Th>
                            <Th>Name</Th>
                            <Th>Phone</Th>
                            <Th>Email</Th>
                            <Th>Message</Th>
                            <Th>Created</Th>
                            <Th>Actions</Th>
                        </Tr>
                    </Thead>
                    {isPending ? (
                        <Tbody>
                            <Tr>
                                {new Array(4).fill(null).map((_, index) => (
                                    <Td key={index}>
                                        <SkeletonText noOfLines={1} paddingBlock="16px" />
                                    </Td>
                                ))}
                            </Tr>
                        </Tbody>
                    ) : (
                        <Tbody>
                            {messages?.data.map((message) => (
                                <Tr key={message.id} opacity={isPlaceholderData ? 0.5 : 1}>
                                    <Td isTruncated maxWidth="50">{message.id}</Td>
                                    <Td maxWidth="150px">
                                        {message.name}
                                    </Td>
                                    <Td maxWidth="150px">
                                        {message.phone}
                                    </Td>
                                    <Td maxWidth="150px">
                                        {message.email}
                                    </Td>
                                    <Td whiteSpace="pre-line" maxWidth="250px">
                                        {message.message}
                                    </Td>
                                    <Td maxWidth="150px">
                                        {moment(message.created_at).utcOffset("+08:00").format('DD-MM-YYYY HH:mm')}
                                    </Td>
                                    <Td>
                                        <ActionsMenu type={"Message"} value={message} />
                                    </Td>
                                </Tr>
                            ))}
                        </Tbody>
                    )}
                </Table>
            </TableContainer>
            <Flex
                gap={4}
                alignItems="center"
                mt={4}
                direction="row"
                justifyContent="flex-end"
            >
                <Button onClick={() => setPage(page - 1)} isDisabled={!hasPreviousPage}>
                    Previous
                </Button>
                <span>Page {page}</span>
                <Button isDisabled={!hasNextPage} onClick={() => setPage(page + 1)}>
                    Next
                </Button>
            </Flex>
        </>
    )
}

function Messages() {
    return (
        <Container maxW="full">
            <Heading size="lg" textAlign={{ base: "center", md: "left" }} pt={12}>
                Messages Management
            </Heading>
            <MessagesTable />
        </Container>
    )
}
