mirror of
https://github.com/BradNut/boredgame
synced 2025-09-08 17:40:22 +00:00
Merge pull request #17 from BradNut/migrate-two-factor
Migrate two factor
This commit is contained in:
commit
a45a24fdea
204 changed files with 10417 additions and 21559 deletions
2
.nvmrc
2
.nvmrc
|
|
@ -1 +1 @@
|
|||
v20
|
||||
20
|
||||
|
|
@ -1,20 +1,21 @@
|
|||
import 'dotenv/config';
|
||||
import { defineConfig } from 'drizzle-kit';
|
||||
import env from './src/env';
|
||||
|
||||
export default defineConfig({
|
||||
schema: './src/schema.ts',
|
||||
out: './drizzle',
|
||||
driver: 'pg',
|
||||
dialect: 'postgresql',
|
||||
schema: './src/db/schema/index.ts',
|
||||
out: './src/db/migrations',
|
||||
dbCredentials: {
|
||||
host: process.env.DATABASE_HOST || 'localhost',
|
||||
port: Number(process.env.DATABASE_PORT) || 5432,
|
||||
user: process.env.DATABASE_USER,
|
||||
password: process.env.DATABASE_PASSWORD,
|
||||
database: process.env.DATABASE || 'boredgame',
|
||||
ssl: process.env.DATABASE_HOST !== 'localhost'
|
||||
host: env.DATABASE_HOST || 'localhost',
|
||||
port: Number(env.DATABASE_PORT) || 5432,
|
||||
user: env.DATABASE_USER,
|
||||
password: env.DATABASE_PASSWORD,
|
||||
database: env.DATABASE_DB || 'boredgame',
|
||||
ssl: env.DATABASE_HOST !== 'localhost',
|
||||
},
|
||||
// Print all statements
|
||||
verbose: true,
|
||||
// Always as for confirmation
|
||||
strict: true
|
||||
strict: true,
|
||||
});
|
||||
|
|
|
|||
|
|
@ -1,6 +0,0 @@
|
|||
ALTER TABLE "collection_items" ALTER COLUMN "collection_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "collection_items" ALTER COLUMN "game_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "expansions" ALTER COLUMN "base_game_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "expansions" ALTER COLUMN "game_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "wishlist_items" ALTER COLUMN "wishlist_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "wishlist_items" ALTER COLUMN "game_id" SET DATA TYPE uuid;
|
||||
|
|
@ -1,5 +0,0 @@
|
|||
ALTER TABLE "collections" ALTER COLUMN "user_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "password_reset_tokens" ALTER COLUMN "user_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "sessions" ALTER COLUMN "user_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "user_roles" ALTER COLUMN "user_id" SET DATA TYPE uuid;--> statement-breakpoint
|
||||
ALTER TABLE "wishlists" ALTER COLUMN "user_id" SET DATA TYPE uuid;
|
||||
|
|
@ -1 +0,0 @@
|
|||
ALTER TABLE "user_roles" ALTER COLUMN "role_id" SET DATA TYPE uuid;
|
||||
|
|
@ -1,13 +0,0 @@
|
|||
ALTER TABLE "categories" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "collection_items" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "collections" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "expansions" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "external_ids" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "games" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "mechanics" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "publishers" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "roles" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "user_roles" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "users" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "wishlist_items" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();--> statement-breakpoint
|
||||
ALTER TABLE "wishlists" ALTER COLUMN "id" SET DEFAULT gen_random_uuid();
|
||||
|
|
@ -1,2 +0,0 @@
|
|||
ALTER TABLE "roles" ALTER COLUMN "cuid" SET NOT NULL;--> statement-breakpoint
|
||||
ALTER TABLE "roles" ALTER COLUMN "name" SET NOT NULL;
|
||||
|
|
@ -1 +0,0 @@
|
|||
ALTER TABLE "user_roles" ADD COLUMN "default" boolean DEFAULT false;
|
||||
|
|
@ -1 +0,0 @@
|
|||
ALTER TABLE "user_roles" RENAME COLUMN "default" TO "primary";
|
||||
|
|
@ -1 +0,0 @@
|
|||
ALTER TABLE "users" ADD COLUMN "two_factor_secret" text;
|
||||
|
|
@ -1,2 +0,0 @@
|
|||
ALTER TABLE "users" ALTER COLUMN "two_factor_secret" SET DEFAULT '';--> statement-breakpoint
|
||||
ALTER TABLE "users" ADD COLUMN "two_factor_enabled" boolean DEFAULT false;
|
||||
|
|
@ -1,14 +0,0 @@
|
|||
CREATE TABLE IF NOT EXISTS "recovery_codes" (
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"code" text NOT NULL,
|
||||
"used" boolean DEFAULT false,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL
|
||||
);
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "recovery_codes" ADD CONSTRAINT "recovery_codes_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE no action ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
|
|
@ -1,2 +0,0 @@
|
|||
ALTER TABLE "collections" ADD COLUMN "name" text DEFAULT 'My Collection' NOT NULL;--> statement-breakpoint
|
||||
ALTER TABLE "wishlists" ADD COLUMN "name" text DEFAULT 'My Wishlist' NOT NULL;
|
||||
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
File diff suppressed because it is too large
Load diff
|
|
@ -1,90 +0,0 @@
|
|||
{
|
||||
"version": "5",
|
||||
"dialect": "pg",
|
||||
"entries": [
|
||||
{
|
||||
"idx": 0,
|
||||
"version": "5",
|
||||
"when": 1710268038944,
|
||||
"tag": "0000_tricky_hitman",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 1,
|
||||
"version": "5",
|
||||
"when": 1710268191378,
|
||||
"tag": "0001_numerous_dragon_man",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 2,
|
||||
"version": "5",
|
||||
"when": 1710268300740,
|
||||
"tag": "0002_thick_lyja",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 3,
|
||||
"version": "5",
|
||||
"when": 1710268371021,
|
||||
"tag": "0003_mushy_madame_masque",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 4,
|
||||
"version": "5",
|
||||
"when": 1710277583673,
|
||||
"tag": "0004_glossy_enchantress",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 5,
|
||||
"version": "5",
|
||||
"when": 1710366724519,
|
||||
"tag": "0005_light_captain_marvel",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 6,
|
||||
"version": "5",
|
||||
"when": 1710905422967,
|
||||
"tag": "0006_wild_stone_men",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 7,
|
||||
"version": "5",
|
||||
"when": 1710905572670,
|
||||
"tag": "0007_large_miss_america",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 8,
|
||||
"version": "5",
|
||||
"when": 1711757183163,
|
||||
"tag": "0008_amusing_franklin_richards",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 9,
|
||||
"version": "5",
|
||||
"when": 1711868447607,
|
||||
"tag": "0009_gray_carlie_cooper",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 10,
|
||||
"version": "5",
|
||||
"when": 1712271520175,
|
||||
"tag": "0010_wakeful_metal_master",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 11,
|
||||
"version": "5",
|
||||
"when": 1713311328819,
|
||||
"tag": "0011_charming_bucky",
|
||||
"breakpoints": true
|
||||
}
|
||||
]
|
||||
}
|
||||
107
package.json
107
package.json
|
|
@ -15,59 +15,58 @@
|
|||
"lint": "prettier --plugin-search-dir . --check . && eslint .",
|
||||
"format": "prettier --plugin-search-dir . --write .",
|
||||
"site:update": "pnpm update -i -L",
|
||||
"generate": "drizzle-kit generate:pg",
|
||||
"migrate": "tsx ./src/migrate.ts",
|
||||
"seed": "tsx ./src/seed.ts",
|
||||
"push": "drizzle-kit push:pg"
|
||||
"generate": "drizzle-kit generate",
|
||||
"migrate": "tsx src/db/migrate.ts",
|
||||
"seed": "tsx src/db/seed.ts",
|
||||
"push": "drizzle-kit push"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@melt-ui/pp": "^0.3.0",
|
||||
"@melt-ui/svelte": "^0.76.3",
|
||||
"@playwright/test": "^1.43.1",
|
||||
"@melt-ui/pp": "^0.3.2",
|
||||
"@melt-ui/svelte": "^0.83.0",
|
||||
"@playwright/test": "^1.45.1",
|
||||
"@resvg/resvg-js": "^2.6.2",
|
||||
"@sveltejs/adapter-auto": "^3.2.0",
|
||||
"@sveltejs/enhanced-img": "^0.2.0",
|
||||
"@sveltejs/kit": "^2.5.6",
|
||||
"@sveltejs/vite-plugin-svelte": "^3.1.0",
|
||||
"@sveltejs/adapter-auto": "^3.2.2",
|
||||
"@sveltejs/enhanced-img": "^0.3.0",
|
||||
"@sveltejs/kit": "^2.5.18",
|
||||
"@sveltejs/vite-plugin-svelte": "^3.1.1",
|
||||
"@types/cookie": "^0.6.0",
|
||||
"@types/node": "^20.12.6",
|
||||
"@types/pg": "^8.11.5",
|
||||
"@typescript-eslint/eslint-plugin": "^7.7.0",
|
||||
"@typescript-eslint/parser": "^7.7.0",
|
||||
"@types/node": "^20.14.10",
|
||||
"@types/pg": "^8.11.6",
|
||||
"@typescript-eslint/eslint-plugin": "^7.13.0",
|
||||
"@typescript-eslint/parser": "^7.13.0",
|
||||
"autoprefixer": "^10.4.19",
|
||||
"dotenv": "^16.4.5",
|
||||
"drizzle-kit": "^0.20.14",
|
||||
"drizzle-kit": "^0.23.0",
|
||||
"eslint": "^8.57.0",
|
||||
"eslint-config-prettier": "^9.1.0",
|
||||
"eslint-plugin-svelte": "^2.36.0",
|
||||
"eslint-plugin-svelte": "^2.41.0",
|
||||
"just-clone": "^6.2.0",
|
||||
"just-debounce-it": "^3.2.0",
|
||||
"postcss": "^8.4.38",
|
||||
"postcss": "^8.4.39",
|
||||
"postcss-import": "^16.1.0",
|
||||
"postcss-load-config": "^5.0.3",
|
||||
"postcss-preset-env": "^9.5.4",
|
||||
"prettier": "^3.2.5",
|
||||
"prettier-plugin-svelte": "^3.2.3",
|
||||
"sass": "^1.74.1",
|
||||
"postcss-load-config": "^5.1.0",
|
||||
"postcss-preset-env": "^9.6.0",
|
||||
"prettier": "^3.3.2",
|
||||
"prettier-plugin-svelte": "^3.2.5",
|
||||
"sass": "^1.77.8",
|
||||
"satori": "^0.10.13",
|
||||
"satori-html": "^0.3.2",
|
||||
"svelte": "^4.2.14",
|
||||
"svelte-check": "^3.6.9",
|
||||
"svelte": "5.0.0-next.175",
|
||||
"svelte-check": "^3.8.4",
|
||||
"svelte-headless-table": "^0.18.2",
|
||||
"svelte-meta-tags": "^3.1.2",
|
||||
"svelte-preprocess": "^5.1.3",
|
||||
"svelte-preprocess": "^6.0.2",
|
||||
"svelte-sequential-preprocessor": "^2.0.1",
|
||||
"sveltekit-flash-message": "^2.4.4",
|
||||
"sveltekit-rate-limiter": "^0.5.1",
|
||||
"sveltekit-superforms": "^2.12.4",
|
||||
"tailwindcss": "^3.4.3",
|
||||
"sveltekit-superforms": "^2.16.0",
|
||||
"tailwindcss": "^3.4.4",
|
||||
"ts-node": "^10.9.2",
|
||||
"tslib": "^2.6.1",
|
||||
"tsx": "^4.7.2",
|
||||
"typescript": "^5.4.4",
|
||||
"vite": "^5.2.8",
|
||||
"vitest": "^1.4.0",
|
||||
"zod": "^3.22.4"
|
||||
"tslib": "^2.6.3",
|
||||
"tsx": "^4.16.2",
|
||||
"typescript": "^5.5.3",
|
||||
"vite": "^5.3.3",
|
||||
"vitest": "^1.6.0",
|
||||
"zod": "^3.23.8"
|
||||
},
|
||||
"type": "module",
|
||||
"engines": {
|
||||
|
|
@ -75,42 +74,44 @@
|
|||
"pnpm": ">=8"
|
||||
},
|
||||
"dependencies": {
|
||||
"@fontsource/fira-mono": "^5.0.12",
|
||||
"@iconify-icons/line-md": "^1.2.26",
|
||||
"@iconify-icons/mdi": "^1.2.47",
|
||||
"@fontsource/fira-mono": "^5.0.13",
|
||||
"@iconify-icons/line-md": "^1.2.30",
|
||||
"@iconify-icons/mdi": "^1.2.48",
|
||||
"@lucia-auth/adapter-drizzle": "^1.0.7",
|
||||
"@lukeed/uuid": "^2.0.1",
|
||||
"@neondatabase/serverless": "^0.9.1",
|
||||
"@neondatabase/serverless": "^0.9.4",
|
||||
"@paralleldrive/cuid2": "^2.2.2",
|
||||
"@sveltejs/adapter-vercel": "^5.2.0",
|
||||
"@sveltejs/adapter-vercel": "^5.4.1",
|
||||
"@types/feather-icons": "^4.29.4",
|
||||
"@vercel/og": "^0.5.20",
|
||||
"bits-ui": "^0.21.3",
|
||||
"bits-ui": "^0.21.12",
|
||||
"boardgamegeekclient": "^1.9.1",
|
||||
"class-variance-authority": "^0.7.0",
|
||||
"clsx": "^2.1.0",
|
||||
"clsx": "^2.1.1",
|
||||
"cookie": "^0.6.0",
|
||||
"drizzle-orm": "^0.30.7",
|
||||
"feather-icons": "^4.29.1",
|
||||
"formsnap": "^1.0.0",
|
||||
"dotenv": "^16.4.5",
|
||||
"dotenv-expand": "^11.0.6",
|
||||
"drizzle-orm": "^0.32.0",
|
||||
"feather-icons": "^4.29.2",
|
||||
"formsnap": "^1.0.1",
|
||||
"html-entities": "^2.5.2",
|
||||
"iconify-icon": "^2.1.0",
|
||||
"just-capitalize": "^3.2.0",
|
||||
"just-kebab-case": "^4.2.0",
|
||||
"loader": "^2.1.1",
|
||||
"lucia": "3.1.1",
|
||||
"lucide-svelte": "^0.368.0",
|
||||
"open-props": "^1.7.2",
|
||||
"oslo": "^1.2.0",
|
||||
"pg": "^8.11.5",
|
||||
"lucia": "3.2.0",
|
||||
"lucide-svelte": "^0.407.0",
|
||||
"open-props": "^1.7.5",
|
||||
"oslo": "^1.2.1",
|
||||
"pg": "^8.12.0",
|
||||
"postgres": "^3.4.4",
|
||||
"qrcode": "^1.5.3",
|
||||
"radix-svelte": "^0.9.0",
|
||||
"svelte-french-toast": "^1.2.0",
|
||||
"svelte-lazy-loader": "^1.0.0",
|
||||
"tailwind-merge": "^2.2.2",
|
||||
"tailwind-merge": "^2.4.0",
|
||||
"tailwind-variants": "^0.2.1",
|
||||
"tailwindcss-animate": "^1.0.6",
|
||||
"zod-to-json-schema": "^3.22.5"
|
||||
"tailwindcss-animate": "^1.0.7",
|
||||
"zod-to-json-schema": "^3.23.1"
|
||||
}
|
||||
}
|
||||
10673
pnpm-lock.yaml
10673
pnpm-lock.yaml
File diff suppressed because it is too large
Load diff
24
src/db/index.ts
Normal file
24
src/db/index.ts
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { drizzle } from 'drizzle-orm/node-postgres';
|
||||
import pg from 'pg';
|
||||
import env from '../env';
|
||||
import * as schema from './schema';
|
||||
|
||||
// create the connection
|
||||
export const pool = new pg.Pool({
|
||||
user: env.DATABASE_USER,
|
||||
password: env.DATABASE_PASSWORD,
|
||||
host: env.DATABASE_HOST,
|
||||
port: Number(env.DATABASE_PORT).valueOf(),
|
||||
database: env.DATABASE_DB,
|
||||
ssl: env.DATABASE_HOST !== 'localhost',
|
||||
max: env.DB_MIGRATING || env.DB_SEEDING ? 1 : undefined,
|
||||
});
|
||||
|
||||
export const db = drizzle(pool, {
|
||||
schema,
|
||||
logger: env.NODE_ENV === 'development',
|
||||
});
|
||||
|
||||
export type db = typeof db;
|
||||
|
||||
export default db;
|
||||
26
src/db/migrate.ts
Normal file
26
src/db/migrate.ts
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
import 'dotenv/config';
|
||||
import postgres from 'postgres';
|
||||
import { drizzle } from 'drizzle-orm/postgres-js';
|
||||
import { migrate } from 'drizzle-orm/postgres-js/migrator';
|
||||
import env from '../env';
|
||||
import config from '../../drizzle.config';
|
||||
|
||||
const connection = postgres({
|
||||
host: env.DATABASE_HOST || 'localhost',
|
||||
port: env.DATABASE_PORT,
|
||||
user: env.DATABASE_USER || 'root',
|
||||
password: env.DATABASE_PASSWORD || '',
|
||||
database: env.DATABASE_DB || 'boredgame',
|
||||
ssl: env.NODE_ENV === 'development' ? false : 'require',
|
||||
max: 1,
|
||||
});
|
||||
const db = drizzle(connection);
|
||||
|
||||
try {
|
||||
await migrate(db, { migrationsFolder: config.out! });
|
||||
console.log('Migrations complete');
|
||||
} catch (e) {
|
||||
console.error(e);
|
||||
}
|
||||
|
||||
process.exit();
|
||||
|
|
@ -1,16 +1,16 @@
|
|||
DO $$ BEGIN
|
||||
CREATE TYPE "external_id_type" AS ENUM('game', 'category', 'mechanic', 'publisher', 'designer', 'artist');
|
||||
CREATE TYPE "public"."external_id_type" AS ENUM('game', 'category', 'mechanic', 'publisher', 'designer', 'artist');
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "categories" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"name" text,
|
||||
"slug" text,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "categories_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
|
|
@ -27,48 +27,49 @@ CREATE TABLE IF NOT EXISTS "categories_to_games" (
|
|||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "collection_items" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"collection_id" text NOT NULL,
|
||||
"game_id" text NOT NULL,
|
||||
"collection_id" uuid NOT NULL,
|
||||
"game_id" uuid NOT NULL,
|
||||
"times_played" integer DEFAULT 0,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "collection_items_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "collections" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"user_id" text NOT NULL,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"name" text DEFAULT 'My Collection' NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "collections_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "expansions" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"base_game_id" text NOT NULL,
|
||||
"game_id" text NOT NULL,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"base_game_id" uuid NOT NULL,
|
||||
"game_id" uuid NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "expansions_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "external_ids" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"type" "external_id_type" NOT NULL,
|
||||
"type" "external_id_type",
|
||||
"external_id" text NOT NULL,
|
||||
CONSTRAINT "external_ids_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "games" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"name" text,
|
||||
"slug" text,
|
||||
"name" text NOT NULL,
|
||||
"slug" text NOT NULL,
|
||||
"description" text,
|
||||
"year_published" integer,
|
||||
"min_players" integer,
|
||||
|
|
@ -80,10 +81,9 @@ CREATE TABLE IF NOT EXISTS "games" (
|
|||
"image_url" text,
|
||||
"thumb_url" text,
|
||||
"url" text,
|
||||
"text_searchable_index" "tsvector",
|
||||
"last_sync_at" timestamp (6) with time zone,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"last_sync_at" timestamp,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "games_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
|
|
@ -94,12 +94,12 @@ CREATE TABLE IF NOT EXISTS "games_to_external_ids" (
|
|||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "mechanics" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"name" text,
|
||||
"slug" text,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "mechanics_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
|
|
@ -117,18 +117,19 @@ CREATE TABLE IF NOT EXISTS "mechanics_to_games" (
|
|||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "password_reset_tokens" (
|
||||
"id" text PRIMARY KEY NOT NULL,
|
||||
"user_id" text NOT NULL,
|
||||
"expires_at" timestamp (6) with time zone,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL
|
||||
"user_id" uuid NOT NULL,
|
||||
"expires_at" timestamp,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "publishers" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"name" text,
|
||||
"slug" text,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "publishers_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
|
|
@ -144,34 +145,61 @@ CREATE TABLE IF NOT EXISTS "publishers_to_games" (
|
|||
CONSTRAINT "publishers_to_games_publisher_id_game_id_pk" PRIMARY KEY("publisher_id","game_id")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "recovery_codes" (
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"code" text NOT NULL,
|
||||
"used" boolean DEFAULT false,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "roles" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"cuid" text,
|
||||
"name" text,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text NOT NULL,
|
||||
"name" text NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "roles_cuid_unique" UNIQUE("cuid"),
|
||||
CONSTRAINT "roles_name_unique" UNIQUE("name")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "sessions" (
|
||||
"id" text PRIMARY KEY NOT NULL,
|
||||
"user_id" text NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"expires_at" timestamp with time zone NOT NULL,
|
||||
"ip_country" text,
|
||||
"ip_address" text
|
||||
"ip_address" text,
|
||||
"two_factor_auth_enabled" boolean DEFAULT false,
|
||||
"is_two_factor_authenticated" boolean DEFAULT false
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "two_factor" (
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"two_factor_secret" text NOT NULL,
|
||||
"two_factor_enabled" boolean DEFAULT false NOT NULL,
|
||||
"initiated_time" timestamp with time zone NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "two_factor_cuid_unique" UNIQUE("cuid"),
|
||||
CONSTRAINT "two_factor_user_id_unique" UNIQUE("user_id")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "user_roles" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"user_id" text NOT NULL,
|
||||
"role_id" text NOT NULL,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"role_id" uuid NOT NULL,
|
||||
"primary" boolean DEFAULT false,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "user_roles_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "users" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"username" text,
|
||||
"hashed_password" text,
|
||||
|
|
@ -181,185 +209,202 @@ CREATE TABLE IF NOT EXISTS "users" (
|
|||
"verified" boolean DEFAULT false,
|
||||
"receive_email" boolean DEFAULT false,
|
||||
"theme" text DEFAULT 'system',
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "users_cuid_unique" UNIQUE("cuid"),
|
||||
CONSTRAINT "users_username_unique" UNIQUE("username"),
|
||||
CONSTRAINT "users_email_unique" UNIQUE("email")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "wishlist_items" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"wishlist_id" text NOT NULL,
|
||||
"game_id" text NOT NULL,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"wishlist_id" uuid NOT NULL,
|
||||
"game_id" uuid NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "wishlist_items_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE TABLE IF NOT EXISTS "wishlists" (
|
||||
"id" uuid PRIMARY KEY NOT NULL,
|
||||
"id" uuid PRIMARY KEY DEFAULT gen_random_uuid() NOT NULL,
|
||||
"cuid" text,
|
||||
"user_id" text NOT NULL,
|
||||
"created_at" timestamp DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp DEFAULT now() NOT NULL,
|
||||
"user_id" uuid NOT NULL,
|
||||
"name" text DEFAULT 'My Wishlist' NOT NULL,
|
||||
"created_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
"updated_at" timestamp with time zone DEFAULT now() NOT NULL,
|
||||
CONSTRAINT "wishlists_cuid_unique" UNIQUE("cuid")
|
||||
);
|
||||
--> statement-breakpoint
|
||||
CREATE INDEX IF NOT EXISTS "text_searchable_idx" ON "games" ("text_searchable_index");--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "categories_to_external_ids" ADD CONSTRAINT "categories_to_external_ids_category_id_categories_id_fk" FOREIGN KEY ("category_id") REFERENCES "categories"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "categories_to_external_ids" ADD CONSTRAINT "categories_to_external_ids_category_id_categories_id_fk" FOREIGN KEY ("category_id") REFERENCES "public"."categories"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "categories_to_external_ids" ADD CONSTRAINT "categories_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "categories_to_external_ids" ADD CONSTRAINT "categories_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "public"."external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "categories_to_games" ADD CONSTRAINT "categories_to_games_category_id_categories_id_fk" FOREIGN KEY ("category_id") REFERENCES "categories"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "categories_to_games" ADD CONSTRAINT "categories_to_games_category_id_categories_id_fk" FOREIGN KEY ("category_id") REFERENCES "public"."categories"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "categories_to_games" ADD CONSTRAINT "categories_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "categories_to_games" ADD CONSTRAINT "categories_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "collection_items" ADD CONSTRAINT "collection_items_collection_id_collections_id_fk" FOREIGN KEY ("collection_id") REFERENCES "collections"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "collection_items" ADD CONSTRAINT "collection_items_collection_id_collections_id_fk" FOREIGN KEY ("collection_id") REFERENCES "public"."collections"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "collection_items" ADD CONSTRAINT "collection_items_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "collection_items" ADD CONSTRAINT "collection_items_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "collections" ADD CONSTRAINT "collections_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "collections" ADD CONSTRAINT "collections_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "expansions" ADD CONSTRAINT "expansions_base_game_id_games_id_fk" FOREIGN KEY ("base_game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "expansions" ADD CONSTRAINT "expansions_base_game_id_games_id_fk" FOREIGN KEY ("base_game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "expansions" ADD CONSTRAINT "expansions_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "expansions" ADD CONSTRAINT "expansions_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "games_to_external_ids" ADD CONSTRAINT "games_to_external_ids_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "games_to_external_ids" ADD CONSTRAINT "games_to_external_ids_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "games_to_external_ids" ADD CONSTRAINT "games_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "games_to_external_ids" ADD CONSTRAINT "games_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "public"."external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "mechanics_to_external_ids" ADD CONSTRAINT "mechanics_to_external_ids_mechanic_id_mechanics_id_fk" FOREIGN KEY ("mechanic_id") REFERENCES "mechanics"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "mechanics_to_external_ids" ADD CONSTRAINT "mechanics_to_external_ids_mechanic_id_mechanics_id_fk" FOREIGN KEY ("mechanic_id") REFERENCES "public"."mechanics"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "mechanics_to_external_ids" ADD CONSTRAINT "mechanics_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "mechanics_to_external_ids" ADD CONSTRAINT "mechanics_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "public"."external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "mechanics_to_games" ADD CONSTRAINT "mechanics_to_games_mechanic_id_mechanics_id_fk" FOREIGN KEY ("mechanic_id") REFERENCES "mechanics"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "mechanics_to_games" ADD CONSTRAINT "mechanics_to_games_mechanic_id_mechanics_id_fk" FOREIGN KEY ("mechanic_id") REFERENCES "public"."mechanics"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "mechanics_to_games" ADD CONSTRAINT "mechanics_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "mechanics_to_games" ADD CONSTRAINT "mechanics_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "password_reset_tokens" ADD CONSTRAINT "password_reset_tokens_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "password_reset_tokens" ADD CONSTRAINT "password_reset_tokens_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "publishers_to_external_ids" ADD CONSTRAINT "publishers_to_external_ids_publisher_id_publishers_id_fk" FOREIGN KEY ("publisher_id") REFERENCES "publishers"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "publishers_to_external_ids" ADD CONSTRAINT "publishers_to_external_ids_publisher_id_publishers_id_fk" FOREIGN KEY ("publisher_id") REFERENCES "public"."publishers"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "publishers_to_external_ids" ADD CONSTRAINT "publishers_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "publishers_to_external_ids" ADD CONSTRAINT "publishers_to_external_ids_external_id_external_ids_id_fk" FOREIGN KEY ("external_id") REFERENCES "public"."external_ids"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "publishers_to_games" ADD CONSTRAINT "publishers_to_games_publisher_id_publishers_id_fk" FOREIGN KEY ("publisher_id") REFERENCES "publishers"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "publishers_to_games" ADD CONSTRAINT "publishers_to_games_publisher_id_publishers_id_fk" FOREIGN KEY ("publisher_id") REFERENCES "public"."publishers"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "publishers_to_games" ADD CONSTRAINT "publishers_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
ALTER TABLE "publishers_to_games" ADD CONSTRAINT "publishers_to_games_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE restrict ON UPDATE cascade;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "sessions" ADD CONSTRAINT "sessions_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE no action ON UPDATE no action;
|
||||
ALTER TABLE "recovery_codes" ADD CONSTRAINT "recovery_codes_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE no action ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "user_roles" ADD CONSTRAINT "user_roles_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "sessions" ADD CONSTRAINT "sessions_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE no action ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "user_roles" ADD CONSTRAINT "user_roles_role_id_roles_id_fk" FOREIGN KEY ("role_id") REFERENCES "roles"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "two_factor" ADD CONSTRAINT "two_factor_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE no action ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "wishlist_items" ADD CONSTRAINT "wishlist_items_wishlist_id_wishlists_id_fk" FOREIGN KEY ("wishlist_id") REFERENCES "wishlists"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "user_roles" ADD CONSTRAINT "user_roles_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "wishlist_items" ADD CONSTRAINT "wishlist_items_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "games"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "user_roles" ADD CONSTRAINT "user_roles_role_id_roles_id_fk" FOREIGN KEY ("role_id") REFERENCES "public"."roles"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "wishlists" ADD CONSTRAINT "wishlists_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
ALTER TABLE "wishlist_items" ADD CONSTRAINT "wishlist_items_wishlist_id_wishlists_id_fk" FOREIGN KEY ("wishlist_id") REFERENCES "public"."wishlists"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "wishlist_items" ADD CONSTRAINT "wishlist_items_game_id_games_id_fk" FOREIGN KEY ("game_id") REFERENCES "public"."games"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
DO $$ BEGIN
|
||||
ALTER TABLE "wishlists" ADD CONSTRAINT "wishlists_user_id_users_id_fk" FOREIGN KEY ("user_id") REFERENCES "public"."users"("id") ON DELETE cascade ON UPDATE no action;
|
||||
EXCEPTION
|
||||
WHEN duplicate_object THEN null;
|
||||
END $$;
|
||||
--> statement-breakpoint
|
||||
CREATE INDEX IF NOT EXISTS "search_index" ON "games" USING gin ((
|
||||
setweight(to_tsvector('english', "name"), 'A') ||
|
||||
setweight(to_tsvector('english', "slug"), 'B')
|
||||
));
|
||||
2
src/db/migrations/0001_noisy_sally_floyd.sql
Normal file
2
src/db/migrations/0001_noisy_sally_floyd.sql
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
ALTER TABLE "two_factor" RENAME COLUMN "two_factor_secret" TO "secret";--> statement-breakpoint
|
||||
ALTER TABLE "two_factor" RENAME COLUMN "two_factor_enabled" TO "enabled";
|
||||
1
src/db/migrations/0002_fancy_valkyrie.sql
Normal file
1
src/db/migrations/0002_fancy_valkyrie.sql
Normal file
|
|
@ -0,0 +1 @@
|
|||
ALTER TABLE "two_factor" ALTER COLUMN "initiated_time" DROP NOT NULL;
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
{
|
||||
"id": "176e5b1f-d146-4604-ab17-b16052da13c0",
|
||||
"id": "e120d11a-bf28-4c96-9f2f-96e23e23c7e2",
|
||||
"prevId": "00000000-0000-0000-0000-000000000000",
|
||||
"version": "5",
|
||||
"dialect": "pg",
|
||||
"version": "7",
|
||||
"dialect": "postgresql",
|
||||
"tables": {
|
||||
"categories": {
|
||||
"public.categories": {
|
||||
"name": "categories",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -12,7 +12,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -34,14 +35,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -60,7 +61,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"categories_to_external_ids": {
|
||||
"public.categories_to_external_ids": {
|
||||
"name": "categories_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -117,7 +118,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"categories_to_games": {
|
||||
"public.categories_to_games": {
|
||||
"name": "categories_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -174,7 +175,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"collection_items": {
|
||||
"public.collection_items": {
|
||||
"name": "collection_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -182,7 +183,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -192,13 +194,13 @@
|
|||
},
|
||||
"collection_id": {
|
||||
"name": "collection_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"game_id": {
|
||||
"name": "game_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
|
|
@ -211,14 +213,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -264,7 +266,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"collections": {
|
||||
"public.collections": {
|
||||
"name": "collections",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -272,7 +274,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -282,20 +285,27 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Collection'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -328,7 +338,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"expansions": {
|
||||
"public.expansions": {
|
||||
"name": "expansions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -336,7 +346,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -346,26 +357,26 @@
|
|||
},
|
||||
"base_game_id": {
|
||||
"name": "base_game_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"game_id": {
|
||||
"name": "game_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -411,7 +422,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"external_ids": {
|
||||
"public.external_ids": {
|
||||
"name": "external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -419,7 +430,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -430,8 +442,9 @@
|
|||
"type": {
|
||||
"name": "type",
|
||||
"type": "external_id_type",
|
||||
"typeSchema": "public",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
"notNull": false
|
||||
},
|
||||
"external_id": {
|
||||
"name": "external_id",
|
||||
|
|
@ -453,7 +466,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games": {
|
||||
"public.games": {
|
||||
"name": "games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -461,7 +474,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -473,13 +487,13 @@
|
|||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"slug": {
|
||||
"name": "slug",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"description": {
|
||||
"name": "description",
|
||||
|
|
@ -547,40 +561,42 @@
|
|||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"text_searchable_index": {
|
||||
"name": "text_searchable_index",
|
||||
"type": "tsvector",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"last_sync_at": {
|
||||
"name": "last_sync_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {
|
||||
"text_searchable_idx": {
|
||||
"name": "text_searchable_idx",
|
||||
"search_index": {
|
||||
"name": "search_index",
|
||||
"columns": [
|
||||
"text_searchable_index"
|
||||
{
|
||||
"expression": "(\n\t\t\t\tsetweight(to_tsvector('english', \"name\"), 'A') ||\n setweight(to_tsvector('english', \"slug\"), 'B')\n )",
|
||||
"asc": true,
|
||||
"isExpression": true,
|
||||
"nulls": "last"
|
||||
}
|
||||
],
|
||||
"isUnique": false
|
||||
"isUnique": false,
|
||||
"concurrently": false,
|
||||
"method": "gin",
|
||||
"with": {}
|
||||
}
|
||||
},
|
||||
"foreignKeys": {},
|
||||
|
|
@ -595,7 +611,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games_to_external_ids": {
|
||||
"public.games_to_external_ids": {
|
||||
"name": "games_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -652,7 +668,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics": {
|
||||
"public.mechanics": {
|
||||
"name": "mechanics",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -660,7 +676,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -682,14 +699,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -708,7 +725,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"mechanics_to_external_ids": {
|
||||
"public.mechanics_to_external_ids": {
|
||||
"name": "mechanics_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -765,7 +782,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics_to_games": {
|
||||
"public.mechanics_to_games": {
|
||||
"name": "mechanics_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -822,7 +839,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"password_reset_tokens": {
|
||||
"public.password_reset_tokens": {
|
||||
"name": "password_reset_tokens",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -834,19 +851,26 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"expires_at": {
|
||||
"name": "expires_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -871,7 +895,7 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers": {
|
||||
"public.publishers": {
|
||||
"name": "publishers",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -879,7 +903,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -901,14 +926,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -927,7 +952,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"publishers_to_external_ids": {
|
||||
"public.publishers_to_external_ids": {
|
||||
"name": "publishers_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -984,7 +1009,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers_to_games": {
|
||||
"public.publishers_to_games": {
|
||||
"name": "publishers_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1041,7 +1066,71 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"roles": {
|
||||
"public.recovery_codes": {
|
||||
"name": "recovery_codes",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"used": {
|
||||
"name": "used",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"recovery_codes_user_id_users_id_fk": {
|
||||
"name": "recovery_codes_user_id_users_id_fk",
|
||||
"tableFrom": "recovery_codes",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"public.roles": {
|
||||
"name": "roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1049,19 +1138,34 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1084,7 +1188,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"sessions": {
|
||||
"public.sessions": {
|
||||
"name": "sessions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1096,7 +1200,7 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
|
|
@ -1117,6 +1221,20 @@
|
|||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"two_factor_auth_enabled": {
|
||||
"name": "two_factor_auth_enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"is_two_factor_authenticated": {
|
||||
"name": "is_two_factor_authenticated",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1138,7 +1256,98 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"user_roles": {
|
||||
"public.two_factor": {
|
||||
"name": "two_factor",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"two_factor_secret": {
|
||||
"name": "two_factor_secret",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"two_factor_enabled": {
|
||||
"name": "two_factor_enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": false
|
||||
},
|
||||
"initiated_time": {
|
||||
"name": "initiated_time",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"two_factor_user_id_users_id_fk": {
|
||||
"name": "two_factor_user_id_users_id_fk",
|
||||
"tableFrom": "two_factor",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {
|
||||
"two_factor_cuid_unique": {
|
||||
"name": "two_factor_cuid_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"cuid"
|
||||
]
|
||||
},
|
||||
"two_factor_user_id_unique": {
|
||||
"name": "two_factor_user_id_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"user_id"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"public.user_roles": {
|
||||
"name": "user_roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1146,7 +1355,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1156,26 +1366,33 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"role_id": {
|
||||
"name": "role_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"primary": {
|
||||
"name": "primary",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1221,7 +1438,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"users": {
|
||||
"public.users": {
|
||||
"name": "users",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1229,7 +1446,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1290,14 +1508,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1330,7 +1548,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlist_items": {
|
||||
"public.wishlist_items": {
|
||||
"name": "wishlist_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1338,7 +1556,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1348,26 +1567,26 @@
|
|||
},
|
||||
"wishlist_id": {
|
||||
"name": "wishlist_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"game_id": {
|
||||
"name": "game_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1413,7 +1632,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlists": {
|
||||
"public.wishlists": {
|
||||
"name": "wishlists",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1421,7 +1640,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1431,20 +1651,27 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Wishlist'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1479,16 +1706,17 @@
|
|||
}
|
||||
},
|
||||
"enums": {
|
||||
"external_id_type": {
|
||||
"public.external_id_type": {
|
||||
"name": "external_id_type",
|
||||
"values": {
|
||||
"game": "game",
|
||||
"category": "category",
|
||||
"mechanic": "mechanic",
|
||||
"publisher": "publisher",
|
||||
"designer": "designer",
|
||||
"artist": "artist"
|
||||
}
|
||||
"schema": "public",
|
||||
"values": [
|
||||
"game",
|
||||
"category",
|
||||
"mechanic",
|
||||
"publisher",
|
||||
"designer",
|
||||
"artist"
|
||||
]
|
||||
}
|
||||
},
|
||||
"schemas": {},
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
{
|
||||
"id": "7fd9b34f-059f-41a9-9a4c-f9769825233d",
|
||||
"prevId": "176e5b1f-d146-4604-ab17-b16052da13c0",
|
||||
"version": "5",
|
||||
"dialect": "pg",
|
||||
"id": "52e7c416-89cb-4c6a-9118-68a03cfc2920",
|
||||
"prevId": "e120d11a-bf28-4c96-9f2f-96e23e23c7e2",
|
||||
"version": "7",
|
||||
"dialect": "postgresql",
|
||||
"tables": {
|
||||
"categories": {
|
||||
"public.categories": {
|
||||
"name": "categories",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -12,7 +12,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -34,14 +35,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -60,7 +61,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"categories_to_external_ids": {
|
||||
"public.categories_to_external_ids": {
|
||||
"name": "categories_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -117,7 +118,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"categories_to_games": {
|
||||
"public.categories_to_games": {
|
||||
"name": "categories_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -174,7 +175,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"collection_items": {
|
||||
"public.collection_items": {
|
||||
"name": "collection_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -182,7 +183,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -211,14 +213,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -264,7 +266,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"collections": {
|
||||
"public.collections": {
|
||||
"name": "collections",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -272,7 +274,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -282,20 +285,27 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Collection'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -328,7 +338,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"expansions": {
|
||||
"public.expansions": {
|
||||
"name": "expansions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -336,7 +346,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -358,14 +369,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -411,7 +422,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"external_ids": {
|
||||
"public.external_ids": {
|
||||
"name": "external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -419,7 +430,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -430,8 +442,9 @@
|
|||
"type": {
|
||||
"name": "type",
|
||||
"type": "external_id_type",
|
||||
"typeSchema": "public",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
"notNull": false
|
||||
},
|
||||
"external_id": {
|
||||
"name": "external_id",
|
||||
|
|
@ -453,7 +466,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games": {
|
||||
"public.games": {
|
||||
"name": "games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -461,7 +474,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -473,13 +487,13 @@
|
|||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"slug": {
|
||||
"name": "slug",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"description": {
|
||||
"name": "description",
|
||||
|
|
@ -547,40 +561,42 @@
|
|||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"text_searchable_index": {
|
||||
"name": "text_searchable_index",
|
||||
"type": "tsvector",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"last_sync_at": {
|
||||
"name": "last_sync_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {
|
||||
"text_searchable_idx": {
|
||||
"name": "text_searchable_idx",
|
||||
"search_index": {
|
||||
"name": "search_index",
|
||||
"columns": [
|
||||
"text_searchable_index"
|
||||
{
|
||||
"expression": "(\n\t\t\t\tsetweight(to_tsvector('english', \"name\"), 'A') ||\n setweight(to_tsvector('english', \"slug\"), 'B')\n )",
|
||||
"asc": true,
|
||||
"isExpression": true,
|
||||
"nulls": "last"
|
||||
}
|
||||
],
|
||||
"isUnique": false
|
||||
"isUnique": false,
|
||||
"concurrently": false,
|
||||
"method": "gin",
|
||||
"with": {}
|
||||
}
|
||||
},
|
||||
"foreignKeys": {},
|
||||
|
|
@ -595,7 +611,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games_to_external_ids": {
|
||||
"public.games_to_external_ids": {
|
||||
"name": "games_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -652,7 +668,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics": {
|
||||
"public.mechanics": {
|
||||
"name": "mechanics",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -660,7 +676,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -682,14 +699,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -708,7 +725,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"mechanics_to_external_ids": {
|
||||
"public.mechanics_to_external_ids": {
|
||||
"name": "mechanics_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -765,7 +782,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics_to_games": {
|
||||
"public.mechanics_to_games": {
|
||||
"name": "mechanics_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -822,7 +839,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"password_reset_tokens": {
|
||||
"public.password_reset_tokens": {
|
||||
"name": "password_reset_tokens",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -834,19 +851,26 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"expires_at": {
|
||||
"name": "expires_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -871,7 +895,7 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers": {
|
||||
"public.publishers": {
|
||||
"name": "publishers",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -879,7 +903,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -901,14 +926,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -927,7 +952,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"publishers_to_external_ids": {
|
||||
"public.publishers_to_external_ids": {
|
||||
"name": "publishers_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -984,7 +1009,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers_to_games": {
|
||||
"public.publishers_to_games": {
|
||||
"name": "publishers_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1041,7 +1066,71 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"roles": {
|
||||
"public.recovery_codes": {
|
||||
"name": "recovery_codes",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"used": {
|
||||
"name": "used",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"recovery_codes_user_id_users_id_fk": {
|
||||
"name": "recovery_codes_user_id_users_id_fk",
|
||||
"tableFrom": "recovery_codes",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"public.roles": {
|
||||
"name": "roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1049,19 +1138,34 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1084,7 +1188,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"sessions": {
|
||||
"public.sessions": {
|
||||
"name": "sessions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1096,7 +1200,7 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
|
|
@ -1117,6 +1221,20 @@
|
|||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"two_factor_auth_enabled": {
|
||||
"name": "two_factor_auth_enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"is_two_factor_authenticated": {
|
||||
"name": "is_two_factor_authenticated",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1138,7 +1256,98 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"user_roles": {
|
||||
"public.two_factor": {
|
||||
"name": "two_factor",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"secret": {
|
||||
"name": "secret",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"enabled": {
|
||||
"name": "enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": false
|
||||
},
|
||||
"initiated_time": {
|
||||
"name": "initiated_time",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"two_factor_user_id_users_id_fk": {
|
||||
"name": "two_factor_user_id_users_id_fk",
|
||||
"tableFrom": "two_factor",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {
|
||||
"two_factor_cuid_unique": {
|
||||
"name": "two_factor_cuid_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"cuid"
|
||||
]
|
||||
},
|
||||
"two_factor_user_id_unique": {
|
||||
"name": "two_factor_user_id_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"user_id"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"public.user_roles": {
|
||||
"name": "user_roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1146,7 +1355,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1156,26 +1366,33 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"role_id": {
|
||||
"name": "role_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"primary": {
|
||||
"name": "primary",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1221,7 +1438,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"users": {
|
||||
"public.users": {
|
||||
"name": "users",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1229,7 +1446,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1290,14 +1508,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1330,7 +1548,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlist_items": {
|
||||
"public.wishlist_items": {
|
||||
"name": "wishlist_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1338,7 +1556,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1360,14 +1579,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1413,7 +1632,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlists": {
|
||||
"public.wishlists": {
|
||||
"name": "wishlists",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1421,7 +1640,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1431,20 +1651,27 @@
|
|||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Wishlist'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1479,16 +1706,17 @@
|
|||
}
|
||||
},
|
||||
"enums": {
|
||||
"external_id_type": {
|
||||
"public.external_id_type": {
|
||||
"name": "external_id_type",
|
||||
"values": {
|
||||
"game": "game",
|
||||
"category": "category",
|
||||
"mechanic": "mechanic",
|
||||
"publisher": "publisher",
|
||||
"designer": "designer",
|
||||
"artist": "artist"
|
||||
}
|
||||
"schema": "public",
|
||||
"values": [
|
||||
"game",
|
||||
"category",
|
||||
"mechanic",
|
||||
"publisher",
|
||||
"designer",
|
||||
"artist"
|
||||
]
|
||||
}
|
||||
},
|
||||
"schemas": {},
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
{
|
||||
"id": "e088433f-589d-4c15-953e-3b32e85e658f",
|
||||
"prevId": "7fd9b34f-059f-41a9-9a4c-f9769825233d",
|
||||
"version": "5",
|
||||
"dialect": "pg",
|
||||
"id": "79adee85-e57c-4a9f-87df-835457b68129",
|
||||
"prevId": "52e7c416-89cb-4c6a-9118-68a03cfc2920",
|
||||
"version": "7",
|
||||
"dialect": "postgresql",
|
||||
"tables": {
|
||||
"categories": {
|
||||
"public.categories": {
|
||||
"name": "categories",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -12,7 +12,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -34,14 +35,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -60,7 +61,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"categories_to_external_ids": {
|
||||
"public.categories_to_external_ids": {
|
||||
"name": "categories_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -117,7 +118,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"categories_to_games": {
|
||||
"public.categories_to_games": {
|
||||
"name": "categories_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -174,7 +175,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"collection_items": {
|
||||
"public.collection_items": {
|
||||
"name": "collection_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -182,7 +183,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -211,14 +213,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -264,7 +266,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"collections": {
|
||||
"public.collections": {
|
||||
"name": "collections",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -272,7 +274,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -286,16 +289,23 @@
|
|||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Collection'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -328,7 +338,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"expansions": {
|
||||
"public.expansions": {
|
||||
"name": "expansions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -336,7 +346,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -358,14 +369,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -411,7 +422,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"external_ids": {
|
||||
"public.external_ids": {
|
||||
"name": "external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -419,7 +430,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -430,8 +442,9 @@
|
|||
"type": {
|
||||
"name": "type",
|
||||
"type": "external_id_type",
|
||||
"typeSchema": "public",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
"notNull": false
|
||||
},
|
||||
"external_id": {
|
||||
"name": "external_id",
|
||||
|
|
@ -453,7 +466,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games": {
|
||||
"public.games": {
|
||||
"name": "games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -461,7 +474,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -473,13 +487,13 @@
|
|||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"slug": {
|
||||
"name": "slug",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"description": {
|
||||
"name": "description",
|
||||
|
|
@ -547,40 +561,42 @@
|
|||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"text_searchable_index": {
|
||||
"name": "text_searchable_index",
|
||||
"type": "tsvector",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"last_sync_at": {
|
||||
"name": "last_sync_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {
|
||||
"text_searchable_idx": {
|
||||
"name": "text_searchable_idx",
|
||||
"search_index": {
|
||||
"name": "search_index",
|
||||
"columns": [
|
||||
"text_searchable_index"
|
||||
{
|
||||
"expression": "(\n\t\t\t\tsetweight(to_tsvector('english', \"name\"), 'A') ||\n setweight(to_tsvector('english', \"slug\"), 'B')\n )",
|
||||
"asc": true,
|
||||
"isExpression": true,
|
||||
"nulls": "last"
|
||||
}
|
||||
],
|
||||
"isUnique": false
|
||||
"isUnique": false,
|
||||
"concurrently": false,
|
||||
"method": "gin",
|
||||
"with": {}
|
||||
}
|
||||
},
|
||||
"foreignKeys": {},
|
||||
|
|
@ -595,7 +611,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"games_to_external_ids": {
|
||||
"public.games_to_external_ids": {
|
||||
"name": "games_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -652,7 +668,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics": {
|
||||
"public.mechanics": {
|
||||
"name": "mechanics",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -660,7 +676,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -682,14 +699,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -708,7 +725,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"mechanics_to_external_ids": {
|
||||
"public.mechanics_to_external_ids": {
|
||||
"name": "mechanics_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -765,7 +782,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"mechanics_to_games": {
|
||||
"public.mechanics_to_games": {
|
||||
"name": "mechanics_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -822,7 +839,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"password_reset_tokens": {
|
||||
"public.password_reset_tokens": {
|
||||
"name": "password_reset_tokens",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -840,13 +857,20 @@
|
|||
},
|
||||
"expires_at": {
|
||||
"name": "expires_at",
|
||||
"type": "timestamp (6) with time zone",
|
||||
"type": "timestamp",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -871,7 +895,7 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers": {
|
||||
"public.publishers": {
|
||||
"name": "publishers",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -879,7 +903,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -901,14 +926,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -927,7 +952,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"publishers_to_external_ids": {
|
||||
"public.publishers_to_external_ids": {
|
||||
"name": "publishers_to_external_ids",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -984,7 +1009,7 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"publishers_to_games": {
|
||||
"public.publishers_to_games": {
|
||||
"name": "publishers_to_games",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1041,7 +1066,71 @@
|
|||
},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"roles": {
|
||||
"public.recovery_codes": {
|
||||
"name": "recovery_codes",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"code": {
|
||||
"name": "code",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"used": {
|
||||
"name": "used",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"recovery_codes_user_id_users_id_fk": {
|
||||
"name": "recovery_codes_user_id_users_id_fk",
|
||||
"tableFrom": "recovery_codes",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"public.roles": {
|
||||
"name": "roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1049,19 +1138,34 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1084,7 +1188,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"sessions": {
|
||||
"public.sessions": {
|
||||
"name": "sessions",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1117,6 +1221,20 @@
|
|||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"two_factor_auth_enabled": {
|
||||
"name": "two_factor_auth_enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"is_two_factor_authenticated": {
|
||||
"name": "is_two_factor_authenticated",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
|
|
@ -1138,7 +1256,98 @@
|
|||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {}
|
||||
},
|
||||
"user_roles": {
|
||||
"public.two_factor": {
|
||||
"name": "two_factor",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
"id": {
|
||||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"secret": {
|
||||
"name": "secret",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"enabled": {
|
||||
"name": "enabled",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": false
|
||||
},
|
||||
"initiated_time": {
|
||||
"name": "initiated_time",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": false
|
||||
},
|
||||
"user_id": {
|
||||
"name": "user_id",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
}
|
||||
},
|
||||
"indexes": {},
|
||||
"foreignKeys": {
|
||||
"two_factor_user_id_users_id_fk": {
|
||||
"name": "two_factor_user_id_users_id_fk",
|
||||
"tableFrom": "two_factor",
|
||||
"tableTo": "users",
|
||||
"columnsFrom": [
|
||||
"user_id"
|
||||
],
|
||||
"columnsTo": [
|
||||
"id"
|
||||
],
|
||||
"onDelete": "no action",
|
||||
"onUpdate": "no action"
|
||||
}
|
||||
},
|
||||
"compositePrimaryKeys": {},
|
||||
"uniqueConstraints": {
|
||||
"two_factor_cuid_unique": {
|
||||
"name": "two_factor_cuid_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"cuid"
|
||||
]
|
||||
},
|
||||
"two_factor_user_id_unique": {
|
||||
"name": "two_factor_user_id_unique",
|
||||
"nullsNotDistinct": false,
|
||||
"columns": [
|
||||
"user_id"
|
||||
]
|
||||
}
|
||||
}
|
||||
},
|
||||
"public.user_roles": {
|
||||
"name": "user_roles",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1146,7 +1355,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1162,20 +1372,27 @@
|
|||
},
|
||||
"role_id": {
|
||||
"name": "role_id",
|
||||
"type": "text",
|
||||
"type": "uuid",
|
||||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"primary": {
|
||||
"name": "primary",
|
||||
"type": "boolean",
|
||||
"primaryKey": false,
|
||||
"notNull": false,
|
||||
"default": false
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1221,7 +1438,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"users": {
|
||||
"public.users": {
|
||||
"name": "users",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1229,7 +1446,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1290,14 +1508,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1330,7 +1548,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlist_items": {
|
||||
"public.wishlist_items": {
|
||||
"name": "wishlist_items",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1338,7 +1556,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1360,14 +1579,14 @@
|
|||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1413,7 +1632,7 @@
|
|||
}
|
||||
}
|
||||
},
|
||||
"wishlists": {
|
||||
"public.wishlists": {
|
||||
"name": "wishlists",
|
||||
"schema": "",
|
||||
"columns": {
|
||||
|
|
@ -1421,7 +1640,8 @@
|
|||
"name": "id",
|
||||
"type": "uuid",
|
||||
"primaryKey": true,
|
||||
"notNull": true
|
||||
"notNull": true,
|
||||
"default": "gen_random_uuid()"
|
||||
},
|
||||
"cuid": {
|
||||
"name": "cuid",
|
||||
|
|
@ -1435,16 +1655,23 @@
|
|||
"primaryKey": false,
|
||||
"notNull": true
|
||||
},
|
||||
"name": {
|
||||
"name": "name",
|
||||
"type": "text",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "'My Wishlist'"
|
||||
},
|
||||
"created_at": {
|
||||
"name": "created_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
},
|
||||
"updated_at": {
|
||||
"name": "updated_at",
|
||||
"type": "timestamp",
|
||||
"type": "timestamp with time zone",
|
||||
"primaryKey": false,
|
||||
"notNull": true,
|
||||
"default": "now()"
|
||||
|
|
@ -1479,16 +1706,17 @@
|
|||
}
|
||||
},
|
||||
"enums": {
|
||||
"external_id_type": {
|
||||
"public.external_id_type": {
|
||||
"name": "external_id_type",
|
||||
"values": {
|
||||
"game": "game",
|
||||
"category": "category",
|
||||
"mechanic": "mechanic",
|
||||
"publisher": "publisher",
|
||||
"designer": "designer",
|
||||
"artist": "artist"
|
||||
}
|
||||
"schema": "public",
|
||||
"values": [
|
||||
"game",
|
||||
"category",
|
||||
"mechanic",
|
||||
"publisher",
|
||||
"designer",
|
||||
"artist"
|
||||
]
|
||||
}
|
||||
},
|
||||
"schemas": {},
|
||||
27
src/db/migrations/meta/_journal.json
Normal file
27
src/db/migrations/meta/_journal.json
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
{
|
||||
"version": "7",
|
||||
"dialect": "postgresql",
|
||||
"entries": [
|
||||
{
|
||||
"idx": 0,
|
||||
"version": "7",
|
||||
"when": 1720625651245,
|
||||
"tag": "0000_dazzling_stick",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 1,
|
||||
"version": "7",
|
||||
"when": 1720625948784,
|
||||
"tag": "0001_noisy_sally_floyd",
|
||||
"breakpoints": true
|
||||
},
|
||||
{
|
||||
"idx": 2,
|
||||
"version": "7",
|
||||
"when": 1720626020902,
|
||||
"tag": "0002_fancy_valkyrie",
|
||||
"breakpoints": true
|
||||
}
|
||||
]
|
||||
}
|
||||
25
src/db/schema/categories.ts
Normal file
25
src/db/schema/categories.ts
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import categoriesToExternalIds from './categoriesToExternalIds';
|
||||
import categories_to_games from './categoriesToGames';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const categories = pgTable('categories', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
name: text('name'),
|
||||
slug: text('slug'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Categories = InferSelectModel<typeof categories>;
|
||||
|
||||
export const categories_relations = relations(categories, ({ many }) => ({
|
||||
categories_to_games: many(categories_to_games),
|
||||
categoriesToExternalIds: many(categoriesToExternalIds),
|
||||
}));
|
||||
|
||||
export default categories;
|
||||
24
src/db/schema/categoriesToExternalIds.ts
Normal file
24
src/db/schema/categoriesToExternalIds.ts
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import categories from './categories';
|
||||
import externalIds from './externalIds';
|
||||
|
||||
const categoriesToExternalIds = pgTable(
|
||||
'categories_to_external_ids',
|
||||
{
|
||||
categoryId: uuid('category_id')
|
||||
.notNull()
|
||||
.references(() => categories.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
externalId: uuid('external_id')
|
||||
.notNull()
|
||||
.references(() => externalIds.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
categoriesToExternalIdsPkey: primaryKey({
|
||||
columns: [table.categoryId, table.externalId],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export default categoriesToExternalIds;
|
||||
36
src/db/schema/categoriesToGames.ts
Normal file
36
src/db/schema/categoriesToGames.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import { relations } from 'drizzle-orm';
|
||||
import categories from './categories';
|
||||
import games from './games';
|
||||
|
||||
const categories_to_games = pgTable(
|
||||
'categories_to_games',
|
||||
{
|
||||
category_id: uuid('category_id')
|
||||
.notNull()
|
||||
.references(() => categories.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
categoriesToGamesPkey: primaryKey({
|
||||
columns: [table.category_id, table.game_id],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export const categories_to_games_relations = relations(categories_to_games, ({ one }) => ({
|
||||
category: one(categories, {
|
||||
fields: [categories_to_games.category_id],
|
||||
references: [categories.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [categories_to_games.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default categories_to_games;
|
||||
36
src/db/schema/collectionItems.ts
Normal file
36
src/db/schema/collectionItems.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
import { integer, pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import collections from './collections';
|
||||
import games from './games';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const collection_items = pgTable('collection_items', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
collection_id: uuid('collection_id')
|
||||
.notNull()
|
||||
.references(() => collections.id, { onDelete: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'cascade' }),
|
||||
times_played: integer('times_played').default(0),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type CollectionItems = InferSelectModel<typeof collection_items>;
|
||||
|
||||
export const collection_item_relations = relations(collection_items, ({ one }) => ({
|
||||
collection: one(collections, {
|
||||
fields: [collection_items.collection_id],
|
||||
references: [collections.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [collection_items.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default collection_items;
|
||||
28
src/db/schema/collections.ts
Normal file
28
src/db/schema/collections.ts
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
import { pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const collections = pgTable('collections', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
user_id: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id, { onDelete: 'cascade' }),
|
||||
name: text('name').notNull().default('My Collection'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export const collection_relations = relations(collections, ({ one }) => ({
|
||||
user: one(users, {
|
||||
fields: [collections.user_id],
|
||||
references: [users.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export type Collections = InferSelectModel<typeof collections>;
|
||||
|
||||
export default collections;
|
||||
34
src/db/schema/expansions.ts
Normal file
34
src/db/schema/expansions.ts
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
import { pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import games from './games';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
export const expansions = pgTable('expansions', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
base_game_id: uuid('base_game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Expansions = InferSelectModel<typeof expansions>;
|
||||
|
||||
export const expansion_relations = relations(expansions, ({ one }) => ({
|
||||
baseGame: one(games, {
|
||||
fields: [expansions.base_game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [expansions.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default expansions;
|
||||
25
src/db/schema/externalIds.ts
Normal file
25
src/db/schema/externalIds.ts
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
import { pgEnum, pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import type { InferSelectModel } from 'drizzle-orm';
|
||||
|
||||
export const externalIdType = pgEnum('external_id_type', [
|
||||
'game',
|
||||
'category',
|
||||
'mechanic',
|
||||
'publisher',
|
||||
'designer',
|
||||
'artist',
|
||||
]);
|
||||
|
||||
const externalIds = pgTable('external_ids', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
type: externalIdType('type'),
|
||||
externalId: text('external_id').notNull(),
|
||||
});
|
||||
|
||||
export type ExternalIds = InferSelectModel<typeof externalIds>;
|
||||
|
||||
export default externalIds;
|
||||
53
src/db/schema/games.ts
Normal file
53
src/db/schema/games.ts
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
import { index, integer, pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations, sql } from 'drizzle-orm';
|
||||
import categoriesToGames from './categoriesToGames';
|
||||
import gamesToExternalIds from './gamesToExternalIds';
|
||||
import mechanicsToGames from './mechanicsToGames';
|
||||
import publishersToGames from './publishersToGames';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const games = pgTable(
|
||||
'games',
|
||||
{
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
name: text('name').notNull(),
|
||||
slug: text('slug').notNull(),
|
||||
description: text('description'),
|
||||
year_published: integer('year_published'),
|
||||
min_players: integer('min_players'),
|
||||
max_players: integer('max_players'),
|
||||
playtime: integer('playtime'),
|
||||
min_playtime: integer('min_playtime'),
|
||||
max_playtime: integer('max_playtime'),
|
||||
min_age: integer('min_age'),
|
||||
image_url: text('image_url'),
|
||||
thumb_url: text('thumb_url'),
|
||||
url: text('url'),
|
||||
last_sync_at: timestamp('last_sync_at'),
|
||||
...timestamps,
|
||||
},
|
||||
(table) => ({
|
||||
searchIndex: index('search_index').using(
|
||||
'gin',
|
||||
sql`(
|
||||
setweight(to_tsvector('english', ${table.name}), 'A') ||
|
||||
setweight(to_tsvector('english', ${table.slug}), 'B')
|
||||
)`,
|
||||
),
|
||||
}),
|
||||
);
|
||||
|
||||
export const gameRelations = relations(games, ({ many }) => ({
|
||||
categories_to_games: many(categoriesToGames),
|
||||
mechanics_to_games: many(mechanicsToGames),
|
||||
publishers_to_games: many(publishersToGames),
|
||||
gamesToExternalIds: many(gamesToExternalIds),
|
||||
}));
|
||||
|
||||
export type Games = InferSelectModel<typeof games>;
|
||||
|
||||
export default games;
|
||||
24
src/db/schema/gamesToExternalIds.ts
Normal file
24
src/db/schema/gamesToExternalIds.ts
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import games from './games';
|
||||
import externalIds from './externalIds';
|
||||
|
||||
const gamesToExternalIds = pgTable(
|
||||
'games_to_external_ids',
|
||||
{
|
||||
gameId: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
externalId: uuid('external_id')
|
||||
.notNull()
|
||||
.references(() => externalIds.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
gamesToExternalIdsPkey: primaryKey({
|
||||
columns: [table.gameId, table.externalId],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export default gamesToExternalIds;
|
||||
36
src/db/schema/index.ts
Normal file
36
src/db/schema/index.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
export { default as users, user_relations, type Users } from './users';
|
||||
export { default as recoveryCodes, type RecoveryCodes } from './recoveryCodes';
|
||||
export {
|
||||
default as password_reset_tokens,
|
||||
password_reset_token_relations,
|
||||
type PasswordResetTokens,
|
||||
} from './passwordResetTokens';
|
||||
export { default as sessions, type Sessions } from './sessions';
|
||||
export { default as roles, role_relations, type Roles } from './roles';
|
||||
export { default as userRoles, user_role_relations, type UserRoles } from './userRoles';
|
||||
export { default as collections, collection_relations, type Collections } from './collections';
|
||||
export {
|
||||
default as collection_items,
|
||||
collection_item_relations,
|
||||
type CollectionItems,
|
||||
} from './collectionItems';
|
||||
export { default as wishlists, wishlists_relations, type Wishlists } from './wishlists';
|
||||
export {
|
||||
default as wishlist_items,
|
||||
wishlist_item_relations,
|
||||
type WishlistItems,
|
||||
} from './wishlistItems';
|
||||
export { default as externalIds, type ExternalIds, externalIdType } from './externalIds';
|
||||
export { default as games, gameRelations, type Games } from './games';
|
||||
export { default as gamesToExternalIds } from './gamesToExternalIds';
|
||||
export { default as expansions, expansion_relations, type Expansions } from './expansions';
|
||||
export { default as publishers, publishers_relations, type Publishers } from './publishers';
|
||||
export { default as publishers_to_games, publishers_to_games_relations } from './publishersToGames';
|
||||
export { default as publishersToExternalIds } from './publishersToExternalIds';
|
||||
export { default as categories, categories_relations, type Categories } from './categories';
|
||||
export { default as categoriesToExternalIds } from './categoriesToExternalIds';
|
||||
export { default as categories_to_games, categories_to_games_relations } from './categoriesToGames';
|
||||
export { default as mechanics, mechanics_relations, type Mechanics } from './mechanics';
|
||||
export { default as mechanicsToExternalIds } from './mechanicsToExternalIds';
|
||||
export { default as mechanics_to_games, mechanics_to_games_relations } from './mechanicsToGames';
|
||||
export { default as twoFactor } from './two-factor.table';
|
||||
25
src/db/schema/mechanics.ts
Normal file
25
src/db/schema/mechanics.ts
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import mechanicsToGames from './mechanicsToGames';
|
||||
import mechanicsToExternalIds from './mechanicsToExternalIds';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const mechanics = pgTable('mechanics', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
name: text('name'),
|
||||
slug: text('slug'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Mechanics = InferSelectModel<typeof mechanics>;
|
||||
|
||||
export const mechanics_relations = relations(mechanics, ({ many }) => ({
|
||||
mechanics_to_games: many(mechanicsToGames),
|
||||
mechanicsToExternalIds: many(mechanicsToExternalIds),
|
||||
}));
|
||||
|
||||
export default mechanics;
|
||||
24
src/db/schema/mechanicsToExternalIds.ts
Normal file
24
src/db/schema/mechanicsToExternalIds.ts
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import mechanics from './mechanics';
|
||||
import externalIds from './externalIds';
|
||||
|
||||
const mechanicsToExternalIds = pgTable(
|
||||
'mechanics_to_external_ids',
|
||||
{
|
||||
mechanicId: uuid('mechanic_id')
|
||||
.notNull()
|
||||
.references(() => mechanics.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
externalId: uuid('external_id')
|
||||
.notNull()
|
||||
.references(() => externalIds.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
mechanicsToExternalIdsPkey: primaryKey({
|
||||
columns: [table.mechanicId, table.externalId],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export default mechanicsToExternalIds;
|
||||
36
src/db/schema/mechanicsToGames.ts
Normal file
36
src/db/schema/mechanicsToGames.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import { relations } from 'drizzle-orm';
|
||||
import mechanics from './mechanics';
|
||||
import games from './games';
|
||||
|
||||
const mechanics_to_games = pgTable(
|
||||
'mechanics_to_games',
|
||||
{
|
||||
mechanic_id: uuid('mechanic_id')
|
||||
.notNull()
|
||||
.references(() => mechanics.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
mechanicsToGamesPkey: primaryKey({
|
||||
columns: [table.mechanic_id, table.game_id],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export const mechanics_to_games_relations = relations(mechanics_to_games, ({ one }) => ({
|
||||
mechanic: one(mechanics, {
|
||||
fields: [mechanics_to_games.mechanic_id],
|
||||
references: [mechanics.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [mechanics_to_games.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default mechanics_to_games;
|
||||
27
src/db/schema/passwordResetTokens.ts
Normal file
27
src/db/schema/passwordResetTokens.ts
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
import { pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const password_reset_tokens = pgTable('password_reset_tokens', {
|
||||
id: text('id')
|
||||
.primaryKey()
|
||||
.$defaultFn(() => cuid2()),
|
||||
user_id: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id, { onDelete: 'cascade' }),
|
||||
expires_at: timestamp('expires_at'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type PasswordResetTokens = InferSelectModel<typeof password_reset_tokens>;
|
||||
|
||||
export const password_reset_token_relations = relations(password_reset_tokens, ({ one }) => ({
|
||||
user: one(users, {
|
||||
fields: [password_reset_tokens.user_id],
|
||||
references: [users.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default password_reset_tokens;
|
||||
25
src/db/schema/publishers.ts
Normal file
25
src/db/schema/publishers.ts
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import publishers_to_games from './publishersToGames';
|
||||
import publishersToExternalIds from './publishersToExternalIds';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const publishers = pgTable('publishers', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
name: text('name'),
|
||||
slug: text('slug'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Publishers = InferSelectModel<typeof publishers>;
|
||||
|
||||
export const publishers_relations = relations(publishers, ({ many }) => ({
|
||||
publishers_to_games: many(publishers_to_games),
|
||||
publishersToExternalIds: many(publishersToExternalIds),
|
||||
}));
|
||||
|
||||
export default publishers;
|
||||
24
src/db/schema/publishersToExternalIds.ts
Normal file
24
src/db/schema/publishersToExternalIds.ts
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import publishers from './publishers';
|
||||
import externalIds from './externalIds';
|
||||
|
||||
const publishersToExternalIds = pgTable(
|
||||
'publishers_to_external_ids',
|
||||
{
|
||||
publisherId: uuid('publisher_id')
|
||||
.notNull()
|
||||
.references(() => publishers.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
externalId: uuid('external_id')
|
||||
.notNull()
|
||||
.references(() => externalIds.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
publishersToExternalIdsPkey: primaryKey({
|
||||
columns: [table.publisherId, table.externalId],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export default publishersToExternalIds;
|
||||
36
src/db/schema/publishersToGames.ts
Normal file
36
src/db/schema/publishersToGames.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
import { pgTable, primaryKey, uuid } from 'drizzle-orm/pg-core';
|
||||
import { relations } from 'drizzle-orm';
|
||||
import publishers from './publishers';
|
||||
import games from './games';
|
||||
|
||||
const publishers_to_games = pgTable(
|
||||
'publishers_to_games',
|
||||
{
|
||||
publisher_id: uuid('publisher_id')
|
||||
.notNull()
|
||||
.references(() => publishers.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'restrict', onUpdate: 'cascade' }),
|
||||
},
|
||||
(table) => {
|
||||
return {
|
||||
publishersToGamesPkey: primaryKey({
|
||||
columns: [table.publisher_id, table.game_id],
|
||||
}),
|
||||
};
|
||||
},
|
||||
);
|
||||
|
||||
export const publishers_to_games_relations = relations(publishers_to_games, ({ one }) => ({
|
||||
publisher: one(publishers, {
|
||||
fields: [publishers_to_games.publisher_id],
|
||||
references: [publishers.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [publishers_to_games.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default publishers_to_games;
|
||||
18
src/db/schema/recoveryCodes.ts
Normal file
18
src/db/schema/recoveryCodes.ts
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
import { boolean, pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import type { InferSelectModel } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const recovery_codes = pgTable('recovery_codes', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
userId: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id),
|
||||
code: text('code').notNull(),
|
||||
used: boolean('used').default(false),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type RecoveryCodes = InferSelectModel<typeof recovery_codes>;
|
||||
|
||||
export default recovery_codes;
|
||||
23
src/db/schema/roles.ts
Normal file
23
src/db/schema/roles.ts
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import user_roles from './userRoles';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const roles = pgTable('roles', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2())
|
||||
.notNull(),
|
||||
name: text('name').unique().notNull(),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Roles = InferSelectModel<typeof roles>;
|
||||
|
||||
export const role_relations = relations(roles, ({ many }) => ({
|
||||
user_roles: many(user_roles),
|
||||
}));
|
||||
|
||||
export default roles;
|
||||
22
src/db/schema/sessions.ts
Normal file
22
src/db/schema/sessions.ts
Normal file
|
|
@ -0,0 +1,22 @@
|
|||
import { boolean, pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { type InferSelectModel } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
|
||||
const sessions = pgTable('sessions', {
|
||||
id: text('id').primaryKey(),
|
||||
userId: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id),
|
||||
expiresAt: timestamp('expires_at', {
|
||||
withTimezone: true,
|
||||
mode: 'date',
|
||||
}).notNull(),
|
||||
ipCountry: text('ip_country'),
|
||||
ipAddress: text('ip_address'),
|
||||
twoFactorAuthEnabled: boolean('two_factor_auth_enabled').default(false),
|
||||
isTwoFactorAuthenticated: boolean('is_two_factor_authenticated').default(false),
|
||||
});
|
||||
|
||||
export type Sessions = InferSelectModel<typeof sessions>;
|
||||
|
||||
export default sessions;
|
||||
34
src/db/schema/two-factor.table.ts
Normal file
34
src/db/schema/two-factor.table.ts
Normal file
|
|
@ -0,0 +1,34 @@
|
|||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import { boolean, pgTable, text, timestamp, uuid } from 'drizzle-orm/pg-core';
|
||||
import { timestamps } from '../utils';
|
||||
import users from './users';
|
||||
|
||||
const twoFactorTable = pgTable('two_factor', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
secret: text('secret').notNull(),
|
||||
enabled: boolean('enabled').notNull().default(false),
|
||||
initiatedTime: timestamp('initiated_time', {
|
||||
mode: 'date',
|
||||
withTimezone: true,
|
||||
}),
|
||||
userId: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id)
|
||||
.unique(),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export const emailVerificationsRelations = relations(twoFactorTable, ({ one }) => ({
|
||||
user: one(users, {
|
||||
fields: [twoFactorTable.userId],
|
||||
references: [users.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export type TwoFactor = InferSelectModel<typeof twoFactorTable>;
|
||||
|
||||
export default twoFactorTable;
|
||||
36
src/db/schema/userRoles.ts
Normal file
36
src/db/schema/userRoles.ts
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
import { boolean, pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
import roles from './roles';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const user_roles = pgTable('user_roles', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
user_id: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id, { onDelete: 'cascade' }),
|
||||
role_id: uuid('role_id')
|
||||
.notNull()
|
||||
.references(() => roles.id, { onDelete: 'cascade' }),
|
||||
primary: boolean('primary').default(false),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export const user_role_relations = relations(user_roles, ({ one }) => ({
|
||||
role: one(roles, {
|
||||
fields: [user_roles.role_id],
|
||||
references: [roles.id],
|
||||
}),
|
||||
user: one(users, {
|
||||
fields: [user_roles.user_id],
|
||||
references: [users.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export type UserRoles = InferSelectModel<typeof user_roles>;
|
||||
|
||||
export default user_roles;
|
||||
29
src/db/schema/users.ts
Normal file
29
src/db/schema/users.ts
Normal file
|
|
@ -0,0 +1,29 @@
|
|||
import { boolean, pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import { timestamps } from '../utils';
|
||||
import user_roles from './userRoles';
|
||||
|
||||
const users = pgTable('users', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
username: text('username').unique(),
|
||||
hashed_password: text('hashed_password'),
|
||||
email: text('email').unique(),
|
||||
first_name: text('first_name'),
|
||||
last_name: text('last_name'),
|
||||
verified: boolean('verified').default(false),
|
||||
receive_email: boolean('receive_email').default(false),
|
||||
theme: text('theme').default('system'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export const user_relations = relations(users, ({ many }) => ({
|
||||
user_roles: many(user_roles),
|
||||
}));
|
||||
|
||||
export type Users = InferSelectModel<typeof users>;
|
||||
|
||||
export default users;
|
||||
35
src/db/schema/wishlistItems.ts
Normal file
35
src/db/schema/wishlistItems.ts
Normal file
|
|
@ -0,0 +1,35 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import wishlists from './wishlists';
|
||||
import games from './games';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const wishlist_items = pgTable('wishlist_items', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
wishlist_id: uuid('wishlist_id')
|
||||
.notNull()
|
||||
.references(() => wishlists.id, { onDelete: 'cascade' }),
|
||||
game_id: uuid('game_id')
|
||||
.notNull()
|
||||
.references(() => games.id, { onDelete: 'cascade' }),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type WishlistItems = InferSelectModel<typeof wishlist_items>;
|
||||
|
||||
export const wishlist_item_relations = relations(wishlist_items, ({ one }) => ({
|
||||
wishlist: one(wishlists, {
|
||||
fields: [wishlist_items.wishlist_id],
|
||||
references: [wishlists.id],
|
||||
}),
|
||||
game: one(games, {
|
||||
fields: [wishlist_items.game_id],
|
||||
references: [games.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default wishlist_items;
|
||||
28
src/db/schema/wishlists.ts
Normal file
28
src/db/schema/wishlists.ts
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
import { pgTable, text, uuid } from 'drizzle-orm/pg-core';
|
||||
import { createId as cuid2 } from '@paralleldrive/cuid2';
|
||||
import { type InferSelectModel, relations } from 'drizzle-orm';
|
||||
import users from './users';
|
||||
import { timestamps } from '../utils';
|
||||
|
||||
const wishlists = pgTable('wishlists', {
|
||||
id: uuid('id').primaryKey().defaultRandom(),
|
||||
cuid: text('cuid')
|
||||
.unique()
|
||||
.$defaultFn(() => cuid2()),
|
||||
user_id: uuid('user_id')
|
||||
.notNull()
|
||||
.references(() => users.id, { onDelete: 'cascade' }),
|
||||
name: text('name').notNull().default('My Wishlist'),
|
||||
...timestamps,
|
||||
});
|
||||
|
||||
export type Wishlists = InferSelectModel<typeof wishlists>;
|
||||
|
||||
export const wishlists_relations = relations(wishlists, ({ one }) => ({
|
||||
user: one(users, {
|
||||
fields: [wishlists.user_id],
|
||||
references: [users.id],
|
||||
}),
|
||||
}));
|
||||
|
||||
export default wishlists;
|
||||
48
src/db/seed.ts
Normal file
48
src/db/seed.ts
Normal file
|
|
@ -0,0 +1,48 @@
|
|||
import { Table, getTableName, sql } from 'drizzle-orm';
|
||||
import env from '../env';
|
||||
import { db, pool } from '$db';
|
||||
import * as schema from './schema';
|
||||
import * as seeds from './seeds';
|
||||
|
||||
if (!env.DB_SEEDING) {
|
||||
throw new Error('You must set DB_SEEDING to "true" when running seeds');
|
||||
}
|
||||
|
||||
async function resetTable(db: db, table: Table) {
|
||||
return db.execute(sql.raw(`TRUNCATE TABLE ${getTableName(table)} RESTART IDENTITY CASCADE`));
|
||||
}
|
||||
|
||||
for (const table of [
|
||||
schema.categories,
|
||||
schema.categoriesToExternalIds,
|
||||
schema.categories_to_games,
|
||||
schema.collection_items,
|
||||
schema.collections,
|
||||
schema.expansions,
|
||||
schema.externalIds,
|
||||
schema.games,
|
||||
schema.gamesToExternalIds,
|
||||
schema.mechanics,
|
||||
schema.mechanicsToExternalIds,
|
||||
schema.mechanics_to_games,
|
||||
schema.password_reset_tokens,
|
||||
schema.publishers,
|
||||
schema.publishersToExternalIds,
|
||||
schema.publishers_to_games,
|
||||
schema.recoveryCodes,
|
||||
schema.roles,
|
||||
schema.sessions,
|
||||
schema.userRoles,
|
||||
schema.users,
|
||||
schema.wishlists,
|
||||
schema.wishlist_items,
|
||||
]) {
|
||||
// await db.delete(table); // clear tables without truncating / resetting ids
|
||||
await resetTable(db, table);
|
||||
}
|
||||
|
||||
await seeds.roles(db);
|
||||
await seeds.users(db);
|
||||
|
||||
await pool.end();
|
||||
process.exit();
|
||||
14
src/db/seeds/data/roles.json
Normal file
14
src/db/seeds/data/roles.json
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
[
|
||||
{
|
||||
"name": "admin"
|
||||
},
|
||||
{
|
||||
"name": "user"
|
||||
},
|
||||
{
|
||||
"name": "editor"
|
||||
},
|
||||
{
|
||||
"name": "moderator"
|
||||
}
|
||||
]
|
||||
62
src/db/seeds/data/users.json
Normal file
62
src/db/seeds/data/users.json
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
[
|
||||
{
|
||||
"first_name": "John",
|
||||
"last_name": "Smith",
|
||||
"username": "john.smith",
|
||||
"email": "john.smith@example.com",
|
||||
"password": "password",
|
||||
"roles": [
|
||||
{
|
||||
"name": "user",
|
||||
"primary": true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"first_name": "Jane",
|
||||
"last_name": "Doe",
|
||||
"username": "jane.doe",
|
||||
"email": "jane.doe@example.com",
|
||||
"password": "password",
|
||||
"roles": [
|
||||
{
|
||||
"name": "user",
|
||||
"primary": true
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"first_name": "Michael",
|
||||
"last_name": "Editor",
|
||||
"username": "michael.editor",
|
||||
"email": "michael.editor@example.com",
|
||||
"password": "password",
|
||||
"roles": [
|
||||
{
|
||||
"name": "editor",
|
||||
"primary": true
|
||||
},
|
||||
{
|
||||
"name": "user",
|
||||
"primary": false
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"first_name": "Jane",
|
||||
"last_name": "Moderator",
|
||||
"username": "jane.moderator",
|
||||
"email": "jane.moderator@example.com",
|
||||
"password": "password",
|
||||
"roles": [
|
||||
{
|
||||
"name": "moderator",
|
||||
"primary": true
|
||||
},
|
||||
{
|
||||
"name": "user",
|
||||
"primary": false
|
||||
}
|
||||
]
|
||||
}
|
||||
]
|
||||
2
src/db/seeds/index.ts
Normal file
2
src/db/seeds/index.ts
Normal file
|
|
@ -0,0 +1,2 @@
|
|||
export { default as users } from './users';
|
||||
export { default as roles } from './roles';
|
||||
12
src/db/seeds/roles.ts
Normal file
12
src/db/seeds/roles.ts
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
import { eq } from 'drizzle-orm';
|
||||
import { type db } from '$db';
|
||||
import * as schema from '$db/schema';
|
||||
import roles from './data/roles.json';
|
||||
|
||||
export default async function seed(db: db) {
|
||||
console.log('Creating roles ...');
|
||||
for (const role of roles) {
|
||||
await db.insert(schema.roles).values(role).onConflictDoNothing();
|
||||
}
|
||||
console.log('Roles created.');
|
||||
}
|
||||
98
src/db/seeds/users.ts
Normal file
98
src/db/seeds/users.ts
Normal file
|
|
@ -0,0 +1,98 @@
|
|||
import { eq } from 'drizzle-orm';
|
||||
import { Argon2id } from 'oslo/password';
|
||||
import { type db } from '$db';
|
||||
import * as schema from '$db/schema';
|
||||
import users from './data/users.json';
|
||||
import env from '../../env';
|
||||
|
||||
type JsonUser = {
|
||||
id: string;
|
||||
username: string;
|
||||
email: string;
|
||||
password: string;
|
||||
roles: {
|
||||
name: string;
|
||||
primary: boolean;
|
||||
}[];
|
||||
};
|
||||
|
||||
type JsonRole = {
|
||||
name: string;
|
||||
primary: boolean;
|
||||
};
|
||||
|
||||
export default async function seed(db: db) {
|
||||
const adminRole = await db.select().from(schema.roles).where(eq(schema.roles.name, 'admin'));
|
||||
const userRole = await db.select().from(schema.roles).where(eq(schema.roles.name, 'user'));
|
||||
|
||||
console.log('Admin Role: ', adminRole);
|
||||
const adminUser = await db
|
||||
.insert(schema.users)
|
||||
.values({
|
||||
username: `${env.ADMIN_USERNAME}`,
|
||||
email: '',
|
||||
hashed_password: await new Argon2id().hash(`${env.ADMIN_PASSWORD}`),
|
||||
first_name: 'Brad',
|
||||
last_name: 'S',
|
||||
verified: true,
|
||||
})
|
||||
.returning()
|
||||
.onConflictDoNothing();
|
||||
|
||||
console.log('Admin user created.', adminUser);
|
||||
|
||||
await db
|
||||
.insert(schema.collections)
|
||||
.values({ user_id: adminUser[0].id })
|
||||
.onConflictDoNothing();
|
||||
|
||||
await db
|
||||
.insert(schema.wishlists)
|
||||
.values({ user_id: adminUser[0].id })
|
||||
.onConflictDoNothing();
|
||||
|
||||
await db
|
||||
.insert(schema.userRoles)
|
||||
.values({
|
||||
user_id: adminUser[0].id,
|
||||
role_id: adminRole[0].id,
|
||||
})
|
||||
.onConflictDoNothing();
|
||||
|
||||
console.log('Admin user given admin role.');
|
||||
|
||||
await db
|
||||
.insert(schema.userRoles)
|
||||
.values({
|
||||
user_id: adminUser[0].id,
|
||||
role_id: userRole[0].id,
|
||||
})
|
||||
.onConflictDoNothing();
|
||||
|
||||
console.log('Admin user given user role.');
|
||||
await Promise.all(
|
||||
users.map(async (user) => {
|
||||
const [insertedUser] = await db
|
||||
.insert(schema.users)
|
||||
.values({
|
||||
...user,
|
||||
hashed_password: await new Argon2id().hash(user.password),
|
||||
})
|
||||
.returning();
|
||||
await db.insert(schema.collections).values({ user_id: insertedUser?.id });
|
||||
await db.insert(schema.wishlists).values({ user_id: insertedUser?.id });
|
||||
await Promise.all(
|
||||
user.roles.map(async (role: JsonRole) => {
|
||||
const foundRole = await db.query.roles.findFirst({
|
||||
where: eq(schema.roles.name, role.name),
|
||||
});
|
||||
await db.insert(schema.userRoles).values({
|
||||
user_id: insertedUser?.id,
|
||||
role_id: foundRole?.id,
|
||||
primary: role?.primary,
|
||||
});
|
||||
}),
|
||||
);
|
||||
}),
|
||||
);
|
||||
}
|
||||
43
src/db/utils.ts
Normal file
43
src/db/utils.ts
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
// import { HTTPException } from 'hono/http-exception';
|
||||
import { timestamp } from 'drizzle-orm/pg-core';
|
||||
import { customType } from 'drizzle-orm/pg-core';
|
||||
|
||||
export const citext = customType<{ data: string }>({
|
||||
dataType() {
|
||||
return 'citext';
|
||||
},
|
||||
});
|
||||
|
||||
export const cuid2 = customType<{ data: string }>({
|
||||
dataType() {
|
||||
return 'text';
|
||||
},
|
||||
});
|
||||
|
||||
export const takeFirst = <T>(values: T[]): T | null => {
|
||||
if (values.length === 0) return null;
|
||||
return values[0]!;
|
||||
};
|
||||
|
||||
export const takeFirstOrThrow = <T>(values: T[]): T => {
|
||||
if (values.length === 0)
|
||||
// throw new HTTPException(404, {
|
||||
// message: 'Resource not found',
|
||||
// });
|
||||
return values[0]!;
|
||||
};
|
||||
|
||||
export const timestamps = {
|
||||
createdAt: timestamp('created_at', {
|
||||
mode: 'date',
|
||||
withTimezone: true,
|
||||
})
|
||||
.notNull()
|
||||
.defaultNow(),
|
||||
updatedAt: timestamp('updated_at', {
|
||||
mode: 'date',
|
||||
withTimezone: true,
|
||||
})
|
||||
.notNull()
|
||||
.defaultNow(),
|
||||
};
|
||||
52
src/env.ts
Normal file
52
src/env.ts
Normal file
|
|
@ -0,0 +1,52 @@
|
|||
import { config } from 'dotenv';
|
||||
import { expand } from 'dotenv-expand';
|
||||
import { ZodError, z } from 'zod';
|
||||
|
||||
const stringBoolean = z.coerce
|
||||
.string()
|
||||
.transform((val) => {
|
||||
return val === 'true';
|
||||
})
|
||||
.default('false');
|
||||
|
||||
const EnvSchema = z.object({
|
||||
NODE_ENV: z.string().default('development'),
|
||||
DATABASE_USER: z.string(),
|
||||
DATABASE_PASSWORD: z.string(),
|
||||
DATABASE_HOST: z.string(),
|
||||
DATABASE_PORT: z.coerce.number(),
|
||||
DATABASE_DB: z.string(),
|
||||
DATABASE_URL: z.string(),
|
||||
PUBLIC_SITE_NAME: z.string(),
|
||||
PUBLIC_SITE_URL: z.string(),
|
||||
PUBLIC_UMAMI_DO_NOT_TRACK: z.string(),
|
||||
PUBLIC_UMAMI_ID: z.string(),
|
||||
PUBLIC_UMAMI_URL: z.string(),
|
||||
DB_MIGRATING: stringBoolean,
|
||||
DB_SEEDING: stringBoolean,
|
||||
ADMIN_USERNAME: z.string(),
|
||||
ADMIN_PASSWORD: z.string(),
|
||||
TWO_FACTOR_TIMEOUT: z.coerce.number().default(300000),
|
||||
});
|
||||
|
||||
export type EnvSchema = z.infer<typeof EnvSchema>;
|
||||
|
||||
expand(config());
|
||||
|
||||
try {
|
||||
EnvSchema.parse(process.env);
|
||||
} catch (error) {
|
||||
if (error instanceof ZodError) {
|
||||
let message = 'Missing required values in .env:\n';
|
||||
error.issues.forEach((issue) => {
|
||||
message += issue.path[0] + '\n';
|
||||
});
|
||||
const e = new Error(message);
|
||||
e.stack = '';
|
||||
throw e;
|
||||
} else {
|
||||
console.error(error);
|
||||
}
|
||||
}
|
||||
|
||||
export default EnvSchema.parse(process.env);
|
||||
|
|
@ -32,11 +32,10 @@ export const authentication: Handle = async function ({ event, resolve }) {
|
|||
if (session && session.fresh) {
|
||||
const sessionCookie = lucia.createSessionCookie(session.id);
|
||||
console.log('sessionCookie', JSON.stringify(sessionCookie, null, 2));
|
||||
// sveltekit types deviates from the de-facto standard
|
||||
// you can use 'as any' too
|
||||
// sveltekit types deviates from the de-facto standard, you can use 'as any' too
|
||||
event.cookies.set(sessionCookie.name, sessionCookie.value, {
|
||||
path: '.',
|
||||
...sessionCookie.attributes
|
||||
...sessionCookie.attributes,
|
||||
});
|
||||
}
|
||||
console.log('session from hooks', JSON.stringify(session, null, 2));
|
||||
|
|
@ -45,7 +44,7 @@ export const authentication: Handle = async function ({ event, resolve }) {
|
|||
console.log('blank sessionCookie', JSON.stringify(sessionCookie, null, 2));
|
||||
event.cookies.set(sessionCookie.name, sessionCookie.value, {
|
||||
path: '.',
|
||||
...sessionCookie.attributes
|
||||
...sessionCookie.attributes,
|
||||
});
|
||||
}
|
||||
event.locals.user = user;
|
||||
|
|
@ -56,6 +55,6 @@ export const authentication: Handle = async function ({ event, resolve }) {
|
|||
|
||||
export const handle: Handle = sequence(
|
||||
// Sentry.sentryHandle(),
|
||||
authentication
|
||||
authentication,
|
||||
);
|
||||
// export const handleError = Sentry.handleErrorWithSentry();
|
||||
|
|
|
|||
|
|
@ -1,4 +1,6 @@
|
|||
<script lang="ts">
|
||||
const { children } = $props();
|
||||
|
||||
function portal(node: HTMLElement) {
|
||||
let target;
|
||||
|
||||
|
|
@ -25,5 +27,5 @@
|
|||
</script>
|
||||
|
||||
<div use:portal hidden>
|
||||
<slot />
|
||||
{@render children()}
|
||||
</div>
|
||||
|
|
|
|||
|
|
@ -2,7 +2,7 @@
|
|||
import { enhance } from "$app/forms";
|
||||
import { MinusCircle, PlusCircle } from "lucide-svelte";
|
||||
import { Button } from '$components/ui/button';
|
||||
import type { CollectionItems, Wishlists } from "../../schema";
|
||||
import type { CollectionItems, Wishlists } from "$db/schema";
|
||||
|
||||
export let game_id: string;
|
||||
export let collection: CollectionItems;
|
||||
|
|
|
|||
|
|
@ -1,112 +1,112 @@
|
|||
<script>
|
||||
/**
|
||||
* @event {boolean} check
|
||||
*/
|
||||
/**
|
||||
* @event {boolean} check
|
||||
*/
|
||||
|
||||
/**
|
||||
* Specify the value of the checkbox
|
||||
* @type {any}
|
||||
*/
|
||||
export let value = '';
|
||||
/**
|
||||
* Specify the value of the checkbox
|
||||
* @type {any}
|
||||
*/
|
||||
export let value = '';
|
||||
|
||||
/** Specify whether the checkbox is checked */
|
||||
export let checked = false;
|
||||
/** Specify whether the checkbox is checked */
|
||||
export let checked = false;
|
||||
|
||||
/**
|
||||
* Specify the bound group
|
||||
* @type {any[]}
|
||||
*/
|
||||
export let group = undefined;
|
||||
/**
|
||||
* Specify the bound group
|
||||
* @type {any[]}
|
||||
*/
|
||||
export let group = undefined;
|
||||
|
||||
/** Specify whether the checkbox is indeterminate */
|
||||
export let indeterminate = false;
|
||||
/** Specify whether the checkbox is indeterminate */
|
||||
export let indeterminate = false;
|
||||
|
||||
/** Set to `true` to display the skeleton state */
|
||||
export let skeleton = false;
|
||||
/** Set to `true` to display the skeleton state */
|
||||
export let skeleton = false;
|
||||
|
||||
/** Set to `true` to mark the field as required */
|
||||
export let required = false;
|
||||
/** Set to `true` to mark the field as required */
|
||||
export let required = false;
|
||||
|
||||
/** Set to `true` for the checkbox to be read-only */
|
||||
export let readonly = false;
|
||||
/** Set to `true` for the checkbox to be read-only */
|
||||
export let readonly = false;
|
||||
|
||||
/** Set to `true` to disable the checkbox */
|
||||
export let disabled = false;
|
||||
/** Set to `true` to disable the checkbox */
|
||||
export let disabled = false;
|
||||
|
||||
/** Specify the label text */
|
||||
export let labelText = '';
|
||||
/** Specify the label text */
|
||||
export let labelText = '';
|
||||
|
||||
/** Set to `true` to visually hide the label text */
|
||||
export let hideLabel = false;
|
||||
/** Set to `true` to visually hide the label text */
|
||||
export let hideLabel = false;
|
||||
|
||||
/** Set a name for the input element */
|
||||
export let name = '';
|
||||
/** Set a name for the input element */
|
||||
export let name = '';
|
||||
|
||||
/**
|
||||
* Specify the title attribute for the label element
|
||||
* @type {string}
|
||||
*/
|
||||
export let title = undefined;
|
||||
/**
|
||||
* Specify the title attribute for the label element
|
||||
* @type {string}
|
||||
*/
|
||||
export let title = undefined;
|
||||
|
||||
/** Set an id for the input label */
|
||||
export let id = 'ccs-' + Math.random().toString(36);
|
||||
/** Set an id for the input label */
|
||||
export let id = 'ccs-' + Math.random().toString(36);
|
||||
|
||||
/** Obtain a reference to the input HTML element */
|
||||
export let ref = null;
|
||||
/** Obtain a reference to the input HTML element */
|
||||
export let ref = null;
|
||||
|
||||
import { createEventDispatcher } from 'svelte';
|
||||
import CheckboxSkeleton from './CheckboxSkeleton.svelte';
|
||||
import { createEventDispatcher } from 'svelte';
|
||||
import CheckboxSkeleton from './CheckboxSkeleton.svelte';
|
||||
|
||||
const dispatch = createEventDispatcher();
|
||||
const dispatch = createEventDispatcher();
|
||||
|
||||
$: useGroup = Array.isArray(group);
|
||||
$: checked = useGroup ? group.includes(value) : checked;
|
||||
$: dispatch('check', checked);
|
||||
$: useGroup = Array.isArray(group);
|
||||
$: checked = useGroup ? group.includes(value) : checked;
|
||||
$: dispatch('check', checked);
|
||||
</script>
|
||||
|
||||
<!-- svelte-ignore a11y-mouse-events-have-key-events -->
|
||||
{#if skeleton}
|
||||
<CheckboxSkeleton {...$$restProps} on:click on:mouseover on:mouseenter on:mouseleave />
|
||||
<CheckboxSkeleton {...$$restProps} on:click on:mouseover on:mouseenter on:mouseleave />
|
||||
{:else}
|
||||
<div
|
||||
class:bx--form-item={true}
|
||||
class:bx--checkbox-wrapper={true}
|
||||
{...$$restProps}
|
||||
on:click
|
||||
on:mouseover
|
||||
on:mouseenter
|
||||
on:mouseleave
|
||||
>
|
||||
<input
|
||||
bind:this={ref}
|
||||
type="checkbox"
|
||||
{value}
|
||||
{checked}
|
||||
{disabled}
|
||||
{id}
|
||||
{indeterminate}
|
||||
{name}
|
||||
{required}
|
||||
{readonly}
|
||||
class:bx--checkbox={true}
|
||||
on:change={() => {
|
||||
if (useGroup) {
|
||||
group = group.includes(value)
|
||||
? group.filter((_value) => _value !== value)
|
||||
: [...group, value];
|
||||
} else {
|
||||
checked = !checked;
|
||||
}
|
||||
}}
|
||||
on:change
|
||||
on:blur
|
||||
/>
|
||||
<label for={id} {title} class:bx--checkbox-label={true}>
|
||||
<span class:bx--checkbox-label-text={true} class:bx--visually-hidden={hideLabel}>
|
||||
<slot name="labelText">
|
||||
{labelText}
|
||||
</slot>
|
||||
</span>
|
||||
</label>
|
||||
</div>
|
||||
<div
|
||||
class:bx--form-item={true}
|
||||
class:bx--checkbox-wrapper={true}
|
||||
{...$$restProps}
|
||||
on:click
|
||||
on:mouseover
|
||||
on:mouseenter
|
||||
on:mouseleave
|
||||
>
|
||||
<input
|
||||
bind:this={ref}
|
||||
type="checkbox"
|
||||
{value}
|
||||
{checked}
|
||||
{disabled}
|
||||
{id}
|
||||
{indeterminate}
|
||||
{name}
|
||||
{required}
|
||||
{readonly}
|
||||
class:bx--checkbox={true}
|
||||
on:change={() => {
|
||||
if (useGroup) {
|
||||
group = group.includes(value)
|
||||
? group.filter((_value) => _value !== value)
|
||||
: [...group, value];
|
||||
} else {
|
||||
checked = !checked;
|
||||
}
|
||||
}}
|
||||
on:change
|
||||
on:blur
|
||||
/>
|
||||
<label for={id} {title} class:bx--checkbox-label={true}>
|
||||
<span class:bx--checkbox-label-text={true} class:bx--visually-hidden={hideLabel}>
|
||||
<slot name="labelText">
|
||||
{labelText}
|
||||
</slot>
|
||||
</span>
|
||||
</label>
|
||||
</div>
|
||||
{/if}
|
||||
|
|
|
|||
|
|
@ -1,10 +1,9 @@
|
|||
<script lang="ts">
|
||||
import type { GameType, SavedGameType } from '$lib/types';
|
||||
import * as Card from "$lib/components/ui/card";
|
||||
import type { CollectionItems } from '../../schema';
|
||||
import type { CollectionItems } from '$db/schema';
|
||||
|
||||
export let game: GameType | CollectionItems;
|
||||
export let detailed: boolean = false;
|
||||
export let variant: 'default' | 'compact' = 'default';
|
||||
|
||||
// Naive and assumes description is only on our GameType at the moment
|
||||
|
|
|
|||
|
|
@ -2,21 +2,19 @@
|
|||
import { applyAction, enhance } from '$app/forms';
|
||||
import toast from 'svelte-french-toast';
|
||||
import { ListChecks, ListTodo, LogOut, User } from 'lucide-svelte';
|
||||
import * as DropdownMenu from "$components/ui/dropdown-menu";
|
||||
import * as Avatar from "$components/ui/avatar";
|
||||
import * as DropdownMenu from '$components/ui/dropdown-menu';
|
||||
import * as Avatar from '$components/ui/avatar';
|
||||
import { invalidateAll } from '$app/navigation';
|
||||
import Logo from '$components/logo.svelte';
|
||||
import type { Users } from "../../schema";
|
||||
import type { Users } from '$db/schema';
|
||||
|
||||
export let user: Users | null = null;
|
||||
type HeaderProps = {
|
||||
user: Users | null;
|
||||
};
|
||||
|
||||
console.log('header user', user);
|
||||
let { user = null }: HeaderProps = $props();
|
||||
|
||||
let avatar: string;
|
||||
|
||||
$: if (user) {
|
||||
avatar = user.username?.slice(0, 1).toUpperCase() || ':)';
|
||||
}
|
||||
let avatar: string = $derived(user?.username?.slice(0, 1).toUpperCase() || ':)');
|
||||
</script>
|
||||
|
||||
<header>
|
||||
|
|
@ -28,7 +26,6 @@
|
|||
<span class="logo-text">Bored Game</span>
|
||||
</a>
|
||||
</div>
|
||||
<!-- <TextSearch /> -->
|
||||
<nav>
|
||||
{#if user}
|
||||
<DropdownMenu.Root>
|
||||
|
|
@ -41,7 +38,7 @@
|
|||
</DropdownMenu.Trigger>
|
||||
<DropdownMenu.Content>
|
||||
<DropdownMenu.Group>
|
||||
<DropdownMenu.Label>My Account</DropdownMenu.Label>
|
||||
<DropdownMenu.Label>Account</DropdownMenu.Label>
|
||||
<DropdownMenu.Separator />
|
||||
<a href="/profile">
|
||||
<DropdownMenu.Item>
|
||||
|
|
@ -49,57 +46,53 @@
|
|||
<span>Profile</span>
|
||||
</DropdownMenu.Item>
|
||||
</a>
|
||||
<a href="/collection">
|
||||
<a href="/collections">
|
||||
<DropdownMenu.Item>
|
||||
<ListChecks class="mr-2 h-4 w-4" />
|
||||
<span>Collection</span>
|
||||
<span>Collections</span>
|
||||
</DropdownMenu.Item>
|
||||
</a>
|
||||
<a href="/wishlist">
|
||||
<a href="/wishlists">
|
||||
<DropdownMenu.Item>
|
||||
<ListTodo class="mr-2 h-4 w-4" />
|
||||
<span>Wishlist</span>
|
||||
<span>Wishlists</span>
|
||||
</DropdownMenu.Item>
|
||||
</a>
|
||||
<form
|
||||
use:enhance={() => {
|
||||
return async ({ result }) => {
|
||||
console.log(result);
|
||||
if (result.type === 'success' || result.type === 'redirect') {
|
||||
toast.success('Logged Out');
|
||||
} else if (result.type === 'error') {
|
||||
<DropdownMenu.Item>
|
||||
<form
|
||||
use:enhance={() => {
|
||||
return async ({ result }) => {
|
||||
console.log(result);
|
||||
toast.error(`Error: ${result.error.message}`);
|
||||
} else {
|
||||
toast.error(`Something went wrong.`);
|
||||
console.log(result);
|
||||
}
|
||||
await invalidateAll();
|
||||
await applyAction(result);
|
||||
};
|
||||
}}
|
||||
action="/logout"
|
||||
method="POST"
|
||||
>
|
||||
<button type="submit" class="">
|
||||
<DropdownMenu.Item>
|
||||
<div class="flex items-center gap-1">
|
||||
<LogOut class="mr-2 h-4 w-4"/>
|
||||
<span>Sign out</span>
|
||||
</div>
|
||||
</DropdownMenu.Item>
|
||||
</button>
|
||||
</form>
|
||||
if (result.type === 'success' || result.type === 'redirect') {
|
||||
toast.success('Logged Out');
|
||||
} else if (result.type === 'error') {
|
||||
console.log(result);
|
||||
toast.error(`Error: ${result.error.message}`);
|
||||
} else {
|
||||
toast.error(`Something went wrong.`);
|
||||
console.log(result);
|
||||
}
|
||||
await invalidateAll();
|
||||
await applyAction(result);
|
||||
};
|
||||
}}
|
||||
action="/logout"
|
||||
method="POST"
|
||||
>
|
||||
<button type="submit">
|
||||
<div class="flex items-center gap-1">
|
||||
<LogOut class="mr-2 h-4 w-4" />
|
||||
<span>Sign out</span>
|
||||
</div>
|
||||
</button>
|
||||
</form>
|
||||
</DropdownMenu.Item>
|
||||
</DropdownMenu.Group>
|
||||
</DropdownMenu.Content>
|
||||
</DropdownMenu.Root>
|
||||
{:else}
|
||||
<a href="/login">
|
||||
<span class="flex-auto">Login</span></a
|
||||
>
|
||||
<a href="/sign-up">
|
||||
<span class="flex-auto">Sign Up</span></a
|
||||
>
|
||||
<a href="/login"> <span class="flex-auto">Login</span></a>
|
||||
<a href="/sign-up"> <span class="flex-auto">Sign Up</span></a>
|
||||
{/if}
|
||||
</nav>
|
||||
</header>
|
||||
|
|
|
|||
|
|
@ -1,7 +1,5 @@
|
|||
<script lang="ts">
|
||||
export let url: string;
|
||||
export let ariaLabel = `Link to ${url}`;
|
||||
export let external = false;
|
||||
const { url, ariaLabel = `Link to ${url}`, external = false, children }: { url: string; ariaLabel?: string; external?: boolean; children: any } = $props();
|
||||
</script>
|
||||
|
||||
<a
|
||||
|
|
@ -10,7 +8,7 @@
|
|||
rel="noreferrer"
|
||||
aria-label={`Board Game Atlas Link for ${ariaLabel}`}
|
||||
>
|
||||
<slot />
|
||||
{@render children()}
|
||||
</a>
|
||||
|
||||
<style>
|
||||
|
|
|
|||
15
src/lib/components/container.svelte
Normal file
15
src/lib/components/container.svelte
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from 'svelte/elements';
|
||||
import { cn } from '$lib/utils/ui';
|
||||
import type { Snippet } from 'svelte';
|
||||
|
||||
interface Props extends HTMLAttributes<HTMLDivElement> {
|
||||
children: Snippet;
|
||||
}
|
||||
|
||||
let { class: classNames, children, ...restProps }: Props = $props();
|
||||
</script>
|
||||
|
||||
<div {...restProps} class={cn('mx-auto w-full max-w-6xl px-0 md:px-6', classNames)}>
|
||||
{@render children()}
|
||||
</div>
|
||||
|
|
@ -1,11 +1,5 @@
|
|||
<script lang="ts">
|
||||
import { fade } from 'svelte/transition';
|
||||
// import {
|
||||
// Dialog,
|
||||
// DialogDescription,
|
||||
// DialogOverlay,
|
||||
// DialogTitle
|
||||
// } from '@rgossiaux/svelte-headlessui';
|
||||
import { boredState } from '$lib/stores/boredState';
|
||||
import { collectionStore } from '$lib/stores/collectionStore';
|
||||
import { browser } from '$app/environment';
|
||||
|
|
|
|||
32
src/lib/components/pin-input.svelte
Normal file
32
src/lib/components/pin-input.svelte
Normal file
|
|
@ -0,0 +1,32 @@
|
|||
<script lang="ts">
|
||||
import { cn } from '$lib/utils/ui';
|
||||
import { PinInput, type PinInputProps } from 'bits-ui';
|
||||
|
||||
interface Props extends Omit<PinInputProps, 'value'> {
|
||||
value: string;
|
||||
inputCount?: number;
|
||||
}
|
||||
|
||||
let { value = $bindable(), inputCount = 6, ...rest }: Props = $props();
|
||||
let pin = $state<string[] | undefined>(value?.split('') ?? []);
|
||||
let inputs = $derived(Array(inputCount).fill(null));
|
||||
|
||||
$effect(() => {
|
||||
value = pin?.join('') ?? '';
|
||||
});
|
||||
</script>
|
||||
|
||||
<PinInput.Root
|
||||
{...rest}
|
||||
bind:value={pin}
|
||||
class={cn('flex items-center gap-2', rest.class)}
|
||||
type="text"
|
||||
placeholder=""
|
||||
>
|
||||
{#each inputs as _}
|
||||
<PinInput.Input
|
||||
class="flex h-14 w-10 rounded-md border border-input bg-background px-3 py-2 text-center text-sm ring-offset-background file:border-0 file:bg-transparent file:text-sm file:font-medium placeholder:text-muted-foreground focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50"
|
||||
/>
|
||||
{/each}
|
||||
<PinInput.HiddenInput />
|
||||
</PinInput.Root>
|
||||
|
|
@ -1,8 +1,8 @@
|
|||
<script lang="ts">
|
||||
import { superForm, type Infer, type SuperValidated } from 'sveltekit-superforms';
|
||||
import { search_schema, type SearchSchema } from '$lib/zodValidation';
|
||||
import * as Form from "$lib/components/ui/form";
|
||||
import { zodClient } from 'sveltekit-superforms/adapters';
|
||||
import { search_schema, type SearchSchema } from '$lib/zodValidation';
|
||||
import * as Form from "$lib/components/ui/form";
|
||||
import Input from '$components/ui/input/input.svelte';
|
||||
import Checkbox from '$components/ui/checkbox/checkbox.svelte';
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import { Avatar as AvatarPrimitive } from "bits-ui";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = AvatarPrimitive.FallbackProps;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import { Avatar as AvatarPrimitive } from "bits-ui";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = AvatarPrimitive.ImageProps;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import { Avatar as AvatarPrimitive } from "bits-ui";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = AvatarPrimitive.Props;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
<script lang="ts">
|
||||
import { Button as ButtonPrimitive } from "bits-ui";
|
||||
import { type Events, type Props, buttonVariants } from "./index.js";
|
||||
import { cn } from "$lib/utils.js";
|
||||
import { buttonVariants, type Props, type Events } from "./index.js";
|
||||
|
||||
type $$Props = Props;
|
||||
type $$Events = Events;
|
||||
|
|
|
|||
|
|
@ -1,9 +1,9 @@
|
|||
import Root from "./button.svelte";
|
||||
import { tv, type VariantProps } from "tailwind-variants";
|
||||
import { type VariantProps, tv } from "tailwind-variants";
|
||||
import type { Button as ButtonPrimitive } from "bits-ui";
|
||||
import Root from "./button.svelte";
|
||||
|
||||
const buttonVariants = tv({
|
||||
base: "inline-flex items-center justify-center rounded-md text-sm font-medium whitespace-nowrap ring-offset-background transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50",
|
||||
base: "inline-flex items-center justify-center whitespace-nowrap rounded-md text-sm font-medium ring-offset-background transition-colors focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:pointer-events-none disabled:opacity-50",
|
||||
variants: {
|
||||
variant: {
|
||||
default: "bg-primary text-primary-foreground hover:bg-primary/90",
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import { cn } from "$lib/utils";
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLParagraphElement>;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils";
|
||||
import type { HeadingLevel } from ".";
|
||||
import type { HeadingLevel } from "./index.js";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLHeadingElement> & {
|
||||
tag?: HeadingLevel;
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,8 @@
|
|||
<script lang="ts">
|
||||
import { Checkbox as CheckboxPrimitive } from "bits-ui";
|
||||
import { Check, Minus } from "lucide-svelte";
|
||||
import { cn } from "$lib/utils";
|
||||
import Check from "lucide-svelte/icons/check";
|
||||
import Minus from "lucide-svelte/icons/minus";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = CheckboxPrimitive.Props;
|
||||
type $$Events = CheckboxPrimitive.Events;
|
||||
|
|
@ -13,7 +14,7 @@
|
|||
|
||||
<CheckboxPrimitive.Root
|
||||
class={cn(
|
||||
"box-content peer h-4 w-4 shrink-0 rounded-sm border border-primary ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 data-[state=checked]:bg-primary data-[state=checked]:text-primary-foreground data-[disabled=true]:cursor-not-allowed data-[disabled=true]:opacity-50",
|
||||
"peer box-content h-4 w-4 shrink-0 rounded-sm border border-primary ring-offset-background focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-ring focus-visible:ring-offset-2 disabled:cursor-not-allowed disabled:opacity-50 data-[disabled=true]:cursor-not-allowed data-[state=checked]:bg-primary data-[state=checked]:text-primary-foreground data-[disabled=true]:opacity-50",
|
||||
className
|
||||
)}
|
||||
bind:checked
|
||||
|
|
@ -21,7 +22,7 @@
|
|||
on:click
|
||||
>
|
||||
<CheckboxPrimitive.Indicator
|
||||
class={cn("flex items-center justify-center text-current h-4 w-4")}
|
||||
class={cn("flex h-4 w-4 items-center justify-center text-current")}
|
||||
let:isChecked
|
||||
let:isIndeterminate
|
||||
>
|
||||
|
|
|
|||
|
|
@ -2,5 +2,5 @@ import Root from "./checkbox.svelte";
|
|||
export {
|
||||
Root,
|
||||
//
|
||||
Root as Checkbox
|
||||
Root as Checkbox,
|
||||
};
|
||||
|
|
|
|||
36
src/lib/components/ui/dialog/dialog-content.svelte
Normal file
36
src/lib/components/ui/dialog/dialog-content.svelte
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
<script lang="ts">
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
import X from "lucide-svelte/icons/x";
|
||||
import * as Dialog from "./index.js";
|
||||
import { cn, flyAndScale } from "$lib/utils.js";
|
||||
|
||||
type $$Props = DialogPrimitive.ContentProps;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export let transition: $$Props["transition"] = flyAndScale;
|
||||
export let transitionConfig: $$Props["transitionConfig"] = {
|
||||
duration: 200,
|
||||
};
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<Dialog.Portal>
|
||||
<Dialog.Overlay />
|
||||
<DialogPrimitive.Content
|
||||
{transition}
|
||||
{transitionConfig}
|
||||
class={cn(
|
||||
"fixed left-[50%] top-[50%] z-50 grid w-full max-w-lg translate-x-[-50%] translate-y-[-50%] gap-4 border bg-background p-6 shadow-lg sm:rounded-lg md:w-full",
|
||||
className
|
||||
)}
|
||||
{...$$restProps}
|
||||
>
|
||||
<slot />
|
||||
<DialogPrimitive.Close
|
||||
class="absolute right-4 top-4 rounded-sm opacity-70 ring-offset-background transition-opacity hover:opacity-100 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none data-[state=open]:bg-accent data-[state=open]:text-muted-foreground"
|
||||
>
|
||||
<X class="h-4 w-4" />
|
||||
<span class="sr-only">Close</span>
|
||||
</DialogPrimitive.Close>
|
||||
</DialogPrimitive.Content>
|
||||
</Dialog.Portal>
|
||||
16
src/lib/components/ui/dialog/dialog-description.svelte
Normal file
16
src/lib/components/ui/dialog/dialog-description.svelte
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
<script lang="ts">
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = DialogPrimitive.DescriptionProps;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<DialogPrimitive.Description
|
||||
class={cn("text-sm text-muted-foreground", className)}
|
||||
{...$$restProps}
|
||||
>
|
||||
<slot />
|
||||
</DialogPrimitive.Description>
|
||||
16
src/lib/components/ui/dialog/dialog-footer.svelte
Normal file
16
src/lib/components/ui/dialog/dialog-footer.svelte
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<div
|
||||
class={cn("flex flex-col-reverse sm:flex-row sm:justify-end sm:space-x-2", className)}
|
||||
{...$$restProps}
|
||||
>
|
||||
<slot />
|
||||
</div>
|
||||
13
src/lib/components/ui/dialog/dialog-header.svelte
Normal file
13
src/lib/components/ui/dialog/dialog-header.svelte
Normal file
|
|
@ -0,0 +1,13 @@
|
|||
<script lang="ts">
|
||||
import type { HTMLAttributes } from "svelte/elements";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = HTMLAttributes<HTMLDivElement>;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<div class={cn("flex flex-col space-y-1.5 text-center sm:text-left", className)} {...$$restProps}>
|
||||
<slot />
|
||||
</div>
|
||||
21
src/lib/components/ui/dialog/dialog-overlay.svelte
Normal file
21
src/lib/components/ui/dialog/dialog-overlay.svelte
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
<script lang="ts">
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
import { fade } from "svelte/transition";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = DialogPrimitive.OverlayProps;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export let transition: $$Props["transition"] = fade;
|
||||
export let transitionConfig: $$Props["transitionConfig"] = {
|
||||
duration: 150,
|
||||
};
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<DialogPrimitive.Overlay
|
||||
{transition}
|
||||
{transitionConfig}
|
||||
class={cn("fixed inset-0 z-50 bg-background/80 backdrop-blur-sm", className)}
|
||||
{...$$restProps}
|
||||
/>
|
||||
8
src/lib/components/ui/dialog/dialog-portal.svelte
Normal file
8
src/lib/components/ui/dialog/dialog-portal.svelte
Normal file
|
|
@ -0,0 +1,8 @@
|
|||
<script lang="ts">
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
type $$Props = DialogPrimitive.PortalProps;
|
||||
</script>
|
||||
|
||||
<DialogPrimitive.Portal {...$$restProps}>
|
||||
<slot />
|
||||
</DialogPrimitive.Portal>
|
||||
16
src/lib/components/ui/dialog/dialog-title.svelte
Normal file
16
src/lib/components/ui/dialog/dialog-title.svelte
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
<script lang="ts">
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = DialogPrimitive.TitleProps;
|
||||
|
||||
let className: $$Props["class"] = undefined;
|
||||
export { className as class };
|
||||
</script>
|
||||
|
||||
<DialogPrimitive.Title
|
||||
class={cn("text-lg font-semibold leading-none tracking-tight", className)}
|
||||
{...$$restProps}
|
||||
>
|
||||
<slot />
|
||||
</DialogPrimitive.Title>
|
||||
|
|
@ -1,12 +1,37 @@
|
|||
import { Dialog as DialogPrimitive } from "radix-svelte";
|
||||
import { Dialog as DialogPrimitive } from "bits-ui";
|
||||
|
||||
export const Dialog = DialogPrimitive.Root;
|
||||
export const DialogTrigger = DialogPrimitive.Trigger;
|
||||
import Title from "./dialog-title.svelte";
|
||||
import Portal from "./dialog-portal.svelte";
|
||||
import Footer from "./dialog-footer.svelte";
|
||||
import Header from "./dialog-header.svelte";
|
||||
import Overlay from "./dialog-overlay.svelte";
|
||||
import Content from "./dialog-content.svelte";
|
||||
import Description from "./dialog-description.svelte";
|
||||
|
||||
export { default as DialogContent } from "./DialogContent.svelte";
|
||||
export { default as DialogDescription } from "./DialogDescription.svelte";
|
||||
export { default as DialogFooter } from "./DialogFooter.svelte";
|
||||
export { default as DialogHeader } from "./DialogHeader.svelte";
|
||||
export { default as DialogOverlay } from "./DialogOverlay.svelte";
|
||||
export { default as DialogPortal } from "./DialogPortal.svelte";
|
||||
export { default as DialogTitle } from "./DialogTitle.svelte";
|
||||
const Root = DialogPrimitive.Root;
|
||||
const Trigger = DialogPrimitive.Trigger;
|
||||
const Close = DialogPrimitive.Close;
|
||||
|
||||
export {
|
||||
Root,
|
||||
Title,
|
||||
Portal,
|
||||
Footer,
|
||||
Header,
|
||||
Trigger,
|
||||
Overlay,
|
||||
Content,
|
||||
Description,
|
||||
Close,
|
||||
//
|
||||
Root as Dialog,
|
||||
Title as DialogTitle,
|
||||
Portal as DialogPortal,
|
||||
Footer as DialogFooter,
|
||||
Header as DialogHeader,
|
||||
Trigger as DialogTrigger,
|
||||
Overlay as DialogOverlay,
|
||||
Content as DialogContent,
|
||||
Description as DialogDescription,
|
||||
Close as DialogClose,
|
||||
};
|
||||
|
|
|
|||
|
|
@ -1,7 +1,7 @@
|
|||
<script lang="ts">
|
||||
import { DropdownMenu as DropdownMenuPrimitive } from "bits-ui";
|
||||
import Check from "lucide-svelte/icons/check";
|
||||
import { cn } from "$lib/utils";
|
||||
import { cn } from "$lib/utils.js";
|
||||
|
||||
type $$Props = DropdownMenuPrimitive.CheckboxItemProps;
|
||||
type $$Events = DropdownMenuPrimitive.CheckboxItemEvents;
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue