From d20b00532d0b68783915fd85cf20e8bfce0a4f21 Mon Sep 17 00:00:00 2001 From: Jorge Vargas Date: Tue, 3 Sep 2024 19:11:19 -0600 Subject: [PATCH] Add sequelize index file --- auth.config.ts | 11 +++++++++-- src/app.d.ts | 1 - src/graphql/apolloClient.mts | 11 ++++------- src/graphql/resolvers/mutations/user.js | 4 ++-- src/graphql/resolvers/queries/search.ts | 2 ++ src/graphql/resolvers/types/album.ts | 3 ++- src/graphql/resolvers/types/user.js | 26 +++++++++++++++---------- src/sequelize/index.ts | 10 ++++++++++ src/sequelize/models/config.ts | 5 +---- src/sequelize/models/user.js | 23 ---------------------- src/sequelize/models/user.ts | 20 +++++++++++++++++++ src/utils/resolvers.ts | 11 +++++++++++ 12 files changed, 77 insertions(+), 50 deletions(-) create mode 100644 src/sequelize/index.ts delete mode 100644 src/sequelize/models/user.js create mode 100644 src/sequelize/models/user.ts create mode 100644 src/utils/resolvers.ts diff --git a/auth.config.ts b/auth.config.ts index 9de03f6..470346e 100644 --- a/auth.config.ts +++ b/auth.config.ts @@ -3,7 +3,14 @@ import { defineConfig } from 'auth-astro' import Credentials from "@auth/core/providers/credentials" import bcrypt from 'bcrypt' -import db from '@/sequelize' +import User from '@/sequelize/models/user' + +declare module "@auth/core" { + interface Session { + id: string + username: string + } +} class InvalidLoginError extends CredentialsSignin { code = "Invalid username/email or password" @@ -19,7 +26,7 @@ export default defineConfig({ async authorize(credentials) { if (!credentials?.username || !credentials.password) throw new InvalidLoginError() - const user = await db.models.user.findByPk(credentials.username) + const user = await User.findByPk(credentials.username) if (!user) throw new InvalidLoginError() // @ts-ignore diff --git a/src/app.d.ts b/src/app.d.ts index cd7e042..462eac2 100644 --- a/src/app.d.ts +++ b/src/app.d.ts @@ -1,7 +1,6 @@ import type { ParaglideLocals } from "@inlang/paraglide-sveltekit" import type { AvailableLanguageTag } from "$lib/paraglide/runtime" - declare global { namespace App { interface Locals { diff --git a/src/graphql/apolloClient.mts b/src/graphql/apolloClient.mts index d17688f..1319705 100644 --- a/src/graphql/apolloClient.mts +++ b/src/graphql/apolloClient.mts @@ -4,24 +4,21 @@ import { SchemaLink } from "@apollo/client/link/schema" import { makeExecutableSchema } from "@graphql-tools/schema"; import { getSession } from 'auth-astro/server'; import type { Session } from '@auth/core/types'; + import { typeDefs } from "./__generated__/typeDefs.generated"; import resolvers from '@/graphql/resolvers' -import type { MySqlDialect } from '@sequelize/mysql'; -import { Sequelize, type ModelStatic, type Options } from '@sequelize/core' + +import db from '@/sequelize'; const schema = makeExecutableSchema({ typeDefs, resolvers }) export type ResolverContext = { request?: Request, session?: Session } -const envOptions: Options = JSON.parse(import.meta.env.SEQUELIZE) || {} - export async function getApolloClient(request?: Request) { const session = request ? await getSession(request) : null - const db = new Sequelize(envOptions) - envOptions.models = Object.values(await import.meta.glob('@/sequelize/models/**/*.ts', { eager: true, import: 'default' })) return new ApolloClient({ ssrMode: true, - link: new SchemaLink({ schema, context: { request, session } }), + link: new SchemaLink({ schema, context: { request, session, db } }), cache: new InMemoryCache() }) } \ No newline at end of file diff --git a/src/graphql/resolvers/mutations/user.js b/src/graphql/resolvers/mutations/user.js index 6e0835e..53194ab 100644 --- a/src/graphql/resolvers/mutations/user.js +++ b/src/graphql/resolvers/mutations/user.js @@ -1,5 +1,5 @@ import { composeResolvers } from '@graphql-tools/resolvers-composition' -import type { Resolvers } from '@/graphql/__generated__/types.generated' +// import type { Resolvers } from '@/graphql/__generated__/types.generated' const resolversComposition = { //'Mutation.updateUser': [isAuthedApp] @@ -49,7 +49,7 @@ async function cropPFP(streamItem, username, imgId) { return await processImage(fullPath) }*/ -const resolvers: Resolvers = { +const resolvers = { Mutation: { /*registerUser: async (_, { username, email, pfp }, { db }) => { await Promise.all([ diff --git a/src/graphql/resolvers/queries/search.ts b/src/graphql/resolvers/queries/search.ts index e892c30..1d62661 100644 --- a/src/graphql/resolvers/queries/search.ts +++ b/src/graphql/resolvers/queries/search.ts @@ -8,6 +8,7 @@ const fuzzySearch = (words: string[]) => `^${words.map(w => `(?=.*\b${w}\b)`)}.+ const resolvers: Resolvers = { Query: { + // @ts-ignore searchAlbum: async (_, args, { db }) => { const { title, categories, limit = 10, offset = 0, order = ['createdAt'], mode = 'DESC', status = ['show'] } = args const fuzzyCondition = title ? { @@ -27,6 +28,7 @@ const resolvers: Resolvers = { status: { [Op.in]: status } }, include, + // @ts-ignore order: [literal('`album`.`status` = \'coming\' DESC'), ...order.map(o => [o, mode])] }) diff --git a/src/graphql/resolvers/types/album.ts b/src/graphql/resolvers/types/album.ts index c5e9b0b..a736b7c 100644 --- a/src/graphql/resolvers/types/album.ts +++ b/src/graphql/resolvers/types/album.ts @@ -5,7 +5,8 @@ import type Album from "@/sequelize/models/album" const resolvers: Resolvers = { // Upload: GraphQLUpload, Album: { - artists: (parent: Album, args, context, info) => parent.getArtists(), + // @ts-ignore + artists: (parent, args, context, info) => parent.getArtists(), /* categories: (parent, args, context, info) => parent.getCategories(), classifications: (parent, args, context, info) => parent.getClassifications(), diff --git a/src/graphql/resolvers/types/user.js b/src/graphql/resolvers/types/user.js index c5ba52d..e47895d 100644 --- a/src/graphql/resolvers/types/user.js +++ b/src/graphql/resolvers/types/user.js @@ -1,6 +1,6 @@ -import type { Resolvers } from '@/graphql/__generated__/types.generated' +// import type { Resolvers } from '@/graphql/__generated__/types.generated' -const userResolvable: Resolvers = { +const userResolvable = { /* roles: parent => parent.getRoles(), permissions: async parent => { const roles = await parent.getRoles() @@ -8,26 +8,32 @@ const userResolvable: Resolvers = { }, */ pages: async (_, __, { session }) => { const roles = await parent.getRoles() - const permissions = roles.map(r => r.permissions).flat() + const permissions = roles.map((r) => r.permissions).flat() - return pages.filter(({ perms }) => perms.length === 0 || perms.some(r => permissions.includes(r))) - }, + return pages.filter( + ({ perms }) => + perms.length === 0 || perms.some((r) => permissions.includes(r)) + ) + } /* comments: (user, _, { db }) => user.getComments({ where: { albumId: { [Op.not]: null } } }), favorites: user => user.getAlbums(), imgUrl: async user => `https://cdn.sittingonclouds.net/user/${user.imgId ? `${user.username}_${user.imgId}` : 'default' }.png` */ } -const resolvers: Resolvers = { +const resolvers = { // User: userResolvable, UserMe: { pages: async (_, __, { session }) => { const roles = await parent.getRoles() - const permissions = roles.map(r => r.permissions).flat() + const permissions = roles.map((r) => r.permissions).flat() - return pages.filter(({ perms }) => perms.length === 0 || perms.some(r => permissions.includes(r))) - }, - }, + return pages.filter( + ({ perms }) => + perms.length === 0 || perms.some((r) => permissions.includes(r)) + ) + } + } /*Role: { permissions: parent => typeof parent.permissions === 'string' || parent.permissions instanceof String ? JSON.parse(parent.permissions) : parent.permissions }, Submission: { submitter: submission => submission.getUser(), diff --git a/src/sequelize/index.ts b/src/sequelize/index.ts new file mode 100644 index 0000000..00c0daf --- /dev/null +++ b/src/sequelize/index.ts @@ -0,0 +1,10 @@ +import type { MySqlDialect } from '@sequelize/mysql'; +import { Sequelize, type ModelStatic, type Options } from '@sequelize/core' + +const envOptions: Options = JSON.parse(import.meta.env.SEQUELIZE) || {} +const db = new Sequelize({ + ...envOptions, + models: Object.values(await import.meta.glob('@/sequelize/models/**/*.ts', { eager: true, import: 'default' })) +}) + +export default db \ No newline at end of file diff --git a/src/sequelize/models/config.ts b/src/sequelize/models/config.ts index 61c80b3..2d70f00 100644 --- a/src/sequelize/models/config.ts +++ b/src/sequelize/models/config.ts @@ -1,10 +1,7 @@ import { DataTypes, Model, type CreationOptional, type InferAttributes, type InferCreationAttributes } from '@sequelize/core'; import { Attribute, PrimaryKey, AutoIncrement, Default, Table } from '@sequelize/core/decorators-legacy'; -@Table({ - freezeTableName: true, -}) - +@Table({ tableName: 'config' }) export default class Config extends Model, InferCreationAttributes> { @Attribute(DataTypes.ENUM('banner', 'banner-position')) @PrimaryKey diff --git a/src/sequelize/models/user.js b/src/sequelize/models/user.js deleted file mode 100644 index b329cbf..0000000 --- a/src/sequelize/models/user.js +++ /dev/null @@ -1,23 +0,0 @@ -import { DataTypes } from '@/sequelize' - -const model = (sequelize) => { - const User = sequelize.define('user', { - username: { - type: DataTypes.STRING, - primaryKey: true - }, - email: DataTypes.STRING, - password: DataTypes.STRING, - placeholder: { type: DataTypes.TEXT }, - imgId: DataTypes.STRING - }) - - sequelize.define('forgor', { - key: { type: DataTypes.STRING, primaryKey: true }, - expires: DataTypes.DATE - }) - - return User -} - -export default model diff --git a/src/sequelize/models/user.ts b/src/sequelize/models/user.ts new file mode 100644 index 0000000..9c20e97 --- /dev/null +++ b/src/sequelize/models/user.ts @@ -0,0 +1,20 @@ +import { DataTypes, Model, type InferAttributes, type InferCreationAttributes } from '@sequelize/core' +import { Attribute, NotNull, PrimaryKey } from '@sequelize/core/decorators-legacy' + +export default class User extends Model, InferCreationAttributes> { + @PrimaryKey + @Attribute(DataTypes.STRING) + declare username: string + + @Attribute(DataTypes.STRING) + @NotNull + declare email: string + + @Attribute(DataTypes.STRING) + @NotNull + declare password: string + + @Attribute(DataTypes.STRING) + @NotNull + declare imgId: string +} \ No newline at end of file diff --git a/src/utils/resolvers.ts b/src/utils/resolvers.ts new file mode 100644 index 0000000..b5142c4 --- /dev/null +++ b/src/utils/resolvers.ts @@ -0,0 +1,11 @@ + +import User from "@/sequelize/models/user"; +import type { Session } from "@auth/core"; + +export async function getUser(session: Session | null) { + if (!session) return null + + const { id } = session + const user = await User.findByPk(id) + return user +} \ No newline at end of file