/** * Copyright (c) 2023-present Plane Software, Inc. and contributors * SPDX-License-Identifier: AGPL-3.0-only * See the LICENSE file for details. */ import { isNil } from "lodash-es"; // types import { EIconSize, ISSUE_PRIORITIES } from "@plane/constants"; import { CycleGroupIcon, CycleIcon, ModuleIcon, PriorityIcon, StateGroupIcon } from "@plane/propel/icons"; import type { GroupByColumnTypes, IGroupByColumn, TCycleGroups, IIssueDisplayProperties, TGroupedIssues, } from "@plane/types"; // ui import { Avatar } from "@plane/ui"; // components // constants // stores import type { ICycleStore } from "@/store/cycle.store"; import type { IIssueLabelStore } from "@/store/label.store"; import type { IIssueMemberStore } from "@/store/members.store"; import type { IIssueModuleStore } from "@/store/module.store"; import type { IStateStore } from "@/store/state.store"; export const HIGHLIGHT_CLASS = "highlight"; export const HIGHLIGHT_WITH_LINE = "highlight-with-line"; export const getGroupByColumns = ( groupBy: GroupByColumnTypes | null, cycle: ICycleStore, module: IIssueModuleStore, label: IIssueLabelStore, projectState: IStateStore, member: IIssueMemberStore, includeNone?: boolean ): IGroupByColumn[] | undefined => { switch (groupBy) { case "cycle": return getCycleColumns(cycle); case "module": return getModuleColumns(module); case "state": return getStateColumns(projectState); case "priority": return getPriorityColumns(); case "labels": return getLabelsColumns(label) as any; case "assignees": return getAssigneeColumns(member); case "created_by": return getCreatedByColumns(member) as any; default: if (includeNone) return [{ id: `All Issues`, name: `All work items`, payload: {}, icon: undefined }]; } }; const getCycleColumns = (cycleStore: ICycleStore): IGroupByColumn[] | undefined => { const { cycles } = cycleStore; if (!cycles) return; const cycleGroups: IGroupByColumn[] = []; cycles.map((cycle) => { if (cycle) { const cycleStatus = cycle?.status ? (cycle.status.toLocaleLowerCase() as TCycleGroups) : "draft"; cycleGroups.push({ id: cycle.id, name: cycle.name, icon: , payload: { cycle_id: cycle.id }, }); } }); cycleGroups.push({ id: "None", name: "None", icon: , payload: { cycle_id: null }, }); return cycleGroups; }; const getModuleColumns = (moduleStore: IIssueModuleStore): IGroupByColumn[] | undefined => { const { modules } = moduleStore; if (!modules) return; const moduleGroups: IGroupByColumn[] = []; modules.map((moduleInfo) => { if (moduleInfo) moduleGroups.push({ id: moduleInfo.id, name: moduleInfo.name, icon: , payload: { module_ids: [moduleInfo.id] }, }); }) as any; moduleGroups.push({ id: "None", name: "None", icon: , payload: { module_ids: [] }, }); return moduleGroups as any; }; const getStateColumns = (projectState: IStateStore): IGroupByColumn[] | undefined => { const { sortedStates } = projectState; if (!sortedStates) return; return sortedStates.map((state) => ({ id: state.id, name: state.name, icon: (
), payload: { state_id: state.id }, })) as any; }; const getPriorityColumns = () => { const priorities = ISSUE_PRIORITIES; return priorities.map((priority) => ({ id: priority.key, name: priority.title, icon: , payload: { priority: priority.key }, })); }; const getLabelsColumns = (label: IIssueLabelStore) => { const { labels: storeLabels } = label; if (!storeLabels) return; const labels = [...storeLabels, { id: "None", name: "None", color: "#666" }]; return labels.map((label) => ({ id: label.id, name: label.name, icon: (
), payload: label?.id === "None" ? {} : { label_ids: [label.id] }, })); }; const getAssigneeColumns = (member: IIssueMemberStore) => { const { members } = member; if (!members) return; const assigneeColumns: any = members.map((member) => ({ id: member.id, name: member?.member__display_name || "", icon: , payload: { assignee_ids: [member.id] }, })); assigneeColumns.push({ id: "None", name: "None", icon: , payload: {} }); return assigneeColumns; }; const getCreatedByColumns = (member: IIssueMemberStore) => { const { members } = member; if (!members) return; return members.map((member) => ({ id: member.id, name: member?.member__display_name || "", icon: , payload: {}, })); }; export const getDisplayPropertiesCount = ( displayProperties: IIssueDisplayProperties, ignoreFields?: (keyof IIssueDisplayProperties)[] ) => { const propertyKeys = Object.keys(displayProperties) as (keyof IIssueDisplayProperties)[]; let count = 0; for (const propertyKey of propertyKeys) { if (ignoreFields && ignoreFields.includes(propertyKey)) continue; if (displayProperties[propertyKey]) count++; } return count; }; export const getIssueBlockId = (issueId: string | undefined, groupId: string | undefined, subGroupId?: string) => `issue_${issueId}_${groupId}_${subGroupId}`; /** * returns empty Array if groupId is None * @param groupId * @returns */ export const getGroupId = (groupId: string) => { if (groupId === "None") return []; return [groupId]; }; /** * method that removes Null or undefined Keys from object * @param obj * @returns */ export const removeNillKeys = (obj: T) => Object.fromEntries(Object.entries(obj ?? {}).filter(([key, value]) => key && !isNil(value))); /** * This Method returns if the grouped values are subGrouped * @param groupedIssueIds * @returns */ export const isSubGrouped = (groupedIssueIds: TGroupedIssues) => { if (!groupedIssueIds || Array.isArray(groupedIssueIds)) { return false; } if (Array.isArray(groupedIssueIds[Object.keys(groupedIssueIds)[0]])) { return false; } return true; };