From 106b971920cf0911709a770a0a3ddd9bac6da363 Mon Sep 17 00:00:00 2001 From: Vamsi krishna Date: Tue, 31 Dec 2024 17:44:36 +0530 Subject: [PATCH 1/2] chore: removed refacotr changes:w --- apiserver/requirements/base.txt | 2 +- packages/ui/src/icons/transfer-icon.tsx | 2 +- .../cycles/list/cycle-list-item-action.tsx | 27 ++++++++++++-- .../cycles/transfer-issues-modal.tsx | 36 +++++++++++++------ .../issue-layouts/roots/cycle-layout-root.tsx | 6 +++- 5 files changed, 58 insertions(+), 15 deletions(-) diff --git a/apiserver/requirements/base.txt b/apiserver/requirements/base.txt index f7eb46a4a4f..a61832edbfc 100644 --- a/apiserver/requirements/base.txt +++ b/apiserver/requirements/base.txt @@ -6,7 +6,7 @@ Django==4.2.17 djangorestframework==3.15.2 # postgres psycopg==3.1.18 -psycopg-binary==3.1.18 +psycopg-binary==3.2.3 psycopg-c==3.1.18 dj-database-url==2.1.0 # redis diff --git a/packages/ui/src/icons/transfer-icon.tsx b/packages/ui/src/icons/transfer-icon.tsx index 9a5286f94d5..f762f9611e0 100644 --- a/packages/ui/src/icons/transfer-icon.tsx +++ b/packages/ui/src/icons/transfer-icon.tsx @@ -3,7 +3,7 @@ import * as React from "react"; import { ISvgIcons } from "./type"; export const TransferIcon: React.FC = ({ className = "fill-current", ...rest }) => ( - + ); diff --git a/web/core/components/cycles/list/cycle-list-item-action.tsx b/web/core/components/cycles/list/cycle-list-item-action.tsx index d83256b89bc..fca9ede6750 100644 --- a/web/core/components/cycles/list/cycle-list-item-action.tsx +++ b/web/core/components/cycles/list/cycle-list-item-action.tsx @@ -1,6 +1,6 @@ "use client"; -import React, { FC, MouseEvent, useEffect, useMemo } from "react"; +import React, { FC, MouseEvent, useEffect, useMemo, useState } from "react"; import { observer } from "mobx-react"; import { usePathname, useSearchParams } from "next/navigation"; import { Controller, useForm } from "react-hook-form"; @@ -15,11 +15,12 @@ import { LayersIcon, TOAST_TYPE, Tooltip, + TransferIcon, setPromiseToast, setToast, } from "@plane/ui"; // components -import { CycleQuickActions } from "@/components/cycles"; +import { CycleQuickActions, TransferIssuesModal } from "@/components/cycles"; import { DateRangeDropdown } from "@/components/dropdowns"; import { ButtonAvatars } from "@/components/dropdowns/member/avatar"; // constants @@ -32,6 +33,7 @@ import { generateQueryParams } from "@/helpers/router.helper"; import { useCycle, useEventTracker, useMember, useUserPermissions } from "@/hooks/store"; import { useAppRouter } from "@/hooks/use-app-router"; import { usePlatformOS } from "@/hooks/use-platform-os"; +// plane web // plane web constants import { EUserPermissions, EUserPermissionsLevel } from "@/plane-web/constants/user-permissions"; // services @@ -55,6 +57,8 @@ const defaultValues: Partial = { export const CycleListItemAction: FC = observer((props) => { const { workspaceSlug, projectId, cycleId, cycleDetails, parentRef, isActive = false } = props; + //states + const [transferIssuesModal, setTransferIssuesModal] = useState(false); // hooks const { isMobile } = usePlatformOS(); // router @@ -76,6 +80,8 @@ export const CycleListItemAction: FC = observer((props) => { // derived values const cycleStatus = cycleDetails.status ? (cycleDetails.status.toLocaleLowerCase() as TCycleGroups) : "draft"; const showIssueCount = useMemo(() => cycleStatus === "draft" || cycleStatus === "upcoming", [cycleStatus]); + const transferableIssuesCount = cycleDetails ? cycleDetails.total_issues - cycleDetails.completed_issues : 0; + const showTransferIssues = transferableIssuesCount > 0 && cycleStatus === "completed"; const isEditingAllowed = allowPermissions( [EUserPermissions.ADMIN, EUserPermissions.MEMBER], EUserPermissionsLevel.PROJECT, @@ -218,6 +224,11 @@ export const CycleListItemAction: FC = observer((props) => { return ( <> + setTransferIssuesModal(false)} + isOpen={transferIssuesModal} + cycleId={cycleId.toString()} + />
{ + setTransferIssuesModal(true); + }} + > + + Transfer {transferableIssuesCount} issues +
+ )} + {!isActive && ( void; + cycleId: string; }; export const TransferIssuesModal: React.FC = observer((props) => { - const { isOpen, handleClose } = props; + const { isOpen, handleClose, cycleId } = props; // states const [query, setQuery] = useState(""); // store hooks - const { currentProjectIncompleteCycleIds, getCycleById } = useCycle(); + const { currentProjectIncompleteCycleIds, getCycleById, fetchCycleDetails } = useCycle(); const { issues: { transferIssuesFromCycle }, } = useIssues(EIssuesStoreType.CYCLE); - const { workspaceSlug, projectId, cycleId } = useParams(); + const { workspaceSlug, projectId } = useParams(); - const transferIssue = async (payload: any) => { + const transferIssue = async (payload: { new_cycle_id: string }) => { if (!workspaceSlug || !projectId || !cycleId) return; - // TODO: import transferIssuesFromCycle from store await transferIssuesFromCycle(workspaceSlug.toString(), projectId.toString(), cycleId.toString(), payload) - .then(() => { + .then(async () => { setToast({ type: TOAST_TYPE.SUCCESS, title: "Success!", message: "Issues have been transferred successfully", }); + await getCycleDetails(payload.new_cycle_id); }) .catch(() => { setToast({ type: TOAST_TYPE.ERROR, title: "Error!", - message: "Issues cannot be transfer. Please try again.", + message: "Unable to transfer Issues. Please try again.", }); }); }; + /**To update issue counts in target cycle and current cycle */ + const getCycleDetails = async (newCycleId: string) => { + const cyclesFetch = [ + fetchCycleDetails(workspaceSlug.toString(), projectId.toString(), cycleId), + fetchCycleDetails(workspaceSlug.toString(), projectId.toString(), newCycleId), + ]; + await Promise.all(cyclesFetch).catch((error) => { + setToast({ + type: TOAST_TYPE.ERROR, + title: "Error", + message: error.error || "Unable to fetch cycle details", + }); + }); + }; + const filteredOptions = currentProjectIncompleteCycleIds?.filter((optionId) => { const cycleDetails = getCycleById(optionId); @@ -96,8 +112,8 @@ export const TransferIssuesModal: React.FC = observer((props) => {
-
- +
+

Transfer Issues