fix: project identifier check in project settings (#613)

This commit is contained in:
Aaryan Khandelwal 2023-03-30 17:48:03 +05:30 committed by GitHub
parent b65fa89cdb
commit 16abbe0b3e
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -1,4 +1,4 @@
import { useCallback, useEffect, useState } from "react"; import { useEffect, useState } from "react";
import { useRouter } from "next/router"; import { useRouter } from "next/router";
@ -13,7 +13,6 @@ import { requiredAdmin } from "lib/auth";
import AppLayout from "layouts/app-layout"; import AppLayout from "layouts/app-layout";
// services // services
import projectService from "services/project.service"; import projectService from "services/project.service";
import workspaceService from "services/workspace.service";
// components // components
import { DeleteProjectModal } from "components/project"; import { DeleteProjectModal } from "components/project";
import EmojiIconPicker from "components/emoji-icon-picker"; import EmojiIconPicker from "components/emoji-icon-picker";
@ -29,12 +28,10 @@ import {
SecondaryButton, SecondaryButton,
} from "components/ui"; } from "components/ui";
import { BreadcrumbItem, Breadcrumbs } from "components/breadcrumbs"; import { BreadcrumbItem, Breadcrumbs } from "components/breadcrumbs";
// helpers
import { debounce } from "helpers/common.helper";
// types // types
import type { NextPage, GetServerSidePropsContext } from "next"; import type { NextPage, GetServerSidePropsContext } from "next";
// fetch-keys // fetch-keys
import { PROJECTS_LIST, PROJECT_DETAILS, WORKSPACE_DETAILS } from "constants/fetch-keys"; import { PROJECTS_LIST, PROJECT_DETAILS } from "constants/fetch-keys";
// constants // constants
import { NETWORK_CHOICES } from "constants/project"; import { NETWORK_CHOICES } from "constants/project";
@ -45,9 +42,7 @@ const defaultValues: Partial<IProject> = {
network: 0, network: 0,
}; };
const GeneralSettings: NextPage<UserAuth> = (props) => { const GeneralSettings: NextPage<UserAuth> = ({ isMember, isOwner, isViewer, isGuest }) => {
const { isMember, isOwner, isViewer, isGuest } = props;
const [selectProject, setSelectedProject] = useState<string | null>(null); const [selectProject, setSelectedProject] = useState<string | null>(null);
const { setToastAlert } = useToast(); const { setToastAlert } = useToast();
@ -55,11 +50,6 @@ const GeneralSettings: NextPage<UserAuth> = (props) => {
const router = useRouter(); const router = useRouter();
const { workspaceSlug, projectId } = router.query; const { workspaceSlug, projectId } = router.query;
const { data: activeWorkspace } = useSWR(
workspaceSlug ? WORKSPACE_DETAILS(workspaceSlug as string) : null,
() => (workspaceSlug ? workspaceService.getWorkspace(workspaceSlug as string) : null)
);
const { data: projectDetails } = useSWR<IProject>( const { data: projectDetails } = useSWR<IProject>(
workspaceSlug && projectId ? PROJECT_DETAILS(projectId as string) : null, workspaceSlug && projectId ? PROJECT_DETAILS(projectId as string) : null,
workspaceSlug && projectId workspaceSlug && projectId
@ -78,15 +68,16 @@ const GeneralSettings: NextPage<UserAuth> = (props) => {
defaultValues, defaultValues,
}); });
const checkIdentifier = (slug: string, value: string) => { const checkIdentifier = (value: string) => {
projectService.checkProjectIdentifierAvailability(slug, value).then((response) => { if (!workspaceSlug) return;
projectService
.checkProjectIdentifierAvailability(workspaceSlug as string, value)
.then((response) => {
if (response.exists) setError("identifier", { message: "Identifier already exists" }); if (response.exists) setError("identifier", { message: "Identifier already exists" });
}); });
}; };
// eslint-disable-next-line react-hooks/exhaustive-deps
const checkIdentifierAvailability = useCallback(debounce(checkIdentifier, 1500), []);
useEffect(() => { useEffect(() => {
if (projectDetails) if (projectDetails)
reset({ reset({
@ -98,7 +89,7 @@ const GeneralSettings: NextPage<UserAuth> = (props) => {
}, [projectDetails, reset]); }, [projectDetails, reset]);
const onSubmit = async (formData: IProject) => { const onSubmit = async (formData: IProject) => {
if (!activeWorkspace || !projectDetails) return; if (!workspaceSlug || !projectDetails) return;
const payload: Partial<IProject> = { const payload: Partial<IProject> = {
name: formData.name, name: formData.name,
@ -111,22 +102,32 @@ const GeneralSettings: NextPage<UserAuth> = (props) => {
}; };
await projectService await projectService
.updateProject(activeWorkspace.slug, projectDetails.id, payload) .checkProjectIdentifierAvailability(workspaceSlug as string, payload.identifier ?? "")
.then(async (res) => {
if (res.exists) setError("identifier", { message: "Identifier already exists" });
else
await projectService
.updateProject(workspaceSlug as string, projectDetails.id, payload)
.then((res) => { .then((res) => {
mutate<IProject>( mutate<IProject>(
PROJECT_DETAILS(projectDetails.id), PROJECT_DETAILS(projectDetails.id),
(prevData) => ({ ...prevData, ...res }), (prevData) => ({ ...prevData, ...res }),
false false
); );
mutate(PROJECTS_LIST(activeWorkspace.slug)); mutate(PROJECTS_LIST(workspaceSlug as string));
setToastAlert({ setToastAlert({
title: "Success",
type: "success", type: "success",
title: "Success!",
message: "Project updated successfully", message: "Project updated successfully",
}); });
}) })
.catch((err) => { .catch(() => {
console.error(err); setToastAlert({
type: "error",
title: "Error!",
message: "Project could not be updated. Please try again.",
});
});
}); });
}; };
@ -233,10 +234,6 @@ const GeneralSettings: NextPage<UserAuth> = (props) => {
error={errors.identifier} error={errors.identifier}
register={register} register={register}
placeholder="Enter identifier" placeholder="Enter identifier"
onChange={(e: any) => {
if (!activeWorkspace || !e.target.value) return;
checkIdentifierAvailability(activeWorkspace.slug, e.target.value);
}}
validations={{ validations={{
required: "Identifier is required", required: "Identifier is required",
minLength: { minLength: {