diff --git a/apps/portal/src/components/resumes/browse/constants.ts b/apps/portal/src/components/resumes/browse/constants.ts index 19f3035b..e08358b6 100644 --- a/apps/portal/src/components/resumes/browse/constants.ts +++ b/apps/portal/src/components/resumes/browse/constants.ts @@ -54,7 +54,7 @@ export const EXPERIENCE = [ export const LOCATION = [ { checked: false, label: 'Singapore', value: 'Singapore' }, - { checked: false, label: 'United States', value: 'Usa' }, + { checked: false, label: 'United States', value: 'US' }, { checked: false, label: 'India', value: 'India' }, ]; diff --git a/apps/portal/src/components/resumes/comments/CommentsList.tsx b/apps/portal/src/components/resumes/comments/CommentsList.tsx index 7e15e4d8..56a1affa 100644 --- a/apps/portal/src/components/resumes/comments/CommentsList.tsx +++ b/apps/portal/src/components/resumes/comments/CommentsList.tsx @@ -20,7 +20,6 @@ export default function CommentsList({ const [tab, setTab] = useState(COMMENTS_SECTIONS[0].value); const { data: session } = useSession(); - // Fetch the most updated comments to render const commentsQuery = trpc.useQuery(['resumes.reviews.list', { resumeId }]); // TODO: Add loading prompt diff --git a/apps/portal/src/pages/resumes/[resumeId].tsx b/apps/portal/src/pages/resumes/[resumeId].tsx index d56c1135..52d4f3b7 100644 --- a/apps/portal/src/pages/resumes/[resumeId].tsx +++ b/apps/portal/src/pages/resumes/[resumeId].tsx @@ -27,17 +27,17 @@ export default function ResumeReviewPage() { const { data: session } = useSession(); const router = useRouter(); const { resumeId } = router.query; - const utils = trpc.useContext(); + const trpcContext = trpc.useContext(); // Safe to assert resumeId type as string because query is only sent if so const detailsQuery = trpc.useQuery( - ['resumes.details.find', { resumeId: resumeId as string }], + ['resumes.resume.findOne', { resumeId: resumeId as string }], { - enabled: typeof resumeId === 'string' && session?.user?.id !== undefined, + enabled: typeof resumeId === 'string', }, ); - const starMutation = trpc.useMutation('resumes.details.update_star', { + const starMutation = trpc.useMutation('resumes.star.user.create_or_delete', { onSuccess() { - utils.invalidateQueries(); + trpcContext.invalidateQueries(['resumes.resume.findOne']); }, }); diff --git a/apps/portal/src/pages/resumes/index.tsx b/apps/portal/src/pages/resumes/index.tsx index 0cfde12e..357c4852 100644 --- a/apps/portal/src/pages/resumes/index.tsx +++ b/apps/portal/src/pages/resumes/index.tsx @@ -53,24 +53,30 @@ export default function ResumeHomePage() { const [searchValue, setSearchValue] = useState(''); const [resumes, setResumes] = useState>([]); - const allResumesQuery = trpc.useQuery(['resumes.resume.all'], { + const allResumesQuery = trpc.useQuery(['resumes.resume.findAll'], { enabled: tabsValue === BROWSE_TABS_VALUES.ALL, onSuccess: (data) => { setResumes(data); }, }); - const starredResumesQuery = trpc.useQuery(['resumes.resume.browse.stars'], { - enabled: tabsValue === BROWSE_TABS_VALUES.STARRED, - onSuccess: (data) => { - setResumes(data); + const starredResumesQuery = trpc.useQuery( + ['resumes.resume.user.findUserStarred'], + { + enabled: tabsValue === BROWSE_TABS_VALUES.STARRED, + onSuccess: (data) => { + setResumes(data); + }, }, - }); - const myResumesQuery = trpc.useQuery(['resumes.resume.browse.my'], { - enabled: tabsValue === BROWSE_TABS_VALUES.MY, - onSuccess: (data) => { - setResumes(data); + ); + const myResumesQuery = trpc.useQuery( + ['resumes.resume.user.findUserCreated'], + { + enabled: tabsValue === BROWSE_TABS_VALUES.MY, + onSuccess: (data) => { + setResumes(data); + }, }, - }); + ); const onClickNew = () => { if (sessionData?.user?.id) { diff --git a/apps/portal/src/server/router/index.ts b/apps/portal/src/server/router/index.ts index e6d5a960..5783f9fc 100644 --- a/apps/portal/src/server/router/index.ts +++ b/apps/portal/src/server/router/index.ts @@ -2,13 +2,12 @@ import superjson from 'superjson'; import { createRouter } from './context'; import { protectedExampleRouter } from './protected-example-router'; -import { questionsQuestionRouter} from './questions-question-router'; -import { resumesRouter } from './resumes'; -import { resumesDetailsRouter } from './resumes-details-router'; -import { resumesResumeProtectedTabsRouter } from './resumes-resume-protected-tabs-router'; -import { resumesResumeUserRouter } from './resumes-resume-user-router'; -import { resumeReviewsRouter } from './resumes-reviews-router'; -import { resumesReviewsUserRouter } from './resumes-reviews-user-router'; +import { questionsQuestionRouter } from './questions-question-router'; +import { resumesRouter } from './resumes/resumes-resume-router'; +import { resumesResumeUserRouter } from './resumes/resumes-resume-user-router'; +import { resumeReviewsRouter } from './resumes/resumes-reviews-router'; +import { resumesReviewsUserRouter } from './resumes/resumes-reviews-user-router'; +import { resumesStarUserRouter } from './resumes/resumes-star-user-router'; import { todosRouter } from './todos'; import { todosUserRouter } from './todos-user-router'; @@ -21,9 +20,8 @@ export const appRouter = createRouter() .merge('todos.', todosRouter) .merge('todos.user.', todosUserRouter) .merge('resumes.resume.', resumesRouter) - .merge('resumes.details.', resumesDetailsRouter) .merge('resumes.resume.user.', resumesResumeUserRouter) - .merge('resumes.resume.browse.', resumesResumeProtectedTabsRouter) + .merge('resumes.star.user.', resumesStarUserRouter) .merge('resumes.reviews.', resumeReviewsRouter) .merge('resumes.reviews.user.', resumesReviewsUserRouter) .merge('questions.questions.', questionsQuestionRouter); diff --git a/apps/portal/src/server/router/resumes-resume-user-router.ts b/apps/portal/src/server/router/resumes-resume-user-router.ts deleted file mode 100644 index aa41e9ce..00000000 --- a/apps/portal/src/server/router/resumes-resume-user-router.ts +++ /dev/null @@ -1,27 +0,0 @@ -import { z } from 'zod'; - -import { createProtectedRouter } from './context'; - -export const resumesResumeUserRouter = createProtectedRouter().mutation( - 'create', - { - // TODO: Use enums for experience, location, role - input: z.object({ - additionalInfo: z.string().optional(), - experience: z.string(), - location: z.string(), - role: z.string(), - title: z.string(), - url: z.string(), - }), - async resolve({ ctx, input }) { - const userId = ctx.session?.user.id; - return await ctx.prisma.resumesResume.create({ - data: { - ...input, - userId, - }, - }); - }, - }, -); diff --git a/apps/portal/src/server/router/resumes.ts b/apps/portal/src/server/router/resumes.ts deleted file mode 100644 index 2125f446..00000000 --- a/apps/portal/src/server/router/resumes.ts +++ /dev/null @@ -1,42 +0,0 @@ -import { createRouter } from './context'; - -import type { Resume } from '~/types/resume'; - -export const resumesRouter = createRouter().query('all', { - async resolve({ ctx }) { - const resumesData = await ctx.prisma.resumesResume.findMany({ - include: { - _count: { - select: { - comments: true, - stars: true, - }, - }, - user: { - select: { - name: true, - }, - }, - }, - orderBy: { - createdAt: 'desc', - }, - }); - return resumesData.map((r) => { - const resume: Resume = { - additionalInfo: r.additionalInfo, - createdAt: r.createdAt, - experience: r.experience, - id: r.id, - location: r.location, - numComments: r._count.comments, - numStars: r._count.stars, - role: r.role, - title: r.title, - url: r.url, - user: r.user.name!, - }; - return resume; - }); - }, -}); diff --git a/apps/portal/src/server/router/resumes/resumes-resume-router.ts b/apps/portal/src/server/router/resumes/resumes-resume-router.ts new file mode 100644 index 00000000..177b076e --- /dev/null +++ b/apps/portal/src/server/router/resumes/resumes-resume-router.ts @@ -0,0 +1,79 @@ +import { z } from 'zod'; + +import { createRouter } from '../context'; + +import type { Resume } from '~/types/resume'; + +export const resumesRouter = createRouter() + .query('findAll', { + async resolve({ ctx }) { + const resumesData = await ctx.prisma.resumesResume.findMany({ + include: { + _count: { + select: { + comments: true, + stars: true, + }, + }, + user: { + select: { + name: true, + }, + }, + }, + orderBy: { + createdAt: 'desc', + }, + }); + return resumesData.map((r) => { + const resume: Resume = { + additionalInfo: r.additionalInfo, + createdAt: r.createdAt, + experience: r.experience, + id: r.id, + location: r.location, + numComments: r._count.comments, + numStars: r._count.stars, + role: r.role, + title: r.title, + url: r.url, + user: r.user.name!, + }; + return resume; + }); + }, + }) + .query('findOne', { + input: z.object({ + resumeId: z.string(), + }), + async resolve({ ctx, input }) { + const { resumeId } = input; + const userId = ctx.session?.user?.id; + + // Use the resumeId to query all related information of a single resume + // from Resumesresume: + return await ctx.prisma.resumesResume.findUnique({ + include: { + _count: { + select: { + stars: true, + }, + }, + stars: { + where: { + userId, + }, + }, + user: { + select: { + name: true, + }, + }, + }, + where: { + id: resumeId, + }, + }); + }, + }); diff --git a/apps/portal/src/server/router/resumes-resume-protected-tabs-router.ts b/apps/portal/src/server/router/resumes/resumes-resume-user-router.ts similarity index 75% rename from apps/portal/src/server/router/resumes-resume-protected-tabs-router.ts rename to apps/portal/src/server/router/resumes/resumes-resume-user-router.ts index 663c0f80..3b0b5a0b 100644 --- a/apps/portal/src/server/router/resumes-resume-protected-tabs-router.ts +++ b/apps/portal/src/server/router/resumes/resumes-resume-user-router.ts @@ -1,9 +1,31 @@ -import { createProtectedRouter } from './context'; +import { z } from 'zod'; + +import { createProtectedRouter } from '../context'; import type { Resume } from '~/types/resume'; -export const resumesResumeProtectedTabsRouter = createProtectedRouter() - .query('stars', { +export const resumesResumeUserRouter = createProtectedRouter() + .mutation('create', { + // TODO: Use enums for experience, location, role + input: z.object({ + additionalInfo: z.string().optional(), + experience: z.string(), + location: z.string(), + role: z.string(), + title: z.string(), + url: z.string(), + }), + async resolve({ ctx, input }) { + const userId = ctx.session?.user.id; + return await ctx.prisma.resumesResume.create({ + data: { + ...input, + userId, + }, + }); + }, + }) + .query('findUserStarred', { async resolve({ ctx }) { const userId = ctx.session?.user?.id; const resumeStarsData = await ctx.prisma.resumesStar.findMany({ @@ -49,7 +71,7 @@ export const resumesResumeProtectedTabsRouter = createProtectedRouter() }); }, }) - .query('my', { + .query('findUserCreated', { async resolve({ ctx }) { const userId = ctx.session?.user?.id; const resumesData = await ctx.prisma.resumesResume.findMany({ diff --git a/apps/portal/src/server/router/resumes-reviews-router.ts b/apps/portal/src/server/router/resumes/resumes-reviews-router.ts similarity index 97% rename from apps/portal/src/server/router/resumes-reviews-router.ts rename to apps/portal/src/server/router/resumes/resumes-reviews-router.ts index f908717e..04672cb2 100644 --- a/apps/portal/src/server/router/resumes-reviews-router.ts +++ b/apps/portal/src/server/router/resumes/resumes-reviews-router.ts @@ -1,6 +1,6 @@ import { z } from 'zod'; -import { createRouter } from './context'; +import { createRouter } from '../context'; import type { ResumeComment } from '~/types/resume-comments'; diff --git a/apps/portal/src/server/router/resumes-reviews-user-router.ts b/apps/portal/src/server/router/resumes/resumes-reviews-user-router.ts similarity index 96% rename from apps/portal/src/server/router/resumes-reviews-user-router.ts rename to apps/portal/src/server/router/resumes/resumes-reviews-user-router.ts index 5730887f..069e5548 100644 --- a/apps/portal/src/server/router/resumes-reviews-user-router.ts +++ b/apps/portal/src/server/router/resumes/resumes-reviews-user-router.ts @@ -1,7 +1,7 @@ import { z } from 'zod'; import { ResumesSection } from '@prisma/client'; -import { createProtectedRouter } from './context'; +import { createProtectedRouter } from '../context'; type IResumeCommentInput = Readonly<{ description: string; diff --git a/apps/portal/src/server/router/resumes-details-router.ts b/apps/portal/src/server/router/resumes/resumes-star-user-router.ts similarity index 51% rename from apps/portal/src/server/router/resumes-details-router.ts rename to apps/portal/src/server/router/resumes/resumes-star-user-router.ts index 1255ac2e..40daea7d 100644 --- a/apps/portal/src/server/router/resumes-details-router.ts +++ b/apps/portal/src/server/router/resumes/resumes-star-user-router.ts @@ -1,43 +1,10 @@ import { z } from 'zod'; -import { createRouter } from './context'; +import { createProtectedRouter } from '../context'; -export const resumesDetailsRouter = createRouter() - .query('find', { - input: z.object({ - resumeId: z.string(), - }), - async resolve({ ctx, input }) { - const { resumeId } = input; - const userId = ctx.session?.user?.id; - - // Use the resumeId to query all related information of a single resume - // from Resumesresume: - return await ctx.prisma.resumesResume.findUnique({ - include: { - _count: { - select: { - stars: true, - }, - }, - stars: { - where: { - userId, - }, - }, - user: { - select: { - name: true, - }, - }, - }, - where: { - id: resumeId, - }, - }); - }, - }) - .mutation('update_star', { +export const resumesStarUserRouter = createProtectedRouter().mutation( + 'create_or_delete', + { input: z.object({ resumeId: z.string(), }), @@ -76,4 +43,5 @@ export const resumesDetailsRouter = createRouter() }, }); }, - }); + }, +);