db: remove table suffix from schemas
This commit is contained in:
@@ -1,11 +1,5 @@
|
|||||||
import { desc, eq, like } from "drizzle-orm";
|
import { desc, eq, like } from "drizzle-orm";
|
||||||
import {
|
import { anime, animeSongLinks, artists, groups, songs } from "$lib/db/schema";
|
||||||
animeSongLinksTable,
|
|
||||||
animeTable,
|
|
||||||
artistsTable,
|
|
||||||
groupsTable,
|
|
||||||
songsTable,
|
|
||||||
} from "$lib/db/schema";
|
|
||||||
import type { ClientDb } from "./index";
|
import type { ClientDb } from "./index";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -31,18 +25,14 @@ export async function getAnimeList(db: ClientDb, limit = DEFAULT_LIST_LIMIT) {
|
|||||||
// Explicit selection keeps payload small and gives a stable, inferred return type
|
// Explicit selection keeps payload small and gives a stable, inferred return type
|
||||||
return db
|
return db
|
||||||
.select({
|
.select({
|
||||||
annId: animeTable.annId,
|
annId: anime.annId,
|
||||||
mainName: animeTable.mainName,
|
mainName: anime.mainName,
|
||||||
year: animeTable.year,
|
year: anime.year,
|
||||||
seasonId: animeTable.seasonId,
|
seasonId: anime.seasonId,
|
||||||
malId: animeTable.malId,
|
malId: anime.malId,
|
||||||
})
|
})
|
||||||
.from(animeTable)
|
.from(anime)
|
||||||
.orderBy(
|
.orderBy(desc(anime.year), desc(anime.seasonId), desc(anime.annId))
|
||||||
desc(animeTable.year),
|
|
||||||
desc(animeTable.seasonId),
|
|
||||||
desc(animeTable.annId),
|
|
||||||
)
|
|
||||||
.limit(safeLimit);
|
.limit(safeLimit);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -65,19 +55,15 @@ export async function searchAnimeByName(
|
|||||||
|
|
||||||
return db
|
return db
|
||||||
.select({
|
.select({
|
||||||
annId: animeTable.annId,
|
annId: anime.annId,
|
||||||
mainName: animeTable.mainName,
|
mainName: anime.mainName,
|
||||||
year: animeTable.year,
|
year: anime.year,
|
||||||
seasonId: animeTable.seasonId,
|
seasonId: anime.seasonId,
|
||||||
malId: animeTable.malId,
|
malId: anime.malId,
|
||||||
})
|
})
|
||||||
.from(animeTable)
|
.from(anime)
|
||||||
.where(like(animeTable.mainName, pattern))
|
.where(like(anime.mainName, pattern))
|
||||||
.orderBy(
|
.orderBy(desc(anime.year), desc(anime.seasonId), desc(anime.annId))
|
||||||
desc(animeTable.year),
|
|
||||||
desc(animeTable.seasonId),
|
|
||||||
desc(animeTable.annId),
|
|
||||||
)
|
|
||||||
.limit(safeLimit);
|
.limit(safeLimit);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -93,43 +79,37 @@ export async function searchAnimeByName(
|
|||||||
export async function getAnimeWithSongsByAnnId(db: ClientDb, annId: number) {
|
export async function getAnimeWithSongsByAnnId(db: ClientDb, annId: number) {
|
||||||
const animeRows = await db
|
const animeRows = await db
|
||||||
.select({
|
.select({
|
||||||
annId: animeTable.annId,
|
annId: anime.annId,
|
||||||
mainName: animeTable.mainName,
|
mainName: anime.mainName,
|
||||||
year: animeTable.year,
|
year: anime.year,
|
||||||
seasonId: animeTable.seasonId,
|
seasonId: anime.seasonId,
|
||||||
malId: animeTable.malId,
|
malId: anime.malId,
|
||||||
})
|
})
|
||||||
.from(animeTable)
|
.from(anime)
|
||||||
.where(eq(animeTable.annId, annId))
|
.where(eq(anime.annId, annId))
|
||||||
.limit(1);
|
.limit(1);
|
||||||
|
|
||||||
const anime = animeRows[0];
|
const foundAnime = animeRows[0];
|
||||||
if (!anime) return null;
|
if (!foundAnime) return null;
|
||||||
|
|
||||||
const rows = await db
|
const rows = await db
|
||||||
.select({
|
.select({
|
||||||
annSongId: animeSongLinksTable.annSongId,
|
annSongId: animeSongLinks.annSongId,
|
||||||
type: animeSongLinksTable.type,
|
type: animeSongLinks.type,
|
||||||
number: animeSongLinksTable.number,
|
number: animeSongLinks.number,
|
||||||
|
|
||||||
songName: songsTable.name,
|
songName: songs.name,
|
||||||
fileName: songsTable.fileName,
|
fileName: songs.fileName,
|
||||||
|
|
||||||
artistName: artistsTable.name,
|
artistName: artists.name,
|
||||||
groupName: groupsTable.name,
|
groupName: groups.name,
|
||||||
})
|
})
|
||||||
.from(animeSongLinksTable)
|
.from(animeSongLinks)
|
||||||
.innerJoin(
|
.innerJoin(songs, eq(songs.annSongId, animeSongLinks.annSongId))
|
||||||
songsTable,
|
.leftJoin(artists, eq(artists.songArtistId, songs.songArtistId))
|
||||||
eq(songsTable.annSongId, animeSongLinksTable.annSongId),
|
.leftJoin(groups, eq(groups.songGroupId, songs.songGroupId))
|
||||||
)
|
.where(eq(animeSongLinks.annId, annId))
|
||||||
.leftJoin(
|
.orderBy(desc(animeSongLinks.type), desc(animeSongLinks.number));
|
||||||
artistsTable,
|
|
||||||
eq(artistsTable.songArtistId, songsTable.songArtistId),
|
|
||||||
)
|
|
||||||
.leftJoin(groupsTable, eq(groupsTable.songGroupId, songsTable.songGroupId))
|
|
||||||
.where(eq(animeSongLinksTable.annId, annId))
|
|
||||||
.orderBy(desc(animeSongLinksTable.type), desc(animeSongLinksTable.number));
|
|
||||||
|
|
||||||
return {
|
return {
|
||||||
anime,
|
anime,
|
||||||
|
|||||||
@@ -14,21 +14,21 @@ import amqGroupsJson from "../../../data/amq-groups.json" with { type: "json" };
|
|||||||
import amqSongsJson from "../../../data/amq-songs.json" with { type: "json" };
|
import amqSongsJson from "../../../data/amq-songs.json" with { type: "json" };
|
||||||
import { db } from "./index";
|
import { db } from "./index";
|
||||||
import {
|
import {
|
||||||
animeGenresTable,
|
anime,
|
||||||
animeNamesTable,
|
animeGenres,
|
||||||
animeSongLinksTable,
|
animeNames,
|
||||||
animeTable,
|
animeSongLinks,
|
||||||
animeTagsTable,
|
animeTags,
|
||||||
artistAltNamesTable,
|
artistAltNames,
|
||||||
artistGroupsTable,
|
artistGroups,
|
||||||
artistsTable,
|
artists,
|
||||||
genresTable,
|
genres,
|
||||||
groupAltNamesTable,
|
groupAltNames,
|
||||||
groupArtistMembersTable,
|
groupArtistMembers,
|
||||||
groupGroupMembersTable,
|
groupGroupMembers,
|
||||||
groupsTable,
|
groups,
|
||||||
songsTable,
|
songs,
|
||||||
tagsTable,
|
tags,
|
||||||
} from "./schema";
|
} from "./schema";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -169,15 +169,15 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
const anime = animeParsed.data;
|
const animeData = animeParsed.data;
|
||||||
const songs = songsParsed.data;
|
const songsData = songsParsed.data;
|
||||||
const artists = artistsParsed.data;
|
const artistsData = artistsParsed.data;
|
||||||
const groups = groupsParsed.data;
|
const groupsData = groupsParsed.data;
|
||||||
|
|
||||||
if (verbose) {
|
if (verbose) {
|
||||||
// eslint-disable-next-line no-console
|
// eslint-disable-next-line no-console
|
||||||
console.info(
|
console.info(
|
||||||
`AMQ import: ${anime.length} anime, ${songs.length} songs, ${artists.length} artists, ${groups.length} groups`,
|
`AMQ import: ${animeData.length} anime, ${songsData.length} songs, ${artistsData.length} artists, ${groupsData.length} groups`,
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -185,45 +185,45 @@ export async function importAmqData(
|
|||||||
db.transaction(() => {
|
db.transaction(() => {
|
||||||
if (wipeFirst) {
|
if (wipeFirst) {
|
||||||
// Child tables first, then parents (respect FKs)
|
// Child tables first, then parents (respect FKs)
|
||||||
db.delete(animeSongLinksTable).run();
|
db.delete(animeSongLinks).run();
|
||||||
db.delete(animeNamesTable).run();
|
db.delete(animeNames).run();
|
||||||
db.delete(animeGenresTable).run();
|
db.delete(animeGenres).run();
|
||||||
db.delete(animeTagsTable).run();
|
db.delete(animeTags).run();
|
||||||
|
|
||||||
// artist/group graph tables
|
// artist/group graph tables
|
||||||
db.delete(groupGroupMembersTable).run();
|
db.delete(groupGroupMembers).run();
|
||||||
db.delete(groupArtistMembersTable).run();
|
db.delete(groupArtistMembers).run();
|
||||||
db.delete(artistGroupsTable).run();
|
db.delete(artistGroups).run();
|
||||||
db.delete(groupAltNamesTable).run();
|
db.delete(groupAltNames).run();
|
||||||
db.delete(artistAltNamesTable).run();
|
db.delete(artistAltNames).run();
|
||||||
|
|
||||||
db.delete(animeTable).run();
|
db.delete(anime).run();
|
||||||
|
|
||||||
// songs referenced by anime_song_links; delete after links wiped
|
// songs referenced by anime_song_links; delete after links wiped
|
||||||
db.delete(songsTable).run();
|
db.delete(songs).run();
|
||||||
|
|
||||||
// groups referenced by graph tables
|
// groups referenced by graph tables
|
||||||
db.delete(groupsTable).run();
|
db.delete(groups).run();
|
||||||
|
|
||||||
// artists referenced by graph tables
|
// artists referenced by graph tables
|
||||||
db.delete(artistsTable).run();
|
db.delete(artists).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
// 2a) Insert artists (core)
|
// 2a) Insert artists (core)
|
||||||
{
|
{
|
||||||
const artistRows = artists.map((a) => ({
|
const artistRows = artistsData.map((a) => ({
|
||||||
songArtistId: a.songArtistId,
|
songArtistId: a.songArtistId,
|
||||||
name: a.name,
|
name: a.name,
|
||||||
}));
|
}));
|
||||||
|
|
||||||
for (const batch of chunk(artistRows, batchSize)) {
|
for (const batch of chunk(artistRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(artistsTable)
|
db.insert(artists)
|
||||||
.values(batch)
|
.values(batch)
|
||||||
.onConflictDoUpdate({
|
.onConflictDoUpdate({
|
||||||
target: artistsTable.songArtistId,
|
target: artists.songArtistId,
|
||||||
set: {
|
set: {
|
||||||
name: artistsTable.name,
|
name: artists.name,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
.run();
|
.run();
|
||||||
@@ -232,19 +232,19 @@ export async function importAmqData(
|
|||||||
|
|
||||||
// 2a.1) Insert groups (core)
|
// 2a.1) Insert groups (core)
|
||||||
{
|
{
|
||||||
const groupRows = groups.map((g) => ({
|
const groupRows = groupsData.map((g) => ({
|
||||||
songGroupId: g.songGroupId,
|
songGroupId: g.songGroupId,
|
||||||
name: g.name,
|
name: g.name,
|
||||||
}));
|
}));
|
||||||
|
|
||||||
for (const batch of chunk(groupRows, batchSize)) {
|
for (const batch of chunk(groupRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(groupsTable)
|
db.insert(groups)
|
||||||
.values(batch)
|
.values(batch)
|
||||||
.onConflictDoUpdate({
|
.onConflictDoUpdate({
|
||||||
target: groupsTable.songGroupId,
|
target: groups.songGroupId,
|
||||||
set: {
|
set: {
|
||||||
name: groupsTable.name,
|
name: groups.name,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
.run();
|
.run();
|
||||||
@@ -255,14 +255,14 @@ export async function importAmqData(
|
|||||||
// For these join tables, easiest/most consistent is replace-all (delete then insert),
|
// For these join tables, easiest/most consistent is replace-all (delete then insert),
|
||||||
// since they’re derived arrays and can change over time.
|
// since they’re derived arrays and can change over time.
|
||||||
{
|
{
|
||||||
db.delete(artistGroupsTable).run();
|
db.delete(artistGroups).run();
|
||||||
db.delete(groupArtistMembersTable).run();
|
db.delete(groupArtistMembers).run();
|
||||||
db.delete(groupGroupMembersTable).run();
|
db.delete(groupGroupMembers).run();
|
||||||
db.delete(artistAltNamesTable).run();
|
db.delete(artistAltNames).run();
|
||||||
db.delete(groupAltNamesTable).run();
|
db.delete(groupAltNames).run();
|
||||||
|
|
||||||
// artist -> groups
|
// artist -> groups
|
||||||
const artistGroupRows = artists.flatMap((a) =>
|
const artistGroupRows = artistsData.flatMap((a) =>
|
||||||
a.inGroups.map((songGroupId) => ({
|
a.inGroups.map((songGroupId) => ({
|
||||||
songArtistId: a.songArtistId,
|
songArtistId: a.songArtistId,
|
||||||
songGroupId,
|
songGroupId,
|
||||||
@@ -270,11 +270,11 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
for (const batch of chunk(artistGroupRows, batchSize)) {
|
for (const batch of chunk(artistGroupRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(artistGroupsTable).values(batch).run();
|
db.insert(artistGroups).values(batch).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
// group -> artist members
|
// group -> artist members
|
||||||
const groupArtistMemberRows = groups.flatMap((g) =>
|
const groupArtistMemberRows = groupsData.flatMap((g) =>
|
||||||
g.artistMembers.map((songArtistId) => ({
|
g.artistMembers.map((songArtistId) => ({
|
||||||
songGroupId: g.songGroupId,
|
songGroupId: g.songGroupId,
|
||||||
songArtistId,
|
songArtistId,
|
||||||
@@ -282,11 +282,11 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
for (const batch of chunk(groupArtistMemberRows, batchSize)) {
|
for (const batch of chunk(groupArtistMemberRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(groupArtistMembersTable).values(batch).run();
|
db.insert(groupArtistMembers).values(batch).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
// group -> group members
|
// group -> group members
|
||||||
const groupGroupMemberRows = groups.flatMap((g) =>
|
const groupGroupMemberRows = groupsData.flatMap((g) =>
|
||||||
g.groupMembers.map((memberSongGroupId) => ({
|
g.groupMembers.map((memberSongGroupId) => ({
|
||||||
songGroupId: g.songGroupId,
|
songGroupId: g.songGroupId,
|
||||||
memberSongGroupId,
|
memberSongGroupId,
|
||||||
@@ -294,11 +294,11 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
for (const batch of chunk(groupGroupMemberRows, batchSize)) {
|
for (const batch of chunk(groupGroupMemberRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(groupGroupMembersTable).values(batch).run();
|
db.insert(groupGroupMembers).values(batch).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
// artist alt names: { songArtistId, name } (stored as altSongArtistId in DB)
|
// artist alt names: { songArtistId, name } (stored as altSongArtistId in DB)
|
||||||
const artistAltNameRows = artists.flatMap((a) =>
|
const artistAltNameRows = artistsData.flatMap((a) =>
|
||||||
a.altNames.map((alt) => ({
|
a.altNames.map((alt) => ({
|
||||||
songArtistId: a.songArtistId,
|
songArtistId: a.songArtistId,
|
||||||
altSongArtistId: alt.songArtistId,
|
altSongArtistId: alt.songArtistId,
|
||||||
@@ -307,11 +307,11 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
for (const batch of chunk(artistAltNameRows, batchSize)) {
|
for (const batch of chunk(artistAltNameRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(artistAltNamesTable).values(batch).run();
|
db.insert(artistAltNames).values(batch).run();
|
||||||
}
|
}
|
||||||
|
|
||||||
// group alt names: { songGroupId, name } where object.songGroupId is the context
|
// group alt names: { songGroupId, name } where object.songGroupId is the context
|
||||||
const groupAltNameRows = groups.flatMap((g) =>
|
const groupAltNameRows = groupsData.flatMap((g) =>
|
||||||
g.altNames.map((alt) => ({
|
g.altNames.map((alt) => ({
|
||||||
songGroupId: g.songGroupId,
|
songGroupId: g.songGroupId,
|
||||||
contextSongGroupId: alt.songGroupId,
|
contextSongGroupId: alt.songGroupId,
|
||||||
@@ -320,13 +320,13 @@ export async function importAmqData(
|
|||||||
);
|
);
|
||||||
for (const batch of chunk(groupAltNameRows, batchSize)) {
|
for (const batch of chunk(groupAltNameRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(groupAltNamesTable).values(batch).run();
|
db.insert(groupAltNames).values(batch).run();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// 2b) Insert songs
|
// 2b) Insert songs
|
||||||
{
|
{
|
||||||
const songRows = songs.map((s) => ({
|
const songRows = songsData.map((s) => ({
|
||||||
annSongId: s.annSongId,
|
annSongId: s.annSongId,
|
||||||
songId: s.songId,
|
songId: s.songId,
|
||||||
name: s.name,
|
name: s.name,
|
||||||
@@ -345,21 +345,21 @@ export async function importAmqData(
|
|||||||
|
|
||||||
for (const batch of chunk(songRows, batchSize)) {
|
for (const batch of chunk(songRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(songsTable)
|
db.insert(songs)
|
||||||
.values(batch)
|
.values(batch)
|
||||||
.onConflictDoUpdate({
|
.onConflictDoUpdate({
|
||||||
target: songsTable.annSongId,
|
target: songs.annSongId,
|
||||||
set: {
|
set: {
|
||||||
songId: songsTable.songId,
|
songId: songs.songId,
|
||||||
name: songsTable.name,
|
name: songs.name,
|
||||||
category: songsTable.category,
|
category: songs.category,
|
||||||
fileName: songsTable.fileName,
|
fileName: songs.fileName,
|
||||||
songArtistId: songsTable.songArtistId,
|
songArtistId: songs.songArtistId,
|
||||||
songGroupId: songsTable.songGroupId,
|
songGroupId: songs.songGroupId,
|
||||||
composerArtistId: songsTable.composerArtistId,
|
composerArtistId: songs.composerArtistId,
|
||||||
composerGroupId: songsTable.composerGroupId,
|
composerGroupId: songs.composerGroupId,
|
||||||
arrangerArtistId: songsTable.arrangerArtistId,
|
arrangerArtistId: songs.arrangerArtistId,
|
||||||
arrangerGroupId: songsTable.arrangerGroupId,
|
arrangerGroupId: songs.arrangerGroupId,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
.run();
|
.run();
|
||||||
@@ -368,7 +368,7 @@ export async function importAmqData(
|
|||||||
|
|
||||||
// 2c) Insert anime and its normalized children
|
// 2c) Insert anime and its normalized children
|
||||||
{
|
{
|
||||||
const animeRows = anime.map((a) => ({
|
const animeRows = animeData.map((a) => ({
|
||||||
annId: a.annId,
|
annId: a.annId,
|
||||||
aniListId: a.aniListId,
|
aniListId: a.aniListId,
|
||||||
malId: a.malId,
|
malId: a.malId,
|
||||||
@@ -387,24 +387,24 @@ export async function importAmqData(
|
|||||||
|
|
||||||
for (const batch of chunk(animeRows, batchSize)) {
|
for (const batch of chunk(animeRows, batchSize)) {
|
||||||
if (batch.length === 0) continue;
|
if (batch.length === 0) continue;
|
||||||
db.insert(animeTable)
|
db.insert(anime)
|
||||||
.values(batch)
|
.values(batch)
|
||||||
.onConflictDoUpdate({
|
.onConflictDoUpdate({
|
||||||
target: animeTable.annId,
|
target: anime.annId,
|
||||||
set: {
|
set: {
|
||||||
aniListId: animeTable.aniListId,
|
aniListId: anime.aniListId,
|
||||||
malId: animeTable.malId,
|
malId: anime.malId,
|
||||||
kitsuId: animeTable.kitsuId,
|
kitsuId: anime.kitsuId,
|
||||||
categoryName: animeTable.categoryName,
|
categoryName: anime.categoryName,
|
||||||
categoryNumber: animeTable.categoryNumber,
|
categoryNumber: anime.categoryNumber,
|
||||||
mainName: animeTable.mainName,
|
mainName: anime.mainName,
|
||||||
mainNameEn: animeTable.mainNameEn,
|
mainNameEn: anime.mainNameEn,
|
||||||
mainNameJa: animeTable.mainNameJa,
|
mainNameJa: anime.mainNameJa,
|
||||||
year: animeTable.year,
|
year: anime.year,
|
||||||
seasonId: animeTable.seasonId,
|
seasonId: anime.seasonId,
|
||||||
opCount: animeTable.opCount,
|
opCount: anime.opCount,
|
||||||
edCount: animeTable.edCount,
|
edCount: anime.edCount,
|
||||||
insertCount: animeTable.insertCount,
|
insertCount: anime.insertCount,
|
||||||
},
|
},
|
||||||
})
|
})
|
||||||
.run();
|
.run();
|
||||||
@@ -412,23 +412,17 @@ export async function importAmqData(
|
|||||||
|
|
||||||
// For child tables, simplest is: delete existing for these annIds then insert fresh.
|
// For child tables, simplest is: delete existing for these annIds then insert fresh.
|
||||||
// (Safer than trying to upsert composite unique constraints for each child row.)
|
// (Safer than trying to upsert composite unique constraints for each child row.)
|
||||||
for (const a of anime) {
|
for (const a of animeData) {
|
||||||
db.delete(animeNamesTable)
|
db.delete(animeNames).where(eq(animeNames.annId, a.annId)).run();
|
||||||
.where(eq(animeNamesTable.annId, a.annId))
|
db.delete(animeGenres).where(eq(animeGenres.annId, a.annId)).run();
|
||||||
.run();
|
db.delete(animeTags).where(eq(animeTags.annId, a.annId)).run();
|
||||||
db.delete(animeGenresTable)
|
db.delete(animeSongLinks)
|
||||||
.where(eq(animeGenresTable.annId, a.annId))
|
.where(eq(animeSongLinks.annId, a.annId))
|
||||||
.run();
|
|
||||||
db.delete(animeTagsTable)
|
|
||||||
.where(eq(animeTagsTable.annId, a.annId))
|
|
||||||
.run();
|
|
||||||
db.delete(animeSongLinksTable)
|
|
||||||
.where(eq(animeSongLinksTable.annId, a.annId))
|
|
||||||
.run();
|
.run();
|
||||||
|
|
||||||
// names
|
// names
|
||||||
if (a.names.length) {
|
if (a.names.length) {
|
||||||
db.insert(animeNamesTable)
|
db.insert(animeNames)
|
||||||
.values(
|
.values(
|
||||||
a.names.map((n) => ({
|
a.names.map((n) => ({
|
||||||
annId: a.annId,
|
annId: a.annId,
|
||||||
@@ -442,13 +436,13 @@ export async function importAmqData(
|
|||||||
// genres
|
// genres
|
||||||
if (a.genres.length) {
|
if (a.genres.length) {
|
||||||
// Ensure lookup rows exist (string PK)
|
// Ensure lookup rows exist (string PK)
|
||||||
db.insert(genresTable)
|
db.insert(genres)
|
||||||
.values(a.genres.map((g) => ({ name: g })))
|
.values(a.genres.map((g) => ({ name: g })))
|
||||||
.onConflictDoNothing()
|
.onConflictDoNothing()
|
||||||
.run();
|
.run();
|
||||||
|
|
||||||
// Insert relations
|
// Insert relations
|
||||||
db.insert(animeGenresTable)
|
db.insert(animeGenres)
|
||||||
.values(
|
.values(
|
||||||
a.genres.map((g) => ({
|
a.genres.map((g) => ({
|
||||||
annId: a.annId,
|
annId: a.annId,
|
||||||
@@ -461,13 +455,13 @@ export async function importAmqData(
|
|||||||
// tags
|
// tags
|
||||||
if (a.tags.length) {
|
if (a.tags.length) {
|
||||||
// Ensure lookup rows exist (string PK)
|
// Ensure lookup rows exist (string PK)
|
||||||
db.insert(tagsTable)
|
db.insert(tags)
|
||||||
.values(a.tags.map((t) => ({ name: t })))
|
.values(a.tags.map((t) => ({ name: t })))
|
||||||
.onConflictDoNothing()
|
.onConflictDoNothing()
|
||||||
.run();
|
.run();
|
||||||
|
|
||||||
// Insert relations
|
// Insert relations
|
||||||
db.insert(animeTagsTable)
|
db.insert(animeTags)
|
||||||
.values(
|
.values(
|
||||||
a.tags.map((t) => ({
|
a.tags.map((t) => ({
|
||||||
annId: a.annId,
|
annId: a.annId,
|
||||||
@@ -479,7 +473,7 @@ export async function importAmqData(
|
|||||||
|
|
||||||
// song links
|
// song links
|
||||||
if (a.songLinks.length) {
|
if (a.songLinks.length) {
|
||||||
db.insert(animeSongLinksTable)
|
db.insert(animeSongLinks)
|
||||||
.values(
|
.values(
|
||||||
a.songLinks.map((l) => ({
|
a.songLinks.map((l) => ({
|
||||||
annId: a.annId,
|
annId: a.annId,
|
||||||
|
|||||||
@@ -1,87 +1,84 @@
|
|||||||
import { relations } from "drizzle-orm";
|
import { relations } from "drizzle-orm";
|
||||||
import { animeTable } from "./tables/anime";
|
import { anime } from "./tables/anime";
|
||||||
import { animeGenresTable } from "./tables/anime-genres";
|
import { animeGenres } from "./tables/anime-genres";
|
||||||
import { animeNamesTable } from "./tables/anime-names";
|
import { animeNames } from "./tables/anime-names";
|
||||||
import { animeSongLinksTable } from "./tables/anime-song-links";
|
import { animeSongLinks } from "./tables/anime-song-links";
|
||||||
import { animeTagsTable } from "./tables/anime-tags";
|
import { animeTags } from "./tables/anime-tags";
|
||||||
import { artistAltNamesTable } from "./tables/artist-alt-names";
|
import { artistAltNames } from "./tables/artist-alt-names";
|
||||||
import { artistGroupsTable } from "./tables/artist-groups";
|
import { artistGroups } from "./tables/artist-groups";
|
||||||
import { artistsTable } from "./tables/artists";
|
import { artists } from "./tables/artists";
|
||||||
import { genresTable } from "./tables/genres";
|
import { genres } from "./tables/genres";
|
||||||
import { groupAltNamesTable } from "./tables/group-alt-names";
|
import { groupAltNames } from "./tables/group-alt-names";
|
||||||
import { groupArtistMembersTable } from "./tables/group-artist-members";
|
import { groupArtistMembers } from "./tables/group-artist-members";
|
||||||
import { groupGroupMembersTable } from "./tables/group-group-members";
|
import { groupGroupMembers } from "./tables/group-group-members";
|
||||||
import { groupsTable } from "./tables/groups";
|
import { groups } from "./tables/groups";
|
||||||
import { songsTable } from "./tables/songs";
|
import { songs } from "./tables/songs";
|
||||||
import { tagsTable } from "./tables/tags";
|
import { tags } from "./tables/tags";
|
||||||
|
|
||||||
// ----------------------
|
// ----------------------
|
||||||
// Relations (optional but helpful for Drizzle queries)
|
// Relations (optional but helpful for Drizzle queries)
|
||||||
// ----------------------
|
// ----------------------
|
||||||
|
|
||||||
export const animeRelations = relations(animeTable, ({ many }) => ({
|
export const animeRelations = relations(anime, ({ many }) => ({
|
||||||
names: many(animeNamesTable),
|
names: many(animeNames),
|
||||||
genres: many(animeGenresTable),
|
genres: many(animeGenres),
|
||||||
tags: many(animeTagsTable),
|
tags: many(animeTags),
|
||||||
songLinks: many(animeSongLinksTable),
|
songLinks: many(animeSongLinks),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const songRelations = relations(songsTable, ({ many }) => ({
|
export const songRelations = relations(songs, ({ many }) => ({
|
||||||
animeLinks: many(animeSongLinksTable),
|
animeLinks: many(animeSongLinks),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const artistRelations = relations(artistsTable, ({ many }) => ({
|
export const artistRelations = relations(artists, ({ many }) => ({
|
||||||
inGroups: many(artistGroupsTable),
|
inGroups: many(artistGroups),
|
||||||
altNames: many(artistAltNamesTable),
|
altNames: many(artistAltNames),
|
||||||
groupMemberships: many(groupArtistMembersTable),
|
groupMemberships: many(groupArtistMembers),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const groupRelations = relations(groupsTable, ({ many }) => ({
|
export const groupRelations = relations(groups, ({ many }) => ({
|
||||||
artists: many(artistGroupsTable),
|
artists: many(artistGroups),
|
||||||
artistMembers: many(groupArtistMembersTable),
|
artistMembers: many(groupArtistMembers),
|
||||||
groupMembers: many(groupGroupMembersTable),
|
groupMembers: many(groupGroupMembers),
|
||||||
altNames: many(groupAltNamesTable),
|
altNames: many(groupAltNames),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const animeNamesRelations = relations(animeNamesTable, ({ one }) => ({
|
export const animeNamesRelations = relations(animeNames, ({ one }) => ({
|
||||||
anime: one(animeTable, {
|
anime: one(anime, {
|
||||||
fields: [animeNamesTable.annId],
|
fields: [animeNames.annId],
|
||||||
references: [animeTable.annId],
|
references: [anime.annId],
|
||||||
}),
|
}),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const animeGenresRelations = relations(animeGenresTable, ({ one }) => ({
|
export const animeGenresRelations = relations(animeGenres, ({ one }) => ({
|
||||||
anime: one(animeTable, {
|
anime: one(anime, {
|
||||||
fields: [animeGenresTable.annId],
|
fields: [animeGenres.annId],
|
||||||
references: [animeTable.annId],
|
references: [anime.annId],
|
||||||
}),
|
}),
|
||||||
genre: one(genresTable, {
|
genre: one(genres, {
|
||||||
fields: [animeGenresTable.genreName],
|
fields: [animeGenres.genreName],
|
||||||
references: [genresTable.name],
|
references: [genres.name],
|
||||||
}),
|
}),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const animeTagsRelations = relations(animeTagsTable, ({ one }) => ({
|
export const animeTagsRelations = relations(animeTags, ({ one }) => ({
|
||||||
anime: one(animeTable, {
|
anime: one(anime, {
|
||||||
fields: [animeTagsTable.annId],
|
fields: [animeTags.annId],
|
||||||
references: [animeTable.annId],
|
references: [anime.annId],
|
||||||
}),
|
}),
|
||||||
tag: one(tagsTable, {
|
tag: one(tags, {
|
||||||
fields: [animeTagsTable.tagName],
|
fields: [animeTags.tagName],
|
||||||
references: [tagsTable.name],
|
references: [tags.name],
|
||||||
}),
|
}),
|
||||||
}));
|
}));
|
||||||
|
|
||||||
export const animeSongLinksRelations = relations(
|
export const animeSongLinksRelations = relations(animeSongLinks, ({ one }) => ({
|
||||||
animeSongLinksTable,
|
anime: one(anime, {
|
||||||
({ one }) => ({
|
fields: [animeSongLinks.annId],
|
||||||
anime: one(animeTable, {
|
references: [anime.annId],
|
||||||
fields: [animeSongLinksTable.annId],
|
|
||||||
references: [animeTable.annId],
|
|
||||||
}),
|
|
||||||
song: one(songsTable, {
|
|
||||||
fields: [animeSongLinksTable.annSongId],
|
|
||||||
references: [songsTable.annSongId],
|
|
||||||
}),
|
|
||||||
}),
|
}),
|
||||||
);
|
song: one(songs, {
|
||||||
|
fields: [animeSongLinks.annSongId],
|
||||||
|
references: [songs.annSongId],
|
||||||
|
}),
|
||||||
|
}));
|
||||||
|
|||||||
@@ -5,23 +5,23 @@ import {
|
|||||||
sqliteTable,
|
sqliteTable,
|
||||||
text,
|
text,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { animeTable } from "./anime";
|
import { anime } from "./anime";
|
||||||
import { genresTable } from "./genres";
|
import { genres } from "./genres";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Anime -> Genres
|
* Join table: Anime -> Genres
|
||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema.genres (string[])
|
* Source: AmqAnimeSchema.genres (string[])
|
||||||
*/
|
*/
|
||||||
export const animeGenresTable = sqliteTable(
|
export const animeGenres = sqliteTable(
|
||||||
"anime_genres",
|
"anime_genres",
|
||||||
{
|
{
|
||||||
annId: integer("ann_id")
|
annId: integer("ann_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => animeTable.annId, { onDelete: "cascade" }),
|
.references(() => anime.annId, { onDelete: "cascade" }),
|
||||||
genreName: text("genre_name")
|
genreName: text("genre_name")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => genresTable.name, { onDelete: "cascade" }),
|
.references(() => genres.name, { onDelete: "cascade" }),
|
||||||
},
|
},
|
||||||
(t) => ({
|
(t) => ({
|
||||||
pk: primaryKey({
|
pk: primaryKey({
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import {
|
|||||||
text,
|
text,
|
||||||
uniqueIndex,
|
uniqueIndex,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { animeTable } from "./anime";
|
import { anime } from "./anime";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Additional localized/alternative names for an anime.
|
* Additional localized/alternative names for an anime.
|
||||||
@@ -14,14 +14,14 @@ import { animeTable } from "./anime";
|
|||||||
* - language: "EN" | "JA" (per source)
|
* - language: "EN" | "JA" (per source)
|
||||||
* - name: string
|
* - name: string
|
||||||
*/
|
*/
|
||||||
export const animeNamesTable = sqliteTable(
|
export const animeNames = sqliteTable(
|
||||||
"anime_names",
|
"anime_names",
|
||||||
{
|
{
|
||||||
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
||||||
|
|
||||||
annId: integer("ann_id")
|
annId: integer("ann_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => animeTable.annId, { onDelete: "cascade" }),
|
.references(() => anime.annId, { onDelete: "cascade" }),
|
||||||
|
|
||||||
/** "EN" | "JA" per source */
|
/** "EN" | "JA" per source */
|
||||||
language: text("language").notNull(),
|
language: text("language").notNull(),
|
||||||
|
|||||||
@@ -4,24 +4,24 @@ import {
|
|||||||
primaryKey,
|
primaryKey,
|
||||||
sqliteTable,
|
sqliteTable,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { animeTable } from "./anime";
|
import { anime } from "./anime";
|
||||||
import { songsTable } from "./songs";
|
import { songs } from "./songs";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Anime <-> Songs links
|
* Join table: Anime <-> Songs links
|
||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema.songLinks (AmqSongLink[])
|
* Source: AmqAnimeSchema.songLinks (AmqSongLink[])
|
||||||
*/
|
*/
|
||||||
export const animeSongLinksTable = sqliteTable(
|
export const animeSongLinks = sqliteTable(
|
||||||
"anime_song_links",
|
"anime_song_links",
|
||||||
{
|
{
|
||||||
annId: integer("ann_id")
|
annId: integer("ann_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => animeTable.annId, { onDelete: "cascade" }),
|
.references(() => anime.annId, { onDelete: "cascade" }),
|
||||||
|
|
||||||
annSongId: integer("ann_song_id")
|
annSongId: integer("ann_song_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => songsTable.annSongId, { onDelete: "cascade" }),
|
.references(() => songs.annSongId, { onDelete: "cascade" }),
|
||||||
|
|
||||||
/** 1(OP) | 2(ED) | 3(INS) per SongLinkType */
|
/** 1(OP) | 2(ED) | 3(INS) per SongLinkType */
|
||||||
type: integer("type").notNull(),
|
type: integer("type").notNull(),
|
||||||
|
|||||||
@@ -5,23 +5,23 @@ import {
|
|||||||
sqliteTable,
|
sqliteTable,
|
||||||
text,
|
text,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { animeTable } from "./anime";
|
import { anime } from "./anime";
|
||||||
import { tagsTable } from "./tags";
|
import { tags } from "./tags";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Anime -> Tags
|
* Join table: Anime -> Tags
|
||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema.tags (string[])
|
* Source: AmqAnimeSchema.tags (string[])
|
||||||
*/
|
*/
|
||||||
export const animeTagsTable = sqliteTable(
|
export const animeTags = sqliteTable(
|
||||||
"anime_tags",
|
"anime_tags",
|
||||||
{
|
{
|
||||||
annId: integer("ann_id")
|
annId: integer("ann_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => animeTable.annId, { onDelete: "cascade" }),
|
.references(() => anime.annId, { onDelete: "cascade" }),
|
||||||
tagName: text("tag_name")
|
tagName: text("tag_name")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => tagsTable.name, { onDelete: "cascade" }),
|
.references(() => tags.name, { onDelete: "cascade" }),
|
||||||
},
|
},
|
||||||
(t) => ({
|
(t) => ({
|
||||||
pk: primaryKey({
|
pk: primaryKey({
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ import { index, integer, sqliteTable, text } from "drizzle-orm/sqlite-core";
|
|||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema
|
* Source: AmqAnimeSchema
|
||||||
*/
|
*/
|
||||||
export const animeTable = sqliteTable(
|
export const anime = sqliteTable(
|
||||||
"anime",
|
"anime",
|
||||||
{
|
{
|
||||||
/** AMQ anime ID */
|
/** AMQ anime ID */
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import {
|
|||||||
text,
|
text,
|
||||||
uniqueIndex,
|
uniqueIndex,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { artistsTable } from "./artists";
|
import { artists } from "./artists";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Alternative names for artists.
|
* Alternative names for artists.
|
||||||
@@ -14,7 +14,7 @@ import { artistsTable } from "./artists";
|
|||||||
*
|
*
|
||||||
* Interpreted as: artist `songArtistId` is also known as `name` (optionally via altSongArtistId link).
|
* Interpreted as: artist `songArtistId` is also known as `name` (optionally via altSongArtistId link).
|
||||||
*/
|
*/
|
||||||
export const artistAltNamesTable = sqliteTable(
|
export const artistAltNames = sqliteTable(
|
||||||
"artist_alt_names",
|
"artist_alt_names",
|
||||||
{
|
{
|
||||||
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
||||||
@@ -24,7 +24,7 @@ export const artistAltNamesTable = sqliteTable(
|
|||||||
*/
|
*/
|
||||||
songArtistId: integer("song_artist_id")
|
songArtistId: integer("song_artist_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => artistsTable.songArtistId, {
|
.references(() => artists.songArtistId, {
|
||||||
onDelete: "cascade",
|
onDelete: "cascade",
|
||||||
}),
|
}),
|
||||||
|
|
||||||
@@ -36,7 +36,7 @@ export const artistAltNamesTable = sqliteTable(
|
|||||||
*/
|
*/
|
||||||
altSongArtistId: integer("alt_song_artist_id")
|
altSongArtistId: integer("alt_song_artist_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => artistsTable.songArtistId, {
|
.references(() => artists.songArtistId, {
|
||||||
onDelete: "cascade",
|
onDelete: "cascade",
|
||||||
}),
|
}),
|
||||||
|
|
||||||
|
|||||||
@@ -4,25 +4,25 @@ import {
|
|||||||
primaryKey,
|
primaryKey,
|
||||||
sqliteTable,
|
sqliteTable,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { artistsTable } from "./artists";
|
import { artists } from "./artists";
|
||||||
import { groupsTable } from "./groups";
|
import { groups } from "./groups";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Artist -> Groups membership
|
* Join table: Artist -> Groups membership
|
||||||
*
|
*
|
||||||
* Source: AmqArtistSchema.inGroups
|
* Source: AmqArtistSchema.inGroups
|
||||||
*/
|
*/
|
||||||
export const artistGroupsTable = sqliteTable(
|
export const artistGroups = sqliteTable(
|
||||||
"artist_groups",
|
"artist_groups",
|
||||||
{
|
{
|
||||||
songArtistId: integer("song_artist_id")
|
songArtistId: integer("song_artist_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => artistsTable.songArtistId, {
|
.references(() => artists.songArtistId, {
|
||||||
onDelete: "cascade",
|
onDelete: "cascade",
|
||||||
}),
|
}),
|
||||||
songGroupId: integer("song_group_id")
|
songGroupId: integer("song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
},
|
},
|
||||||
(t) => ({
|
(t) => ({
|
||||||
pk: primaryKey({
|
pk: primaryKey({
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import { index, integer, sqliteTable, text } from "drizzle-orm/sqlite-core";
|
|||||||
*
|
*
|
||||||
* Source: AmqArtistSchema
|
* Source: AmqArtistSchema
|
||||||
*/
|
*/
|
||||||
export const artistsTable = sqliteTable(
|
export const artists = sqliteTable(
|
||||||
"artists",
|
"artists",
|
||||||
{
|
{
|
||||||
/** AMQ songArtistId */
|
/** AMQ songArtistId */
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import { index, sqliteTable, text } from "drizzle-orm/sqlite-core";
|
|||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema.genres (string[])
|
* Source: AmqAnimeSchema.genres (string[])
|
||||||
*/
|
*/
|
||||||
export const genresTable = sqliteTable(
|
export const genres = sqliteTable(
|
||||||
"genres",
|
"genres",
|
||||||
{
|
{
|
||||||
/** Primary key is the genre string itself */
|
/** Primary key is the genre string itself */
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import {
|
|||||||
text,
|
text,
|
||||||
uniqueIndex,
|
uniqueIndex,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { groupsTable } from "./groups";
|
import { groups } from "./groups";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Alternative names for groups.
|
* Alternative names for groups.
|
||||||
@@ -16,7 +16,7 @@ import { groupsTable } from "./groups";
|
|||||||
* `songGroupId` is effectively the *context group* the alias is associated with.
|
* `songGroupId` is effectively the *context group* the alias is associated with.
|
||||||
* We persist it as `contextSongGroupId` to make the meaning explicit.
|
* We persist it as `contextSongGroupId` to make the meaning explicit.
|
||||||
*/
|
*/
|
||||||
export const groupAltNamesTable = sqliteTable(
|
export const groupAltNames = sqliteTable(
|
||||||
"group_alt_names",
|
"group_alt_names",
|
||||||
{
|
{
|
||||||
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
id: integer("id").notNull().primaryKey({ autoIncrement: true }),
|
||||||
@@ -26,7 +26,7 @@ export const groupAltNamesTable = sqliteTable(
|
|||||||
*/
|
*/
|
||||||
songGroupId: integer("song_group_id")
|
songGroupId: integer("song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Context group the alias is associated with.
|
* Context group the alias is associated with.
|
||||||
@@ -34,7 +34,7 @@ export const groupAltNamesTable = sqliteTable(
|
|||||||
*/
|
*/
|
||||||
contextSongGroupId: integer("context_song_group_id")
|
contextSongGroupId: integer("context_song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
|
|
||||||
name: text("name").notNull(),
|
name: text("name").notNull(),
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -4,23 +4,23 @@ import {
|
|||||||
primaryKey,
|
primaryKey,
|
||||||
sqliteTable,
|
sqliteTable,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { artistsTable } from "./artists";
|
import { artists } from "./artists";
|
||||||
import { groupsTable } from "./groups";
|
import { groups } from "./groups";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Group -> Artist members
|
* Join table: Group -> Artist members
|
||||||
*
|
*
|
||||||
* Source: AmqGroupSchema.artistMembers
|
* Source: AmqGroupSchema.artistMembers
|
||||||
*/
|
*/
|
||||||
export const groupArtistMembersTable = sqliteTable(
|
export const groupArtistMembers = sqliteTable(
|
||||||
"group_artist_members",
|
"group_artist_members",
|
||||||
{
|
{
|
||||||
songGroupId: integer("song_group_id")
|
songGroupId: integer("song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
songArtistId: integer("song_artist_id")
|
songArtistId: integer("song_artist_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => artistsTable.songArtistId, {
|
.references(() => artists.songArtistId, {
|
||||||
onDelete: "cascade",
|
onDelete: "cascade",
|
||||||
}),
|
}),
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -4,22 +4,22 @@ import {
|
|||||||
primaryKey,
|
primaryKey,
|
||||||
sqliteTable,
|
sqliteTable,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { groupsTable } from "./groups";
|
import { groups } from "./groups";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Join table: Group -> Group members
|
* Join table: Group -> Group members
|
||||||
*
|
*
|
||||||
* Source: AmqGroupSchema.groupMembers
|
* Source: AmqGroupSchema.groupMembers
|
||||||
*/
|
*/
|
||||||
export const groupGroupMembersTable = sqliteTable(
|
export const groupGroupMembers = sqliteTable(
|
||||||
"group_group_members",
|
"group_group_members",
|
||||||
{
|
{
|
||||||
songGroupId: integer("song_group_id")
|
songGroupId: integer("song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
memberSongGroupId: integer("member_song_group_id")
|
memberSongGroupId: integer("member_song_group_id")
|
||||||
.notNull()
|
.notNull()
|
||||||
.references(() => groupsTable.songGroupId, { onDelete: "cascade" }),
|
.references(() => groups.songGroupId, { onDelete: "cascade" }),
|
||||||
},
|
},
|
||||||
(t) => ({
|
(t) => ({
|
||||||
pk: primaryKey({
|
pk: primaryKey({
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import { index, integer, sqliteTable, text } from "drizzle-orm/sqlite-core";
|
|||||||
*
|
*
|
||||||
* Source: AmqGroupSchema
|
* Source: AmqGroupSchema
|
||||||
*/
|
*/
|
||||||
export const groupsTable = sqliteTable(
|
export const groups = sqliteTable(
|
||||||
"groups",
|
"groups",
|
||||||
{
|
{
|
||||||
/** AMQ songGroupId */
|
/** AMQ songGroupId */
|
||||||
|
|||||||
@@ -5,15 +5,15 @@ import {
|
|||||||
sqliteTable,
|
sqliteTable,
|
||||||
text,
|
text,
|
||||||
} from "drizzle-orm/sqlite-core";
|
} from "drizzle-orm/sqlite-core";
|
||||||
import { artistsTable } from "./artists";
|
import { artists } from "./artists";
|
||||||
import { groupsTable } from "./groups";
|
import { groups } from "./groups";
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Core `songs` table.
|
* Core `songs` table.
|
||||||
*
|
*
|
||||||
* Source: AmqSongSchema
|
* Source: AmqSongSchema
|
||||||
*/
|
*/
|
||||||
export const songsTable = sqliteTable(
|
export const songs = sqliteTable(
|
||||||
"songs",
|
"songs",
|
||||||
{
|
{
|
||||||
/** AMQ annSongId (ANN song id) */
|
/** AMQ annSongId (ANN song id) */
|
||||||
@@ -44,31 +44,30 @@ export const songsTable = sqliteTable(
|
|||||||
* These reference existing `artists` / `groups` rows.
|
* These reference existing `artists` / `groups` rows.
|
||||||
*/
|
*/
|
||||||
songArtistId: integer("song_artist_id").references(
|
songArtistId: integer("song_artist_id").references(
|
||||||
() => artistsTable.songArtistId,
|
() => artists.songArtistId,
|
||||||
{ onDelete: "set null" },
|
|
||||||
),
|
|
||||||
songGroupId: integer("song_group_id").references(
|
|
||||||
() => groupsTable.songGroupId,
|
|
||||||
{ onDelete: "set null" },
|
{ onDelete: "set null" },
|
||||||
),
|
),
|
||||||
|
songGroupId: integer("song_group_id").references(() => groups.songGroupId, {
|
||||||
|
onDelete: "set null",
|
||||||
|
}),
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Additional contributor ids (nullable in source)
|
* Additional contributor ids (nullable in source)
|
||||||
*/
|
*/
|
||||||
composerArtistId: integer("composer_artist_id").references(
|
composerArtistId: integer("composer_artist_id").references(
|
||||||
() => artistsTable.songArtistId,
|
() => artists.songArtistId,
|
||||||
{ onDelete: "set null" },
|
{ onDelete: "set null" },
|
||||||
),
|
),
|
||||||
composerGroupId: integer("composer_group_id").references(
|
composerGroupId: integer("composer_group_id").references(
|
||||||
() => groupsTable.songGroupId,
|
() => groups.songGroupId,
|
||||||
{ onDelete: "set null" },
|
{ onDelete: "set null" },
|
||||||
),
|
),
|
||||||
arrangerArtistId: integer("arranger_artist_id").references(
|
arrangerArtistId: integer("arranger_artist_id").references(
|
||||||
() => artistsTable.songArtistId,
|
() => artists.songArtistId,
|
||||||
{ onDelete: "set null" },
|
{ onDelete: "set null" },
|
||||||
),
|
),
|
||||||
arrangerGroupId: integer("arranger_group_id").references(
|
arrangerGroupId: integer("arranger_group_id").references(
|
||||||
() => groupsTable.songGroupId,
|
() => groups.songGroupId,
|
||||||
{ onDelete: "set null" },
|
{ onDelete: "set null" },
|
||||||
),
|
),
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ import { index, sqliteTable, text } from "drizzle-orm/sqlite-core";
|
|||||||
*
|
*
|
||||||
* Source: AmqAnimeSchema.tags (string[])
|
* Source: AmqAnimeSchema.tags (string[])
|
||||||
*/
|
*/
|
||||||
export const tagsTable = sqliteTable(
|
export const tags = sqliteTable(
|
||||||
"tags",
|
"tags",
|
||||||
{
|
{
|
||||||
/** Primary key is the tag string itself */
|
/** Primary key is the tag string itself */
|
||||||
|
|||||||
Reference in New Issue
Block a user