feat: добавить рабочий dashboard admin
- добавлен Mantine theme provider и AppShell layout\n- сгенерирован Backend API клиент и добавлены infra/business хуки\n- добавлены таблица assets, detail/presets panels и create asset modal
This commit is contained in:
@@ -0,0 +1,126 @@
|
||||
import { Anchor, Badge, Code, Group, Paper, ScrollArea, Skeleton, Stack, Table, Text, Title } from "@mantine/core"
|
||||
|
||||
import { ASSET_STATUS_COLORS, VARIANT_STATUS_COLORS } from "../../config/dashboard.config"
|
||||
import { formatDateTime } from "../../lib/format-date"
|
||||
import type { AssetDetailPanelProps } from "./types/asset-detail-panel-props.type"
|
||||
|
||||
/**
|
||||
* Детали выбранного asset и его variants.
|
||||
*
|
||||
* Используется для:
|
||||
* - отображения source metadata
|
||||
* - отображения статусов generated variants
|
||||
*/
|
||||
export const AssetDetailPanel = (props: AssetDetailPanelProps) => {
|
||||
const { overview, publicId } = props
|
||||
const { asset, variants } = overview
|
||||
|
||||
if (!publicId) {
|
||||
return (
|
||||
<Paper bg="white" p="xl" radius="xl" shadow="xs" withBorder>
|
||||
<Title order={2} size="h3">
|
||||
Asset detail
|
||||
</Title>
|
||||
<Text c="dimmed" mt="sm">
|
||||
Выберите asset из таблицы, чтобы увидеть source URL и variants.
|
||||
</Text>
|
||||
</Paper>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<Paper bg="white" p="xl" radius="xl" shadow="xs" withBorder>
|
||||
<Group align="start" justify="space-between" mb="lg">
|
||||
<div>
|
||||
<Title order={2} size="h3">
|
||||
Asset detail
|
||||
</Title>
|
||||
<Text c="dimmed" fz="sm">
|
||||
{publicId}
|
||||
</Text>
|
||||
</div>
|
||||
|
||||
{asset ? (
|
||||
<Badge color={ASSET_STATUS_COLORS[asset.status] ?? "gray"} radius="xl" variant="light">
|
||||
{asset.status}
|
||||
</Badge>
|
||||
) : null}
|
||||
</Group>
|
||||
|
||||
{overview.isLoading ? (
|
||||
<Skeleton height={260} radius="lg" />
|
||||
) : asset ? (
|
||||
<Stack gap="lg">
|
||||
<Stack gap={6}>
|
||||
<Text c="dimmed" fz="sm">
|
||||
Source URL
|
||||
</Text>
|
||||
<Anchor href={asset.sourceUrl} target="_blank">
|
||||
{asset.sourceUrl}
|
||||
</Anchor>
|
||||
</Stack>
|
||||
|
||||
<Group gap="xs">
|
||||
<Badge color="violet" radius="xl" variant="light">
|
||||
v{asset.currentVersion}
|
||||
</Badge>
|
||||
<Badge color="gray" radius="xl" variant="light">
|
||||
{asset.sourceHost}
|
||||
</Badge>
|
||||
<Badge color="gray" radius="xl" variant="light">
|
||||
updated {formatDateTime(asset.updatedAt)}
|
||||
</Badge>
|
||||
</Group>
|
||||
|
||||
<Stack gap="sm">
|
||||
<Group justify="space-between">
|
||||
<Title order={3} size="h4">
|
||||
Variants
|
||||
</Title>
|
||||
<Badge radius="xl" variant="light">
|
||||
{variants.length}
|
||||
</Badge>
|
||||
</Group>
|
||||
|
||||
{variants.length > 0 ? (
|
||||
<ScrollArea>
|
||||
<Table verticalSpacing="sm">
|
||||
<Table.Thead>
|
||||
<Table.Tr>
|
||||
<Table.Th>Preset</Table.Th>
|
||||
<Table.Th>Format</Table.Th>
|
||||
<Table.Th>Size</Table.Th>
|
||||
<Table.Th>Status</Table.Th>
|
||||
</Table.Tr>
|
||||
</Table.Thead>
|
||||
<Table.Tbody>
|
||||
{variants.map((variant) => (
|
||||
<Table.Tr key={variant.id}>
|
||||
<Table.Td>
|
||||
<Code>{variant.preset}</Code>
|
||||
</Table.Td>
|
||||
<Table.Td>{variant.format}</Table.Td>
|
||||
<Table.Td>
|
||||
{variant.width}x{variant.height || "auto"} q{variant.quality}
|
||||
</Table.Td>
|
||||
<Table.Td>
|
||||
<Badge color={VARIANT_STATUS_COLORS[variant.status] ?? "gray"} radius="xl" variant="light">
|
||||
{variant.status}
|
||||
</Badge>
|
||||
</Table.Td>
|
||||
</Table.Tr>
|
||||
))}
|
||||
</Table.Tbody>
|
||||
</Table>
|
||||
</ScrollArea>
|
||||
) : (
|
||||
<Text c="dimmed">Variants для текущей версии пока не созданы.</Text>
|
||||
)}
|
||||
</Stack>
|
||||
</Stack>
|
||||
) : (
|
||||
<Text c="dimmed">Asset не найден или ещё загружается.</Text>
|
||||
)}
|
||||
</Paper>
|
||||
)
|
||||
}
|
||||
Reference in New Issue
Block a user