|
|
@ -1,6 +1,14 @@
|
|
|
|
import { useSession } from 'next-auth/react';
|
|
|
|
import { useSession } from 'next-auth/react';
|
|
|
|
import { useState } from 'react';
|
|
|
|
import {
|
|
|
|
import { Spinner, Tabs } from '@tih/ui';
|
|
|
|
BookOpenIcon,
|
|
|
|
|
|
|
|
BriefcaseIcon,
|
|
|
|
|
|
|
|
CodeBracketSquareIcon,
|
|
|
|
|
|
|
|
FaceSmileIcon,
|
|
|
|
|
|
|
|
IdentificationIcon,
|
|
|
|
|
|
|
|
SparklesIcon,
|
|
|
|
|
|
|
|
} from '@heroicons/react/24/outline';
|
|
|
|
|
|
|
|
import { ResumesSection } from '@prisma/client';
|
|
|
|
|
|
|
|
import { Spinner } from '@tih/ui';
|
|
|
|
import { Button } from '@tih/ui';
|
|
|
|
import { Button } from '@tih/ui';
|
|
|
|
|
|
|
|
|
|
|
|
import { trpc } from '~/utils/trpc';
|
|
|
|
import { trpc } from '~/utils/trpc';
|
|
|
@ -21,23 +29,26 @@ export default function ResumeCommentsList({
|
|
|
|
setShowCommentsForm,
|
|
|
|
setShowCommentsForm,
|
|
|
|
}: ResumeCommentsListProps) {
|
|
|
|
}: ResumeCommentsListProps) {
|
|
|
|
const { data: sessionData } = useSession();
|
|
|
|
const { data: sessionData } = useSession();
|
|
|
|
const [tab, setTab] = useState(RESUME_COMMENTS_SECTIONS[0].value);
|
|
|
|
|
|
|
|
const [tabs, setTabs] = useState(RESUME_COMMENTS_SECTIONS);
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
const commentsQuery = trpc.useQuery(['resumes.comments.list', { resumeId }], {
|
|
|
|
const commentsQuery = trpc.useQuery(['resumes.comments.list', { resumeId }]);
|
|
|
|
onSuccess: (data: Array<ResumeComment>) => {
|
|
|
|
|
|
|
|
const updatedTabs = RESUME_COMMENTS_SECTIONS.map(({ label, value }) => {
|
|
|
|
|
|
|
|
const count = data.filter(({ section }) => section === value).length;
|
|
|
|
|
|
|
|
const updatedLabel = count > 0 ? `${label} (${count})` : label;
|
|
|
|
|
|
|
|
return {
|
|
|
|
|
|
|
|
label: updatedLabel,
|
|
|
|
|
|
|
|
value,
|
|
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
setTabs(updatedTabs);
|
|
|
|
const renderIcon = (section: ResumesSection) => {
|
|
|
|
},
|
|
|
|
const className = 'h-8 w-8';
|
|
|
|
});
|
|
|
|
switch (section) {
|
|
|
|
|
|
|
|
case ResumesSection.GENERAL:
|
|
|
|
|
|
|
|
return <IdentificationIcon className={className} />;
|
|
|
|
|
|
|
|
case ResumesSection.EDUCATION:
|
|
|
|
|
|
|
|
return <BookOpenIcon className={className} />;
|
|
|
|
|
|
|
|
case ResumesSection.EXPERIENCE:
|
|
|
|
|
|
|
|
return <BriefcaseIcon className={className} />;
|
|
|
|
|
|
|
|
case ResumesSection.PROJECTS:
|
|
|
|
|
|
|
|
return <CodeBracketSquareIcon className={className} />;
|
|
|
|
|
|
|
|
case ResumesSection.SKILLS:
|
|
|
|
|
|
|
|
return <SparklesIcon className={className} />;
|
|
|
|
|
|
|
|
default:
|
|
|
|
|
|
|
|
return <FaceSmileIcon className={className} />;
|
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
|
|
const renderButton = () => {
|
|
|
|
const renderButton = () => {
|
|
|
|
if (sessionData === null) {
|
|
|
|
if (sessionData === null) {
|
|
|
@ -57,29 +68,45 @@ export default function ResumeCommentsList({
|
|
|
|
<div className="space-y-3">
|
|
|
|
<div className="space-y-3">
|
|
|
|
{renderButton()}
|
|
|
|
{renderButton()}
|
|
|
|
|
|
|
|
|
|
|
|
<Tabs
|
|
|
|
|
|
|
|
label="comments"
|
|
|
|
|
|
|
|
tabs={tabs}
|
|
|
|
|
|
|
|
value={tab}
|
|
|
|
|
|
|
|
onChange={(value) => setTab(value)}
|
|
|
|
|
|
|
|
/>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
{commentsQuery.isFetching ? (
|
|
|
|
{commentsQuery.isFetching ? (
|
|
|
|
<div className="col-span-10 pt-4">
|
|
|
|
<div className="col-span-10 pt-4">
|
|
|
|
<Spinner display="block" size="lg" />
|
|
|
|
<Spinner display="block" size="lg" />
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
) : (
|
|
|
|
) : (
|
|
|
|
<div className="m-2 flow-root h-[calc(100vh-20rem)] w-full flex-col space-y-3 overflow-y-auto">
|
|
|
|
<div className="m-2 flow-root h-[calc(100vh-20rem)] w-full flex-col space-y-4 overflow-y-auto">
|
|
|
|
{(commentsQuery.data?.filter((c) => c.section === tab) ?? []).map(
|
|
|
|
{RESUME_COMMENTS_SECTIONS.map(({ label, value }) => {
|
|
|
|
(comment) => (
|
|
|
|
const comments = commentsQuery.data
|
|
|
|
|
|
|
|
? commentsQuery.data.filter((comment: ResumeComment) => {
|
|
|
|
|
|
|
|
return (comment.section as string) === value;
|
|
|
|
|
|
|
|
})
|
|
|
|
|
|
|
|
: [];
|
|
|
|
|
|
|
|
const commentCount = comments.length;
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
return (
|
|
|
|
|
|
|
|
<div key={value} className="mb-4 space-y-3">
|
|
|
|
|
|
|
|
<div className="flex flex-row items-center space-x-2 text-indigo-800">
|
|
|
|
|
|
|
|
{renderIcon(value)}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
<div className="w-fit text-xl font-medium">{label}</div>
|
|
|
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
{commentCount > 0 ? (
|
|
|
|
|
|
|
|
comments.map((comment) => {
|
|
|
|
|
|
|
|
return (
|
|
|
|
<ResumeCommentListItem
|
|
|
|
<ResumeCommentListItem
|
|
|
|
key={comment.id}
|
|
|
|
key={comment.id}
|
|
|
|
comment={comment}
|
|
|
|
comment={comment}
|
|
|
|
userId={sessionData?.user?.id}
|
|
|
|
userId={sessionData?.user?.id}
|
|
|
|
/>
|
|
|
|
/>
|
|
|
|
),
|
|
|
|
);
|
|
|
|
|
|
|
|
})
|
|
|
|
|
|
|
|
) : (
|
|
|
|
|
|
|
|
<div>There are no comments for this section yet!</div>
|
|
|
|
)}
|
|
|
|
)}
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
|
|
|
|
);
|
|
|
|
|
|
|
|
})}
|
|
|
|
|
|
|
|
</div>
|
|
|
|
)}
|
|
|
|
)}
|
|
|
|
</div>
|
|
|
|
</div>
|
|
|
|
);
|
|
|
|
);
|
|
|
|