mirror of
https://github.com/makeplane/plane
synced 2024-06-14 14:31:34 +00:00
Merge pull request #63 from dakshesh14/main
fix: mutation on set new default button
This commit is contained in:
commit
50cb333646
@ -1,7 +1,8 @@
|
|||||||
import React, { useEffect, useState } from "react";
|
import React, { useEffect, useState } from "react";
|
||||||
// next
|
// next
|
||||||
import { useRouter } from "next/router";
|
|
||||||
import dynamic from "next/dynamic";
|
import dynamic from "next/dynamic";
|
||||||
|
import Link from "next/link";
|
||||||
|
import { useRouter } from "next/router";
|
||||||
// swr
|
// swr
|
||||||
import { mutate } from "swr";
|
import { mutate } from "swr";
|
||||||
// react hook form
|
// react hook form
|
||||||
@ -244,8 +245,6 @@ const CreateUpdateIssuesModal: React.FC<Props> = ({
|
|||||||
return () => setMostSimilarIssue(undefined);
|
return () => setMostSimilarIssue(undefined);
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
// console.log(watch("parent"));
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
{activeProject && (
|
{activeProject && (
|
||||||
@ -323,27 +322,30 @@ const CreateUpdateIssuesModal: React.FC<Props> = ({
|
|||||||
{mostSimilarIssue && (
|
{mostSimilarIssue && (
|
||||||
<div className="flex items-center gap-x-2">
|
<div className="flex items-center gap-x-2">
|
||||||
<p className="text-sm text-gray-500">
|
<p className="text-sm text-gray-500">
|
||||||
Did you mean{" "}
|
<Link
|
||||||
<button
|
href={`/projects/${activeProject?.id}/issues/${mostSimilarIssue}`}
|
||||||
type="button"
|
|
||||||
onClick={() => {
|
|
||||||
setMostSimilarIssue(undefined);
|
|
||||||
router.push(
|
|
||||||
`/projects/${activeProject?.id}/issues/${mostSimilarIssue}`
|
|
||||||
);
|
|
||||||
handleClose();
|
|
||||||
resetForm();
|
|
||||||
}}
|
|
||||||
>
|
>
|
||||||
|
<a target="_blank" type="button" className="inline text-left">
|
||||||
|
<span>Did you mean </span>
|
||||||
<span className="italic">
|
<span className="italic">
|
||||||
{
|
{
|
||||||
issues?.results.find(
|
issues?.results.find((i) => i.id === mostSimilarIssue)
|
||||||
(issue) => issue.id === mostSimilarIssue
|
?.project_detail.identifier
|
||||||
)?.name
|
|
||||||
}
|
}
|
||||||
|
-
|
||||||
|
{
|
||||||
|
issues?.results.find((i) => i.id === mostSimilarIssue)
|
||||||
|
?.sequence_id
|
||||||
|
}
|
||||||
|
:{" "}
|
||||||
|
{
|
||||||
|
issues?.results.find((i) => i.id === mostSimilarIssue)
|
||||||
|
?.name
|
||||||
|
}{" "}
|
||||||
</span>
|
</span>
|
||||||
</button>
|
|
||||||
?
|
?
|
||||||
|
</a>
|
||||||
|
</Link>{" "}
|
||||||
</p>
|
</p>
|
||||||
<button
|
<button
|
||||||
type="button"
|
type="button"
|
||||||
|
@ -216,3 +216,23 @@ export const createSimilarString = (str: string) => {
|
|||||||
|
|
||||||
return shuffled;
|
return shuffled;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const getRandomEmoji = () => {
|
||||||
|
const emojis = [
|
||||||
|
"8986",
|
||||||
|
"9200",
|
||||||
|
"128204",
|
||||||
|
"127773",
|
||||||
|
"127891",
|
||||||
|
"127947",
|
||||||
|
"128076",
|
||||||
|
"128077",
|
||||||
|
"128187",
|
||||||
|
"128188",
|
||||||
|
"128512",
|
||||||
|
"128522",
|
||||||
|
"128578",
|
||||||
|
];
|
||||||
|
|
||||||
|
return emojis[Math.floor(Math.random() * emojis.length)];
|
||||||
|
};
|
||||||
|
@ -1,3 +1,5 @@
|
|||||||
|
import type { IIssue, NestedKeyOf } from "types";
|
||||||
|
|
||||||
export const PRIORITIES = ["urgent", "high", "medium", "low"];
|
export const PRIORITIES = ["urgent", "high", "medium", "low"];
|
||||||
|
|
||||||
export const ROLE = {
|
export const ROLE = {
|
||||||
@ -16,3 +18,36 @@ export const GROUP_CHOICES = {
|
|||||||
completed: "Completed",
|
completed: "Completed",
|
||||||
cancelled: "Cancelled",
|
cancelled: "Cancelled",
|
||||||
};
|
};
|
||||||
|
|
||||||
|
export const groupByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> | null }> = [
|
||||||
|
{ name: "State", key: "state_detail.name" },
|
||||||
|
{ name: "Priority", key: "priority" },
|
||||||
|
// { name: "Cycle", key: "issue_cycle.cycle_detail.name" },
|
||||||
|
{ name: "Created By", key: "created_by" },
|
||||||
|
{ name: "None", key: null },
|
||||||
|
];
|
||||||
|
|
||||||
|
export const orderByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> | null }> = [
|
||||||
|
{ name: "Last created", key: "created_at" },
|
||||||
|
{ name: "Last updated", key: "updated_at" },
|
||||||
|
{ name: "Priority", key: "priority" },
|
||||||
|
{ name: "None", key: null },
|
||||||
|
];
|
||||||
|
|
||||||
|
export const filterIssueOptions: Array<{
|
||||||
|
name: string;
|
||||||
|
key: "activeIssue" | "backlogIssue" | null;
|
||||||
|
}> = [
|
||||||
|
{
|
||||||
|
name: "All",
|
||||||
|
key: null,
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Active Issues",
|
||||||
|
key: "activeIssue",
|
||||||
|
},
|
||||||
|
{
|
||||||
|
name: "Backlog Issues",
|
||||||
|
key: "backlogIssue",
|
||||||
|
},
|
||||||
|
];
|
||||||
|
@ -258,8 +258,10 @@ export const ThemeContextProvider: React.FC<{ children: React.ReactNode }> = ({
|
|||||||
|
|
||||||
const setNewDefaultView = useCallback(() => {
|
const setNewDefaultView = useCallback(() => {
|
||||||
if (!activeWorkspace || !activeProject) return;
|
if (!activeWorkspace || !activeProject) return;
|
||||||
setNewDefault(activeWorkspace.slug, activeProject.id, state);
|
setNewDefault(activeWorkspace.slug, activeProject.id, state).then(() => {
|
||||||
}, [activeProject, activeWorkspace, state]);
|
mutateMyViewProps();
|
||||||
|
});
|
||||||
|
}, [activeProject, activeWorkspace, state, mutateMyViewProps]);
|
||||||
|
|
||||||
const resetToDefault = useCallback(() => {
|
const resetToDefault = useCallback(() => {
|
||||||
dispatch({
|
dispatch({
|
||||||
@ -267,12 +269,8 @@ export const ThemeContextProvider: React.FC<{ children: React.ReactNode }> = ({
|
|||||||
payload: myViewProps?.default_props,
|
payload: myViewProps?.default_props,
|
||||||
});
|
});
|
||||||
if (!activeWorkspace || !activeProject) return;
|
if (!activeWorkspace || !activeProject) return;
|
||||||
saveDataToServer(activeWorkspace.slug, activeProject.id, myViewProps?.default_props).then(
|
saveDataToServer(activeWorkspace.slug, activeProject.id, myViewProps?.default_props);
|
||||||
() => {
|
}, [activeProject, activeWorkspace, myViewProps]);
|
||||||
mutateMyViewProps();
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}, [activeProject, activeWorkspace, myViewProps, mutateMyViewProps]);
|
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
dispatch({
|
dispatch({
|
||||||
|
@ -14,6 +14,8 @@ import CyclesBoardView from "components/project/cycles/board-view";
|
|||||||
import CreateUpdateIssuesModal from "components/project/issues/create-update-issue-modal";
|
import CreateUpdateIssuesModal from "components/project/issues/create-update-issue-modal";
|
||||||
import CycleIssuesListModal from "components/project/cycles/cycle-issues-list-modal";
|
import CycleIssuesListModal from "components/project/cycles/cycle-issues-list-modal";
|
||||||
import ConfirmIssueDeletion from "components/project/issues/confirm-issue-deletion";
|
import ConfirmIssueDeletion from "components/project/issues/confirm-issue-deletion";
|
||||||
|
// constants
|
||||||
|
import { filterIssueOptions, groupByOptions, orderByOptions } from "constants/";
|
||||||
// services
|
// services
|
||||||
import issuesServices from "lib/services/issues.service";
|
import issuesServices from "lib/services/issues.service";
|
||||||
import cycleServices from "lib/services/cycles.service";
|
import cycleServices from "lib/services/cycles.service";
|
||||||
@ -36,37 +38,6 @@ import { CYCLE_ISSUES, PROJECT_MEMBERS } from "constants/fetch-keys";
|
|||||||
// common
|
// common
|
||||||
import { classNames, replaceUnderscoreIfSnakeCase } from "constants/common";
|
import { classNames, replaceUnderscoreIfSnakeCase } from "constants/common";
|
||||||
|
|
||||||
const groupByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> | null }> = [
|
|
||||||
{ name: "State", key: "state_detail.name" },
|
|
||||||
{ name: "Priority", key: "priority" },
|
|
||||||
{ name: "Created By", key: "created_by" },
|
|
||||||
{ name: "None", key: null },
|
|
||||||
];
|
|
||||||
|
|
||||||
const orderByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> }> = [
|
|
||||||
{ name: "Last created", key: "created_at" },
|
|
||||||
{ name: "Last updated", key: "updated_at" },
|
|
||||||
{ name: "Priority", key: "priority" },
|
|
||||||
];
|
|
||||||
|
|
||||||
const filterIssueOptions: Array<{
|
|
||||||
name: string;
|
|
||||||
key: "activeIssue" | "backlogIssue" | null;
|
|
||||||
}> = [
|
|
||||||
{
|
|
||||||
name: "All",
|
|
||||||
key: null,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "Active Issues",
|
|
||||||
key: "activeIssue",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "Backlog Issues",
|
|
||||||
key: "backlogIssue",
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
const SingleCycle: React.FC = () => {
|
const SingleCycle: React.FC = () => {
|
||||||
const [isIssueModalOpen, setIsIssueModalOpen] = useState(false);
|
const [isIssueModalOpen, setIsIssueModalOpen] = useState(false);
|
||||||
const [selectedIssues, setSelectedIssues] = useState<SelectIssue>();
|
const [selectedIssues, setSelectedIssues] = useState<SelectIssue>();
|
||||||
|
@ -17,6 +17,8 @@ import useIssuesProperties from "lib/hooks/useIssuesProperties";
|
|||||||
import { PROJECT_MEMBERS } from "constants/api-routes";
|
import { PROJECT_MEMBERS } from "constants/api-routes";
|
||||||
// services
|
// services
|
||||||
import projectService from "lib/services/project.service";
|
import projectService from "lib/services/project.service";
|
||||||
|
// constants
|
||||||
|
import { filterIssueOptions, groupByOptions, orderByOptions } from "constants/";
|
||||||
// commons
|
// commons
|
||||||
import { classNames, replaceUnderscoreIfSnakeCase } from "constants/common";
|
import { classNames, replaceUnderscoreIfSnakeCase } from "constants/common";
|
||||||
// layouts
|
// layouts
|
||||||
@ -42,42 +44,10 @@ import {
|
|||||||
import { ChevronDownIcon, ListBulletIcon, RectangleStackIcon } from "@heroicons/react/24/outline";
|
import { ChevronDownIcon, ListBulletIcon, RectangleStackIcon } from "@heroicons/react/24/outline";
|
||||||
import { PlusIcon, Squares2X2Icon } from "@heroicons/react/20/solid";
|
import { PlusIcon, Squares2X2Icon } from "@heroicons/react/20/solid";
|
||||||
// types
|
// types
|
||||||
import type { IIssue, Properties, NestedKeyOf, IssueResponse } from "types";
|
import type { IIssue, Properties, IssueResponse } from "types";
|
||||||
// fetch-keys
|
// fetch-keys
|
||||||
import { PROJECT_ISSUES_LIST } from "constants/fetch-keys";
|
import { PROJECT_ISSUES_LIST } from "constants/fetch-keys";
|
||||||
|
|
||||||
const groupByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> | null }> = [
|
|
||||||
{ name: "State", key: "state_detail.name" },
|
|
||||||
{ name: "Priority", key: "priority" },
|
|
||||||
// { name: "Cycle", key: "issue_cycle.cycle_detail.name" },
|
|
||||||
{ name: "Created By", key: "created_by" },
|
|
||||||
{ name: "None", key: null },
|
|
||||||
];
|
|
||||||
|
|
||||||
const orderByOptions: Array<{ name: string; key: NestedKeyOf<IIssue> }> = [
|
|
||||||
{ name: "Last created", key: "created_at" },
|
|
||||||
{ name: "Last updated", key: "updated_at" },
|
|
||||||
{ name: "Priority", key: "priority" },
|
|
||||||
];
|
|
||||||
|
|
||||||
const filterIssueOptions: Array<{
|
|
||||||
name: string;
|
|
||||||
key: "activeIssue" | "backlogIssue" | null;
|
|
||||||
}> = [
|
|
||||||
{
|
|
||||||
name: "All",
|
|
||||||
key: null,
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "Active Issues",
|
|
||||||
key: "activeIssue",
|
|
||||||
},
|
|
||||||
{
|
|
||||||
name: "Backlog Issues",
|
|
||||||
key: "backlogIssue",
|
|
||||||
},
|
|
||||||
];
|
|
||||||
|
|
||||||
const ProjectIssues: NextPage = () => {
|
const ProjectIssues: NextPage = () => {
|
||||||
const [isOpen, setIsOpen] = useState(false);
|
const [isOpen, setIsOpen] = useState(false);
|
||||||
|
|
||||||
|
@ -3,6 +3,8 @@ import React, { useEffect, useState, useRef } from "react";
|
|||||||
import { Tab, Transition, Popover } from "@headlessui/react";
|
import { Tab, Transition, Popover } from "@headlessui/react";
|
||||||
// hooks
|
// hooks
|
||||||
import useOutsideClickDetector from "lib/hooks/useOutsideClickDetector";
|
import useOutsideClickDetector from "lib/hooks/useOutsideClickDetector";
|
||||||
|
// common
|
||||||
|
import { getRandomEmoji } from "constants/common";
|
||||||
// emoji
|
// emoji
|
||||||
import emojis from "./emojis.json";
|
import emojis from "./emojis.json";
|
||||||
// helpers
|
// helpers
|
||||||
@ -36,6 +38,10 @@ const EmojiIconPicker: React.FC<Props> = ({ label, value, onChange }) => {
|
|||||||
setIsOpen(false);
|
setIsOpen(false);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
useEffect(() => {
|
||||||
|
if (!value) onChange(getRandomEmoji());
|
||||||
|
}, [value, onChange]);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Popover className="relative" ref={ref}>
|
<Popover className="relative" ref={ref}>
|
||||||
<Popover.Button
|
<Popover.Button
|
||||||
|
Loading…
Reference in New Issue
Block a user