plane/web/components/inbox/content/issue-root.tsx
guru_sainath ddb07dbe5f
[WEB-406] chore: project inbox revamp (#4141)
* chore: removed inbox id

* fix: inbox changes

* chore: resolved merge conflicts

* chore: inbox issue response changes

* chore: inbox issue filters

* fix: inbox implementation revamp

* fix: type fixes

* fix: pagination implementation

* fix: inbox fixes

* fix: pagination fixes

* fix: inbox Issues pagination fixes

* chore: triage state change

* fix: inbox fixes

* chore: filtering using boolean

* chore: total results in the pagination

* fix: inbox main content changes

* fix: develop pull fixes

* chore: resolved build erros in inbox issues

* dev: fix migrations

* chore: module, labels and assignee in inbox

* chore: inbox issue order by

* chore: inbox filters

* chore: inbox ui revamp

* chore: inbox type updated

* chore: updated filters

* chore: updated filter menmbers and date types in inbox issue filter

* chore: inbox issue filter updated

* chore: updated date filter in the inbox issue filter

* chore: moved the current tab state from local state to store

* chore: updated the filter and fetch request in the inbox issues

* chore: updated tab change handler

* chore: handled isEmpty in the issue filters query params

* chore: inbox sidebar updated

* chore: enabled create inbox issue in mobx

* chore: replaced the key inbox_status to status

* chore: inbox sidebar pagination

* chore: updated inbox issue services

* chore: inbox sidebar total count indicator

* chore: create inbox issue updated

* chore: updated inbox issue sidebar layout

* chore: rendering issue detail in inbox issue

* chore: inbox issue content updated

* chore: create inbox issue modal description improvement

* fix: updated delete functionality in inbox store

* chore: updated multiple inbox issue creation

* chore: handled loading, empty states and inbox user access permissions

* chore: updated rendering issues in the sidebar

* chore: inbox sidebar label improvement

* chore: handled empty states

* chore: disabled inbox empty state added

* chore: module, labels and assignee in list endpoint

* chore: labels in list endpoint

* chore: inboc issue serializer

* chore: representation in serializer

* chore: super function

* chore: inbox empty state updated

* chore: implemented applied filters

* chore: inbox empty state updated

* chore: update date formats in applied filters

* chore: inbox skeleton updated

* chore: ui changes in the siebar list item

* chore: removed the module and cycle ids

* chore: inbox sidebar tab

* chore: inbox actions

* chore: updated inbox issue header actions

* chore: updated inbox issue code cleanup

* chore: loader improvement

* chore: inbox sidebar improvement

* chore: inbox sidebar empty state flicker

* fix: inbox issue delete operation

* chore: inbox issue title and description update indicator added

* fix: resolved issue property rendering in initial load

* chore: inbox sidebar and detail header improvement

* fix: handling selected filter in the issue filters and applied filters

* chore: inbox issue detail improvement

* chore: inbox issue label updated

* chore: inbox issue sidebar improvement

* fix: handling issue description update when we move between the issues in inbox

* chore: removed inbox issue helpers file

* chore: boolean checked

* chore: resolved file change requests

---------

Co-authored-by: NarayanBavisetti <narayan3119@gmail.com>
Co-authored-by: sriram veeraghanta <veeraghanta.sriram@gmail.com>
Co-authored-by: pablohashescobar <nikhilschacko@gmail.com>
Co-authored-by: Anmol Singh Bhatia <anmolsinghbhatia@plane.so>
2024-04-08 19:11:47 +05:30

175 lines
5.5 KiB
TypeScript

import { Dispatch, SetStateAction, useEffect, useMemo } from "react";
import { observer } from "mobx-react";
import { useRouter } from "next/router";
import { TIssue } from "@plane/types";
import { Loader, TOAST_TYPE, setToast } from "@plane/ui";
// components
import { InboxIssueProperties } from "@/components/inbox/content";
import {
IssueDescriptionInput,
IssueTitleInput,
IssueActivity,
IssueReaction,
TIssueOperations,
} from "@/components/issues";
// hooks
import { useEventTracker, useProjectInbox, useUser } from "@/hooks/store";
import useReloadConfirmations from "@/hooks/use-reload-confirmation";
// store types
import { IInboxIssueStore } from "@/store/inbox/inbox-issue.store";
type Props = {
workspaceSlug: string;
projectId: string;
inboxIssue: IInboxIssueStore;
is_editable: boolean;
isSubmitting: "submitting" | "submitted" | "saved";
setIsSubmitting: Dispatch<SetStateAction<"submitting" | "submitted" | "saved">>;
};
export const InboxIssueMainContent: React.FC<Props> = observer((props) => {
const router = useRouter();
const { workspaceSlug, projectId, inboxIssue, is_editable, isSubmitting, setIsSubmitting } = props;
// hooks
const { currentUser } = useUser();
const { isLoading } = useProjectInbox();
const { setShowAlert } = useReloadConfirmations(isSubmitting === "submitting");
const { captureIssueEvent } = useEventTracker();
useEffect(() => {
if (isSubmitting === "submitted") {
setShowAlert(false);
setTimeout(async () => {
setIsSubmitting("saved");
}, 3000);
} else if (isSubmitting === "submitting") {
setShowAlert(true);
}
}, [isSubmitting, setShowAlert, setIsSubmitting]);
const issue = inboxIssue.issue;
if (!issue) return <></>;
const issueDescription =
issue.description_html !== undefined || issue.description_html !== null
? issue.description_html != ""
? issue.description_html
: "<p></p>"
: undefined;
const issueOperations: TIssueOperations = useMemo(
() => ({
// eslint-disable-next-line @typescript-eslint/no-unused-vars
fetch: async (workspaceSlug: string, projectId: string, issueId: string) => {
try {
return;
} catch (error) {
setToast({
title: "Issue fetch failed",
type: TOAST_TYPE.ERROR,
message: "Issue fetch failed",
});
}
},
// eslint-disable-next-line @typescript-eslint/no-unused-vars
remove: async (workspaceSlug: string, projectId: string, issueId: string) => {
try {
return;
} catch (error) {
setToast({
title: "Issue remove failed",
type: TOAST_TYPE.ERROR,
message: "Issue remove failed",
});
}
},
update: async (workspaceSlug: string, projectId: string, issueId: string, data: Partial<TIssue>) => {
try {
await inboxIssue.updateIssue(data);
captureIssueEvent({
eventName: "Inbox issue updated",
payload: { ...data, state: "SUCCESS", element: "Inbox" },
updates: {
changed_property: Object.keys(data).join(","),
change_details: Object.values(data).join(","),
},
path: router.asPath,
});
} catch (error) {
setToast({
title: "Issue update failed",
type: TOAST_TYPE.ERROR,
message: "Issue update failed",
});
captureIssueEvent({
eventName: "Inbox issue updated",
payload: { state: "SUCCESS", element: "Inbox" },
updates: {
changed_property: Object.keys(data).join(","),
change_details: Object.values(data).join(","),
},
path: router.asPath,
});
}
},
}),
[inboxIssue]
);
if (!issue?.project_id || !issue?.id) return <></>;
return (
<>
<div className="rounded-lg space-y-4">
<IssueTitleInput
workspaceSlug={workspaceSlug}
projectId={issue.project_id}
issueId={issue.id}
isSubmitting={isSubmitting}
setIsSubmitting={(value) => setIsSubmitting(value)}
issueOperations={issueOperations}
disabled={!is_editable}
value={issue.name}
/>
{isLoading ? (
<Loader className="h-[150px] space-y-2 overflow-hidden rounded-md border border-custom-border-200 p-2 py-2">
<Loader.Item width="100%" height="132px" />
</Loader>
) : (
<IssueDescriptionInput
workspaceSlug={workspaceSlug}
projectId={issue.project_id}
issueId={issue.id}
value={issueDescription}
initialValue={issueDescription}
disabled={!is_editable}
issueOperations={issueOperations}
setIsSubmitting={(value) => setIsSubmitting(value)}
/>
)}
{currentUser && (
<IssueReaction
workspaceSlug={workspaceSlug}
projectId={projectId}
issueId={issue.id}
currentUser={currentUser}
/>
)}
</div>
<InboxIssueProperties
workspaceSlug={workspaceSlug}
projectId={projectId}
issue={issue}
issueOperations={issueOperations}
is_editable={is_editable}
/>
<div className="pb-12">
<IssueActivity workspaceSlug={workspaceSlug} projectId={projectId} issueId={issue.id} />
</div>
</>
);
});