Fix moving of tags table
This commit is contained in:
@ -53,7 +53,7 @@ model Artwork {
|
|||||||
albums Album[]
|
albums Album[]
|
||||||
categories ArtCategory[]
|
categories ArtCategory[]
|
||||||
colors ArtworkColor[]
|
colors ArtworkColor[]
|
||||||
tags ArtTag[]
|
tags Tag[] @relation("ArtworkTags")
|
||||||
variants FileVariant[]
|
variants FileVariant[]
|
||||||
|
|
||||||
@@index([colorStatus])
|
@@index([colorStatus])
|
||||||
@ -101,43 +101,7 @@ model ArtCategory {
|
|||||||
description String?
|
description String?
|
||||||
|
|
||||||
artworks Artwork[]
|
artworks Artwork[]
|
||||||
tags ArtTag[]
|
tagLinks TagCategory[]
|
||||||
}
|
|
||||||
|
|
||||||
model ArtTag {
|
|
||||||
id String @id @default(cuid())
|
|
||||||
createdAt DateTime @default(now())
|
|
||||||
updatedAt DateTime @updatedAt
|
|
||||||
sortIndex Int @default(0)
|
|
||||||
|
|
||||||
name String @unique
|
|
||||||
slug String @unique
|
|
||||||
isParent Boolean @default(false)
|
|
||||||
showOnAnimalPage Boolean @default(false)
|
|
||||||
|
|
||||||
description String?
|
|
||||||
|
|
||||||
aliases ArtTagAlias[]
|
|
||||||
artworks Artwork[]
|
|
||||||
categories ArtCategory[]
|
|
||||||
|
|
||||||
parentId String?
|
|
||||||
parent ArtTag? @relation("TagHierarchy", fields: [parentId], references: [id], onDelete: SetNull)
|
|
||||||
children ArtTag[] @relation("TagHierarchy")
|
|
||||||
}
|
|
||||||
|
|
||||||
model ArtTagAlias {
|
|
||||||
id String @id @default(cuid())
|
|
||||||
createdAt DateTime @default(now())
|
|
||||||
updatedAt DateTime @updatedAt
|
|
||||||
|
|
||||||
alias String @unique
|
|
||||||
|
|
||||||
tagId String
|
|
||||||
tag ArtTag @relation(fields: [tagId], references: [id], onDelete: Cascade)
|
|
||||||
|
|
||||||
@@unique([tagId, alias])
|
|
||||||
@@index([alias])
|
|
||||||
}
|
}
|
||||||
|
|
||||||
model Color {
|
model Color {
|
||||||
@ -248,6 +212,71 @@ model FileVariant {
|
|||||||
@@unique([artworkId, type])
|
@@unique([artworkId, type])
|
||||||
}
|
}
|
||||||
|
|
||||||
|
model Tag {
|
||||||
|
id String @id @default(cuid())
|
||||||
|
createdAt DateTime @default(now())
|
||||||
|
updatedAt DateTime @updatedAt
|
||||||
|
sortIndex Int @default(0)
|
||||||
|
|
||||||
|
name String @unique
|
||||||
|
slug String @unique
|
||||||
|
isVisible Boolean @default(true)
|
||||||
|
|
||||||
|
description String?
|
||||||
|
|
||||||
|
aliases TagAlias[]
|
||||||
|
categoryLinks TagCategory[]
|
||||||
|
categoryParents TagCategory[] @relation("TagCategoryParent")
|
||||||
|
artworks Artwork[] @relation("ArtworkTags")
|
||||||
|
commissionTypes CommissionType[] @relation("CommissionTypeTags")
|
||||||
|
miniatures Miniature[] @relation("MiniatureTags")
|
||||||
|
}
|
||||||
|
|
||||||
|
model TagAlias {
|
||||||
|
id String @id @default(cuid())
|
||||||
|
createdAt DateTime @default(now())
|
||||||
|
updatedAt DateTime @updatedAt
|
||||||
|
|
||||||
|
alias String @unique
|
||||||
|
|
||||||
|
tagId String
|
||||||
|
tag Tag @relation(fields: [tagId], references: [id], onDelete: Cascade)
|
||||||
|
|
||||||
|
@@unique([tagId, alias])
|
||||||
|
@@index([alias])
|
||||||
|
}
|
||||||
|
|
||||||
|
model TagCategory {
|
||||||
|
id String @id @default(cuid())
|
||||||
|
createdAt DateTime @default(now())
|
||||||
|
updatedAt DateTime @updatedAt
|
||||||
|
|
||||||
|
tagId String
|
||||||
|
categoryId String
|
||||||
|
|
||||||
|
isParent Boolean @default(false)
|
||||||
|
showOnAnimalPage Boolean @default(false)
|
||||||
|
parentTagId String?
|
||||||
|
|
||||||
|
tag Tag @relation(fields: [tagId], references: [id], onDelete: Cascade)
|
||||||
|
category ArtCategory @relation(fields: [categoryId], references: [id], onDelete: Cascade)
|
||||||
|
parentTag Tag? @relation("TagCategoryParent", fields: [parentTagId], references: [id], onDelete: SetNull)
|
||||||
|
|
||||||
|
@@unique([tagId, categoryId])
|
||||||
|
@@index([categoryId])
|
||||||
|
@@index([tagId])
|
||||||
|
@@index([parentTagId])
|
||||||
|
@@index([categoryId, parentTagId])
|
||||||
|
}
|
||||||
|
|
||||||
|
model Miniature {
|
||||||
|
id String @id @default(cuid())
|
||||||
|
createdAt DateTime @default(now())
|
||||||
|
updatedAt DateTime @updatedAt
|
||||||
|
|
||||||
|
tags Tag[] @relation("MiniatureTags")
|
||||||
|
}
|
||||||
|
|
||||||
model Commission {
|
model Commission {
|
||||||
id String @id @default(cuid())
|
id String @id @default(cuid())
|
||||||
createdAt DateTime @default(now())
|
createdAt DateTime @default(now())
|
||||||
@ -265,6 +294,8 @@ model CommissionType {
|
|||||||
|
|
||||||
description String?
|
description String?
|
||||||
|
|
||||||
|
tags Tag[] @relation("CommissionTypeTags")
|
||||||
|
|
||||||
options CommissionTypeOption[]
|
options CommissionTypeOption[]
|
||||||
extras CommissionTypeExtra[]
|
extras CommissionTypeExtra[]
|
||||||
customInputs CommissionTypeCustomInput[]
|
customInputs CommissionTypeCustomInput[]
|
||||||
|
|||||||
@ -30,14 +30,22 @@ function sortArtworks(a: SimpleArtwork, b: SimpleArtwork) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export default async function AnimalListPage() {
|
export default async function AnimalListPage() {
|
||||||
const tags = await prisma.artTag.findMany({
|
const tags = await prisma.tag.findMany({
|
||||||
where: { showOnAnimalPage: true },
|
where: {
|
||||||
|
isVisible: true,
|
||||||
|
categoryLinks: {
|
||||||
|
some: { category: { name: "Animal Studies" }, showOnAnimalPage: true },
|
||||||
|
},
|
||||||
|
},
|
||||||
select: {
|
select: {
|
||||||
id: true,
|
id: true,
|
||||||
name: true,
|
name: true,
|
||||||
slug: true,
|
slug: true,
|
||||||
sortIndex: true,
|
sortIndex: true,
|
||||||
parentId: true,
|
categoryLinks: {
|
||||||
|
where: { category: { name: "Animal Studies" } },
|
||||||
|
select: { parentTagId: true },
|
||||||
|
},
|
||||||
artworks: {
|
artworks: {
|
||||||
where: {
|
where: {
|
||||||
published: true,
|
published: true,
|
||||||
@ -50,10 +58,15 @@ export default async function AnimalListPage() {
|
|||||||
orderBy: [{ sortIndex: "asc" }, { name: "asc" }],
|
orderBy: [{ sortIndex: "asc" }, { name: "asc" }],
|
||||||
});
|
});
|
||||||
|
|
||||||
const byId = new Map(tags.map((t) => [t.id, t]));
|
const tagsWithParents = tags.map((t) => ({
|
||||||
const childrenByParentId = new Map<string, typeof tags>();
|
...t,
|
||||||
|
parentId: t.categoryLinks[0]?.parentTagId ?? null,
|
||||||
|
}));
|
||||||
|
|
||||||
for (const t of tags) {
|
const byId = new Map(tagsWithParents.map((t) => [t.id, t]));
|
||||||
|
const childrenByParentId = new Map<string, typeof tagsWithParents>();
|
||||||
|
|
||||||
|
for (const t of tagsWithParents) {
|
||||||
if (!t.parentId) continue;
|
if (!t.parentId) continue;
|
||||||
const arr = childrenByParentId.get(t.parentId) ?? [];
|
const arr = childrenByParentId.get(t.parentId) ?? [];
|
||||||
arr.push(t);
|
arr.push(t);
|
||||||
@ -64,12 +77,12 @@ export default async function AnimalListPage() {
|
|||||||
childrenByParentId.set(pid, arr.slice().sort(sortBySortIndexName));
|
childrenByParentId.set(pid, arr.slice().sort(sortBySortIndexName));
|
||||||
}
|
}
|
||||||
|
|
||||||
const parents = tags
|
const parents = tagsWithParents
|
||||||
.filter((t) => t.parentId === null)
|
.filter((t) => t.parentId === null)
|
||||||
.slice()
|
.slice()
|
||||||
.sort(sortBySortIndexName);
|
.sort(sortBySortIndexName);
|
||||||
|
|
||||||
const orphans = tags
|
const orphans = tagsWithParents
|
||||||
.filter((t) => t.parentId !== null && !byId.has(t.parentId))
|
.filter((t) => t.parentId !== null && !byId.has(t.parentId))
|
||||||
.slice()
|
.slice()
|
||||||
.sort(sortBySortIndexName);
|
.sort(sortBySortIndexName);
|
||||||
|
|||||||
@ -17,17 +17,28 @@ function parseTagsParam(tags: string | string[] | undefined): string[] {
|
|||||||
function expandSelectedWithChildren(
|
function expandSelectedWithChildren(
|
||||||
selectedSlugs: string[],
|
selectedSlugs: string[],
|
||||||
tagsForFilter: Array<{
|
tagsForFilter: Array<{
|
||||||
|
id: string;
|
||||||
slug: string;
|
slug: string;
|
||||||
children: Array<{ slug: string }>;
|
parentId: string | null;
|
||||||
}>,
|
}>,
|
||||||
) {
|
) {
|
||||||
const bySlug = new Map(tagsForFilter.map((t) => [t.slug, t]));
|
const bySlug = new Map(tagsForFilter.map((t) => [t.slug, t]));
|
||||||
|
const childrenByParentId = new Map<string, typeof tagsForFilter>();
|
||||||
|
|
||||||
|
for (const t of tagsForFilter) {
|
||||||
|
if (!t.parentId) continue;
|
||||||
|
const arr = childrenByParentId.get(t.parentId) ?? [];
|
||||||
|
arr.push(t);
|
||||||
|
childrenByParentId.set(t.parentId, arr);
|
||||||
|
}
|
||||||
|
|
||||||
const out = new Set(selectedSlugs);
|
const out = new Set(selectedSlugs);
|
||||||
|
|
||||||
for (const slug of selectedSlugs) {
|
for (const slug of selectedSlugs) {
|
||||||
const t = bySlug.get(slug);
|
const t = bySlug.get(slug);
|
||||||
if (!t) continue;
|
if (!t) continue;
|
||||||
for (const c of t.children ?? []) out.add(c.slug);
|
const children = childrenByParentId.get(t.id) ?? [];
|
||||||
|
for (const c of children) out.add(c.slug);
|
||||||
}
|
}
|
||||||
|
|
||||||
return Array.from(out);
|
return Array.from(out);
|
||||||
@ -41,24 +52,31 @@ export default async function AnimalStudiesPage({
|
|||||||
const { tags } = await searchParams;
|
const { tags } = await searchParams;
|
||||||
|
|
||||||
const selectedTagSlugs = parseTagsParam(tags);
|
const selectedTagSlugs = parseTagsParam(tags);
|
||||||
const tagsForFilter = await prisma.artTag.findMany({
|
const tagLinks = await prisma.tagCategory.findMany({
|
||||||
where: { showOnAnimalPage: true },
|
where: {
|
||||||
|
showOnAnimalPage: true,
|
||||||
|
category: { name: "Animal Studies" },
|
||||||
|
tag: { isVisible: true },
|
||||||
|
},
|
||||||
select: {
|
select: {
|
||||||
id: true,
|
parentTagId: true,
|
||||||
name: true,
|
tag: {
|
||||||
slug: true,
|
select: { id: true, name: true, slug: true, sortIndex: true },
|
||||||
sortIndex: true,
|
|
||||||
parentId: true,
|
|
||||||
parent: { select: { id: true, name: true, slug: true, sortIndex: true } },
|
|
||||||
children: {
|
|
||||||
where: { showOnAnimalPage: true },
|
|
||||||
select: { id: true, name: true, slug: true, sortIndex: true, parentId: true },
|
|
||||||
orderBy: [{ sortIndex: "asc" }, { name: "asc" }],
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
orderBy: [{ sortIndex: "asc" }, { name: "asc" }],
|
orderBy: [{ tag: { sortIndex: "asc" } }, { tag: { name: "asc" } }],
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const tagsForFilter = tagLinks.map((link) => ({
|
||||||
|
id: link.tag.id,
|
||||||
|
name: link.tag.name,
|
||||||
|
slug: link.tag.slug,
|
||||||
|
sortIndex: link.tag.sortIndex,
|
||||||
|
parentId: link.parentTagId,
|
||||||
|
parent: null,
|
||||||
|
children: [],
|
||||||
|
}));
|
||||||
|
|
||||||
const expandedTagSlugs = expandSelectedWithChildren(selectedTagSlugs, tagsForFilter);
|
const expandedTagSlugs = expandSelectedWithChildren(selectedTagSlugs, tagsForFilter);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
Reference in New Issue
Block a user