From a4b738508f98ca49268cdea7cc082283d973c153 Mon Sep 17 00:00:00 2001 From: Dakshesh Jain Date: Wed, 21 Dec 2022 11:55:54 +0530 Subject: [PATCH 1/4] fix: selecting random emoji on create-project --- apps/app/components/project/create-project-modal.tsx | 4 ++-- apps/app/ui/emoji-icon-picker/index.tsx | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/apps/app/components/project/create-project-modal.tsx b/apps/app/components/project/create-project-modal.tsx index 3e1d0c5a2..e93fa6d10 100644 --- a/apps/app/components/project/create-project-modal.tsx +++ b/apps/app/components/project/create-project-modal.tsx @@ -9,7 +9,7 @@ import { Dialog, Transition } from "@headlessui/react"; import projectServices from "lib/services/project.service"; import workspaceService from "lib/services/workspace.service"; // common -import { createSimilarString } from "constants/common"; +import { createSimilarString, getRandomEmoji } from "constants/common"; // constants import { NETWORK_CHOICES } from "constants/"; // fetch keys @@ -32,7 +32,7 @@ const defaultValues: Partial = { identifier: "", description: "", network: 0, - icon: "", + icon: getRandomEmoji(), }; const IsGuestCondition: React.FC<{ diff --git a/apps/app/ui/emoji-icon-picker/index.tsx b/apps/app/ui/emoji-icon-picker/index.tsx index dbe8abeee..26afe7d67 100644 --- a/apps/app/ui/emoji-icon-picker/index.tsx +++ b/apps/app/ui/emoji-icon-picker/index.tsx @@ -39,7 +39,7 @@ const EmojiIconPicker: React.FC = ({ label, value, onChange }) => { }); useEffect(() => { - if (!value) onChange(getRandomEmoji()); + if (!value || value?.length === 0) onChange(getRandomEmoji()); }, [value, onChange]); return ( From 08deff5d21ea6aa1e268883eb68f04e7cbb656ec Mon Sep 17 00:00:00 2001 From: Dakshesh Jain Date: Wed, 21 Dec 2022 12:45:46 +0530 Subject: [PATCH 2/4] refractor: changed to due date from target date --- .../common/board-view/single-issue.tsx | 8 ++-- .../project/cycles/list-view/index.tsx | 12 +++--- .../project/issues/list-view/index.tsx | 8 ++-- apps/app/lib/hooks/useIssuesProperties.tsx | 38 ++++++++++--------- apps/app/lib/hooks/useMyIssueFilter.tsx | 2 +- apps/app/pages/me/my-issues.tsx | 10 ++--- apps/app/types/issues.d.ts | 2 +- 7 files changed, 41 insertions(+), 39 deletions(-) diff --git a/apps/app/components/common/board-view/single-issue.tsx b/apps/app/components/common/board-view/single-issue.tsx index 5ce4ff0c0..3fde79ae1 100644 --- a/apps/app/components/common/board-view/single-issue.tsx +++ b/apps/app/components/common/board-view/single-issue.tsx @@ -228,7 +228,7 @@ const SingleIssue: React.FC = ({ )} - {properties.target_date && ( + {properties.due_date && (
= ({
{issue.target_date && (issue.target_date < new Date().toISOString() - ? `Target date has passed by ${findHowManyDaysLeft(issue.target_date)} days` + ? `Due date has passed by ${findHowManyDaysLeft(issue.target_date)} days` : findHowManyDaysLeft(issue.target_date) <= 3 - ? `Target date is in ${findHowManyDaysLeft(issue.target_date)} days` - : "Target date")} + ? `Due date is in ${findHowManyDaysLeft(issue.target_date)} days` + : "Due date")}
diff --git a/apps/app/components/project/cycles/list-view/index.tsx b/apps/app/components/project/cycles/list-view/index.tsx index 1ad8fa8a9..8c34e3109 100644 --- a/apps/app/components/project/cycles/list-view/index.tsx +++ b/apps/app/components/project/cycles/list-view/index.tsx @@ -218,7 +218,7 @@ const CyclesListView: React.FC = ({ )} - {properties.target_date && ( + {properties.due_date && (
= ({ ? renderShortNumericDateFormat(issue.target_date) : "N/A"}
-
- Target date -
+
Due date
{renderShortNumericDateFormat(issue.target_date ?? "")}
{issue.target_date && (issue.target_date < new Date().toISOString() - ? `Target date has passed by ${findHowManyDaysLeft( + ? `Due date has passed by ${findHowManyDaysLeft( issue.target_date )} days` : findHowManyDaysLeft(issue.target_date) <= 3 - ? `Target date is in ${findHowManyDaysLeft( + ? `Due date is in ${findHowManyDaysLeft( issue.target_date )} days` - : "Target date")} + : "Due date")}
diff --git a/apps/app/components/project/issues/list-view/index.tsx b/apps/app/components/project/issues/list-view/index.tsx index 6758a1205..9d3dadc18 100644 --- a/apps/app/components/project/issues/list-view/index.tsx +++ b/apps/app/components/project/issues/list-view/index.tsx @@ -310,7 +310,7 @@ const ListView: React.FC = ({ )} - {properties.target_date && ( + {properties.due_date && (
= ({
{issue.target_date && (issue.target_date < new Date().toISOString() - ? `Target date has passed by ${findHowManyDaysLeft( + ? `Due date has passed by ${findHowManyDaysLeft( issue.target_date )} days` : findHowManyDaysLeft(issue.target_date) <= 3 - ? `Target date is in ${findHowManyDaysLeft( + ? `Due date is in ${findHowManyDaysLeft( issue.target_date )} days` - : "Target date")} + : "Due date")}
diff --git a/apps/app/lib/hooks/useIssuesProperties.tsx b/apps/app/lib/hooks/useIssuesProperties.tsx index 223eafe2a..e509a6f16 100644 --- a/apps/app/lib/hooks/useIssuesProperties.tsx +++ b/apps/app/lib/hooks/useIssuesProperties.tsx @@ -16,7 +16,7 @@ const initialValues: Properties = { assignee: true, priority: false, start_date: false, - target_date: false, + due_date: false, cycle: false, children_count: false, }; @@ -26,7 +26,7 @@ const useIssuesProperties = (workspaceSlug?: string, projectId?: string) => { const { user } = useUser(); - const { data: issueProperties } = useSWR( + const { data: issueProperties, mutate: mutateIssueProperties } = useSWR( workspaceSlug && projectId ? ISSUE_PROPERTIES_ENDPOINT(workspaceSlug, projectId) : null, workspaceSlug && projectId ? () => issueServices.getIssueProperties(workspaceSlug, projectId) @@ -56,6 +56,14 @@ const useIssuesProperties = (workspaceSlug?: string, projectId?: string) => { (key: keyof Properties) => { if (!workspaceSlug || !projectId || !issueProperties || !user) return; setProperties((prev) => ({ ...prev, [key]: !prev[key] })); + mutateIssueProperties( + (prev) => + ({ + ...prev, + properties: { ...prev?.properties, [key]: !prev?.properties?.[key] }, + } as IssuePriorities), + false + ); if (Object.keys(issueProperties).length > 0) { issueServices.patchIssueProperties(workspaceSlug, projectId, issueProperties.id, { properties: { @@ -71,23 +79,19 @@ const useIssuesProperties = (workspaceSlug?: string, projectId?: string) => { }); } }, - [workspaceSlug, projectId, issueProperties, user] + [workspaceSlug, projectId, issueProperties, user, mutateIssueProperties] ); - const newProperties = Object.keys(properties).reduce((obj: any, key) => { - if ( - key !== "children" && - key !== "name" && - key !== "parent" && - key !== "project" && - key !== "description" && - key !== "attachments" && - key !== "sequence_id" - ) { - obj[key] = properties[key as keyof Properties]; - } - return obj; - }, {}); + const newProperties: Properties = { + key: properties.key, + state: properties.state, + assignee: properties.assignee, + priority: properties.priority, + start_date: properties.start_date, + due_date: properties.due_date, + cycle: properties.cycle, + children_count: properties.children_count, + }; return [newProperties, updateIssueProperties] as const; }; diff --git a/apps/app/lib/hooks/useMyIssueFilter.tsx b/apps/app/lib/hooks/useMyIssueFilter.tsx index da8055a5f..019d0fa99 100644 --- a/apps/app/lib/hooks/useMyIssueFilter.tsx +++ b/apps/app/lib/hooks/useMyIssueFilter.tsx @@ -16,7 +16,7 @@ const initialValues: Properties = { assignee: true, priority: false, start_date: false, - target_date: false, + due_date: false, cycle: false, children_count: false, }; diff --git a/apps/app/pages/me/my-issues.tsx b/apps/app/pages/me/my-issues.tsx index 1a7b2f78b..3b6802ec6 100644 --- a/apps/app/pages/me/my-issues.tsx +++ b/apps/app/pages/me/my-issues.tsx @@ -398,7 +398,7 @@ const MyIssues: NextPage = () => { )} - {properties.target_date && ( + {properties.due_date && (
{ : "N/A"}
- Target date + Due date
{renderShortNumericDateFormat(issue.target_date ?? "")} @@ -423,14 +423,14 @@ const MyIssues: NextPage = () => {
{issue.target_date && (issue.target_date < new Date().toISOString() - ? `Target date has passed by ${findHowManyDaysLeft( + ? `Due date has passed by ${findHowManyDaysLeft( issue.target_date )} days` : findHowManyDaysLeft(issue.target_date) <= 3 - ? `Target date is in ${findHowManyDaysLeft( + ? `Due date is in ${findHowManyDaysLeft( issue.target_date )} days` - : "Target date")} + : "Due date")}
diff --git a/apps/app/types/issues.d.ts b/apps/app/types/issues.d.ts index 685623424..2ffb77f2d 100644 --- a/apps/app/types/issues.d.ts +++ b/apps/app/types/issues.d.ts @@ -130,7 +130,7 @@ export type Properties = { assignee: boolean; priority: boolean; start_date: boolean; - target_date: boolean; + due_date: boolean; cycle: boolean; children_count: boolean; }; From f67bbbf9ff48d8e716d1e7f235ddb47109ac5606 Mon Sep 17 00:00:00 2001 From: Dakshesh Jain Date: Wed, 21 Dec 2022 16:45:54 +0530 Subject: [PATCH 3/4] fix: made description as optional field in project settings --- apps/app/pages/projects/[projectId]/settings/index.tsx | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/apps/app/pages/projects/[projectId]/settings/index.tsx b/apps/app/pages/projects/[projectId]/settings/index.tsx index 99bd8a1cd..aaea02d61 100644 --- a/apps/app/pages/projects/[projectId]/settings/index.tsx +++ b/apps/app/pages/projects/[projectId]/settings/index.tsx @@ -177,9 +177,7 @@ const GeneralSettings = () => { error={errors.description} register={register} placeholder="Enter project description" - validations={{ - required: "Description is required", - }} + validations={{}} />
From eadebd8d93c85f100ad59230fa48ebbba14e21c5 Mon Sep 17 00:00:00 2001 From: Dakshesh Jain Date: Wed, 21 Dec 2022 19:11:04 +0530 Subject: [PATCH 4/4] refractor: moved all local state, and component to that component, used dynamic imports where-ever possible --- .../issues/issue-detail/activity/index.tsx | 39 +++- .../comment/IssueCommentSection.tsx | 72 +++++--- .../issue-detail-sidebar/index.tsx | 22 ++- .../issue-detail-sidebar/select-cycle.tsx | 6 +- .../projects/[projectId]/issues/[issueId].tsx | 173 +++++++----------- apps/app/types/issues.d.ts | 1 + apps/app/ui/Breadcrumbs/index.tsx | 4 +- 7 files changed, 167 insertions(+), 150 deletions(-) diff --git a/apps/app/components/project/issues/issue-detail/activity/index.tsx b/apps/app/components/project/issues/issue-detail/activity/index.tsx index 84085d7b1..9b105d2d3 100644 --- a/apps/app/components/project/issues/issue-detail/activity/index.tsx +++ b/apps/app/components/project/issues/issue-detail/activity/index.tsx @@ -1,5 +1,16 @@ +import React from "react"; // next +import { useRouter } from "next/router"; import Image from "next/image"; +// swr +import useSWR from "swr"; +// constants +import { PROJECT_ISSUES_ACTIVITY } from "constants/fetch-keys"; +import { addSpaceIfCamelCase, timeAgo } from "constants/common"; +// services +import issuesServices from "lib/services/issues.service"; +// hooks +import useUser from "lib/hooks/useUser"; // ui import { Spinner } from "ui"; // icons @@ -12,14 +23,6 @@ import { } from "@heroicons/react/24/outline"; // types import { IssueResponse, IState } from "types"; -// constants -import { addSpaceIfCamelCase, timeAgo } from "constants/common"; - -type Props = { - issueActivities: any[] | undefined; - states: IState[] | undefined; - issues: IssueResponse | undefined; -}; const activityIcons: { [key: string]: JSX.Element; @@ -32,7 +35,25 @@ const activityIcons: { parent: , }; -const IssueActivitySection: React.FC = ({ issueActivities, states, issues }) => { +const IssueActivitySection: React.FC = () => { + const router = useRouter(); + + const { issueId, projectId } = router.query; + + const { activeWorkspace, states, issues } = useUser(); + + const { data: issueActivities } = useSWR( + activeWorkspace && projectId && issueId ? PROJECT_ISSUES_ACTIVITY : null, + activeWorkspace && projectId && issueId + ? () => + issuesServices.getIssueActivities( + activeWorkspace.slug, + projectId as string, + issueId as string + ) + : null + ); + return ( <> {issueActivities ? ( diff --git a/apps/app/components/project/issues/issue-detail/comment/IssueCommentSection.tsx b/apps/app/components/project/issues/issue-detail/comment/IssueCommentSection.tsx index fe55bdbf5..d5f4b62ce 100644 --- a/apps/app/components/project/issues/issue-detail/comment/IssueCommentSection.tsx +++ b/apps/app/components/project/issues/issue-detail/comment/IssueCommentSection.tsx @@ -1,12 +1,16 @@ import React from "react"; +// router +import { useRouter } from "next/router"; // swr -import { mutate } from "swr"; +import useSWR from "swr"; // react hook form import { useForm } from "react-hook-form"; // services import issuesServices from "lib/services/issues.service"; // fetch keys import { PROJECT_ISSUES_COMMENTS } from "constants/fetch-keys"; +// hooks +import useUser from "lib/hooks/useUser"; // components import CommentCard from "components/project/issues/issue-detail/comment/IssueCommentCard"; // ui @@ -14,18 +18,11 @@ import { TextArea, Button, Spinner } from "ui"; // types import type { IIssueComment } from "types"; -type Props = { - comments?: IIssueComment[]; - workspaceSlug: string; - projectId: string; - issueId: string; -}; - const defaultValues: Partial = { comment: "", }; -const IssueCommentSection: React.FC = ({ comments, issueId, projectId, workspaceSlug }) => { +const IssueCommentSection: React.FC = () => { const { register, handleSubmit, @@ -34,15 +31,31 @@ const IssueCommentSection: React.FC = ({ comments, issueId, projectId, wo reset, } = useForm({ defaultValues }); + const router = useRouter(); + + let { issueId, projectId } = router.query; + + const { activeWorkspace } = useUser(); + + const { data: comments, mutate } = useSWR( + activeWorkspace && projectId && issueId ? PROJECT_ISSUES_COMMENTS(issueId as string) : null, + activeWorkspace && projectId && issueId + ? () => + issuesServices.getIssueComments( + activeWorkspace.slug, + projectId as string, + issueId as string + ) + : null + ); + const onSubmit = async (formData: IIssueComment) => { + if (!activeWorkspace || !projectId || !issueId || isSubmitting) return; await issuesServices - .createIssueComment(workspaceSlug, projectId, issueId, formData) + .createIssueComment(activeWorkspace.slug, projectId as string, issueId as string, formData) .then((response) => { console.log(response); - mutate(PROJECT_ISSUES_COMMENTS(issueId), (prevData) => [ - response, - ...(prevData ?? []), - ]); + mutate((prevData) => [response, ...(prevData ?? [])]); reset(defaultValues); }) .catch((error) => { @@ -51,26 +64,34 @@ const IssueCommentSection: React.FC = ({ comments, issueId, projectId, wo }; const onCommentUpdate = async (comment: IIssueComment) => { + if (!activeWorkspace || !projectId || !issueId || isSubmitting) return; await issuesServices - .patchIssueComment(workspaceSlug, projectId, issueId, comment.id, comment) + .patchIssueComment( + activeWorkspace.slug, + projectId as string, + issueId as string, + comment.id, + comment + ) .then((response) => { - console.log(response); - mutate(PROJECT_ISSUES_COMMENTS(issueId), (prevData) => { - const newData = prevData ?? []; - const index = newData.findIndex((comment) => comment.id === response.id); - newData[index] = response; - return [...newData]; + mutate((prevData) => { + const updatedComments = prevData?.map((c) => { + if (c.id === comment.id) { + return comment; + } + return c; + }); + return updatedComments; }); }); }; const onCommentDelete = async (commentId: string) => { + if (!activeWorkspace || !projectId || !issueId || isSubmitting) return; await issuesServices - .deleteIssueComment(workspaceSlug, projectId, issueId, commentId) + .deleteIssueComment(activeWorkspace.slug, projectId as string, issueId as string, commentId) .then((response) => { - mutate(PROJECT_ISSUES_COMMENTS(issueId), (prevData) => - (prevData ?? []).filter((c) => c.id !== commentId) - ); + mutate((prevData) => (prevData ?? []).filter((c) => c.id !== commentId)); console.log(response); }); }; @@ -124,7 +145,6 @@ const IssueCommentSection: React.FC = ({ comments, issueId, projectId, wo />
diff --git a/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/index.tsx b/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/index.tsx index 9fedbb757..88c1dadaf 100644 --- a/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/index.tsx +++ b/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/index.tsx @@ -1,6 +1,7 @@ import React, { useState } from "react"; // swr import useSWR from "swr"; +import dynamic from "next/dynamic"; // headless ui import { Listbox, Transition } from "@headlessui/react"; // react hook form @@ -14,6 +15,8 @@ import useToast from "lib/hooks/useToast"; import { PROJECT_ISSUE_LABELS } from "constants/fetch-keys"; // commons import { copyTextToClipboard } from "constants/common"; +// components +import ConfirmIssueDeletion from "components/project/issues/confirm-issue-deletion"; // ui import { Input, Button, Spinner } from "ui"; import { Popover } from "@headlessui/react"; @@ -30,7 +33,7 @@ import { } from "@heroicons/react/24/outline"; // types import type { Control } from "react-hook-form"; -import type { IIssue, IIssueLabels, NestedKeyOf } from "types"; +import type { ICycle, IIssue, IIssueLabels, NestedKeyOf } from "types"; import { TwitterPicker } from "react-color"; import { positionEditorElement } from "components/lexical/helpers/editor"; import SelectState from "./select-state"; @@ -46,7 +49,6 @@ type Props = { submitChanges: (formData: Partial) => void; issueDetail: IIssue | undefined; watch: UseFormWatch; - setDeleteIssueModal: React.Dispatch>; }; const defaultValues: Partial = { @@ -59,7 +61,6 @@ const IssueDetailSidebar: React.FC = ({ submitChanges, issueDetail, watch: watchIssue, - setDeleteIssueModal, }) => { const [createLabelForm, setCreateLabelForm] = useState(false); @@ -74,6 +75,8 @@ const IssueDetailSidebar: React.FC = ({ : null ); + const [deleteIssueModal, setDeleteIssueModal] = useState(false); + const { register, handleSubmit, @@ -97,15 +100,17 @@ const IssueDetailSidebar: React.FC = ({ }); }; - const handleCycleChange = (cycleId: string) => { - if (activeWorkspace && activeProject && issueDetail) + const handleCycleChange = (cycleDetail: ICycle) => { + if (activeWorkspace && activeProject && issueDetail) { + submitChanges({ cycle: cycleDetail.id, cycle_detail: cycleDetail }); issuesServices - .addIssueToCycle(activeWorkspace.slug, activeProject.id, cycleId, { + .addIssueToCycle(activeWorkspace.slug, activeProject.id, cycleDetail.id, { issues: [issueDetail.id], }) .then(() => { submitChanges({}); }); + } }; return ( @@ -420,6 +425,11 @@ const IssueDetailSidebar: React.FC = ({ )} + setDeleteIssueModal(false)} + isOpen={deleteIssueModal} + data={issueDetail} + /> ); }; diff --git a/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/select-cycle.tsx b/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/select-cycle.tsx index 0d8b32c65..21c18fa36 100644 --- a/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/select-cycle.tsx +++ b/apps/app/components/project/issues/issue-detail/issue-detail-sidebar/select-cycle.tsx @@ -9,13 +9,13 @@ import { Spinner, CustomSelect } from "ui"; // icons import { ArrowPathIcon } from "@heroicons/react/24/outline"; // types -import { IIssue } from "types"; +import { ICycle, IIssue } from "types"; // common import { classNames } from "constants/common"; type Props = { control: Control; - handleCycleChange: (cycleId: string) => void; + handleCycleChange: (cycle: ICycle) => void; }; const SelectCycle: React.FC = ({ control, handleCycleChange }) => { @@ -46,7 +46,7 @@ const SelectCycle: React.FC = ({ control, handleCycleChange }) => { } value={value} onChange={(value: any) => { - handleCycleChange(value); + handleCycleChange(cycles?.find((c) => c.id === value) as any); }} > {cycles ? ( diff --git a/apps/app/pages/projects/[projectId]/issues/[issueId].tsx b/apps/app/pages/projects/[projectId]/issues/[issueId].tsx index 5da9e6d1a..43adddc27 100644 --- a/apps/app/pages/projects/[projectId]/issues/[issueId].tsx +++ b/apps/app/pages/projects/[projectId]/issues/[issueId].tsx @@ -1,21 +1,17 @@ import React, { useCallback, useEffect, useState } from "react"; // next import Link from "next/link"; +import dynamic from "next/dynamic"; import type { NextPage } from "next"; import { useRouter } from "next/router"; -import dynamic from "next/dynamic"; // swr -import useSWR, { mutate } from "swr"; +import { mutate } from "swr"; // react hook form import { useForm } from "react-hook-form"; // headless ui import { Disclosure, Menu, Tab, Transition } from "@headlessui/react"; // fetch keys -import { - PROJECT_ISSUES_ACTIVITY, - PROJECT_ISSUES_COMMENTS, - PROJECT_ISSUES_LIST, -} from "constants/fetch-keys"; +import { PROJECT_ISSUES_LIST } from "constants/fetch-keys"; // services import issuesServices from "lib/services/issues.service"; // common @@ -27,14 +23,23 @@ import withAuth from "lib/hoc/withAuthWrapper"; // layouts import AppLayout from "layouts/app-layout"; // components -import CreateUpdateIssuesModal from "components/project/issues/create-update-issue-modal"; -import IssueCommentSection from "components/project/issues/issue-detail/comment/IssueCommentSection"; import AddAsSubIssue from "components/project/issues/issue-detail/add-as-sub-issue"; -import ConfirmIssueDeletion from "components/project/issues/confirm-issue-deletion"; +import CreateUpdateIssuesModal from "components/project/issues/create-update-issue-modal"; import IssueDetailSidebar from "components/project/issues/issue-detail/issue-detail-sidebar"; -import IssueActivitySection from "components/project/issues/issue-detail/activity"; +import IssueCommentSection from "components/project/issues/issue-detail/comment/IssueCommentSection"; +const IssueActivitySection = dynamic( + () => import("components/project/issues/issue-detail/activity"), + { + loading: () => ( +
+ +
+ ), + ssr: false, + } +); // ui -import { Spinner, TextArea, HeaderButton, Breadcrumbs, BreadcrumbItem, CustomMenu } from "ui"; +import { Spinner, TextArea, HeaderButton, Breadcrumbs } from "ui"; // icons import { ChevronLeftIcon, @@ -43,32 +48,51 @@ import { PlusIcon, } from "@heroicons/react/24/outline"; // types -import { IIssue, IIssueComment, IssueResponse } from "types"; +import { IIssue, IssueResponse } from "types"; const RichTextEditor = dynamic(() => import("components/lexical/editor"), { ssr: false, }); +const defaultValues = { + name: "", + description: "", + state: "", + assignees_list: [], + priority: "low", + blockers_list: [], + blocked_list: [], + target_date: new Date().toString(), + issue_cycle: null, + labels_list: [], +}; + const IssueDetail: NextPage = () => { - const [deleteIssueModal, setDeleteIssueModal] = useState(false); + const router = useRouter(); + + const { issueId, projectId } = router.query; + + const { activeWorkspace, activeProject, issues, mutateIssues } = useUser(); + + const issueDetail = issues?.results?.find((issue) => issue.id === issueId); + + const prevIssue = issues?.results[issues?.results.findIndex((issue) => issue.id === issueId) - 1]; + const nextIssue = issues?.results[issues?.results.findIndex((issue) => issue.id === issueId) + 1]; + + const subIssues = (issues && issues.results.filter((i) => i.parent === issueId)) ?? []; + const siblingIssues = + issueDetail && + issues?.results.filter((i) => i.parent === issueDetail.parent && i.id !== issueId); const [isOpen, setIsOpen] = useState(false); const [isAddAsSubIssueOpen, setIsAddAsSubIssueOpen] = useState(false); - const [issueDetail, setIssueDetail] = useState(undefined); - const [preloadedData, setPreloadedData] = useState< (Partial & { actionType: "createIssue" | "edit" | "delete" }) | undefined >(undefined); const [issueDescriptionValue, setIssueDescriptionValue] = useState(""); - const router = useRouter(); - - const { issueId, projectId } = router.query; - - const { activeWorkspace, activeProject, issues, mutateIssues, states } = useUser(); - const handleDescriptionChange: any = (value: any) => { console.log(value); setIssueDescriptionValue(value); @@ -82,44 +106,9 @@ const IssueDetail: NextPage = () => { control, watch, } = useForm({ - defaultValues: { - name: "", - description: "", - state: "", - assignees_list: [], - priority: "low", - blockers_list: [], - blocked_list: [], - target_date: new Date().toString(), - issue_cycle: null, - labels_list: [], - }, + defaultValues, }); - const { data: issueActivities } = useSWR( - activeWorkspace && projectId && issueId ? PROJECT_ISSUES_ACTIVITY : null, - activeWorkspace && projectId && issueId - ? () => - issuesServices.getIssueActivities( - activeWorkspace.slug, - projectId as string, - issueId as string - ) - : null - ); - - const { data: issueComments } = useSWR( - activeWorkspace && projectId && issueId ? PROJECT_ISSUES_COMMENTS(issueId as string) : null, - activeWorkspace && projectId && issueId - ? () => - issuesServices.getIssueComments( - activeWorkspace.slug, - projectId as string, - issueId as string - ) - : null - ); - const submitChanges = useCallback( (formData: Partial) => { if (!activeWorkspace || !activeProject || !issueId) return; @@ -180,19 +169,6 @@ const IssueDetail: NextPage = () => { }); }, [issueDetail, reset]); - useEffect(() => { - const issueDetail = issues?.results.find((issue) => issue.id === issueId); - setIssueDetail(issueDetail); - }, [issueId, issues]); - - const prevIssue = issues?.results[issues?.results.findIndex((issue) => issue.id === issueId) - 1]; - const nextIssue = issues?.results[issues?.results.findIndex((issue) => issue.id === issueId) + 1]; - - const subIssues = (issues && issues.results.filter((i) => i.parent === issueId)) ?? []; - const siblingIssues = - issueDetail && - issues?.results.filter((i) => i.parent === issueDetail.parent && i.id !== issueId); - const handleSubIssueRemove = (issueId: string) => { if (activeWorkspace && activeProject) { issuesServices @@ -215,19 +191,17 @@ const IssueDetail: NextPage = () => { } }; - console.log("Issue detail", issueDetail); - return ( - - { } > - - setDeleteIssueModal(false)} - isOpen={deleteIssueModal} - data={issueDetail} - /> - + {isOpen && ( + + )} + {isAddAsSubIssueOpen && ( + + )} {issueDetail && activeProject ? (
@@ -590,19 +563,10 @@ const IssueDetail: NextPage = () => { - + - + @@ -615,7 +579,6 @@ const IssueDetail: NextPage = () => { issueDetail={issueDetail} submitChanges={submitChanges} watch={watch} - setDeleteIssueModal={setDeleteIssueModal} />
diff --git a/apps/app/types/issues.d.ts b/apps/app/types/issues.d.ts index 2ffb77f2d..7e31282b2 100644 --- a/apps/app/types/issues.d.ts +++ b/apps/app/types/issues.d.ts @@ -72,6 +72,7 @@ export interface IIssue { blocked_issue_details: any[]; sprints: string | null; cycle: string | null; + cycle_detail: ICycle | null; issue_cycle: IIssueCycle; } diff --git a/apps/app/ui/Breadcrumbs/index.tsx b/apps/app/ui/Breadcrumbs/index.tsx index a485a21d2..c07808192 100644 --- a/apps/app/ui/Breadcrumbs/index.tsx +++ b/apps/app/ui/Breadcrumbs/index.tsx @@ -6,7 +6,7 @@ type BreadcrumbsProps = { children: any; }; -const Breadcrumbs: React.FC = ({ children }: BreadcrumbsProps) => { +const Breadcrumbs = ({ children }: BreadcrumbsProps) => { const router = useRouter(); return ( @@ -54,4 +54,6 @@ const BreadcrumbItem: React.FC = ({ title, link, icon }) => ); }; +Breadcrumbs.BreadcrumbItem = BreadcrumbItem; + export { Breadcrumbs, BreadcrumbItem };