From fbb7f409ab89c9d0a083fb2f87e129e840df113c Mon Sep 17 00:00:00 2001 From: hamid zarghami Date: Mon, 5 May 2025 12:27:23 +0330 Subject: [PATCH] create support plan --- .env | 4 +- src/config/Pages.ts | 4 + src/langs/fa.json | 15 ++ src/pages/support/Create.tsx | 212 ++++++++++++++++++++ src/pages/support/List.tsx | 9 + src/pages/support/components/PlanItem.tsx | 50 +++++ src/pages/support/enum/SupportEnum.ts | 11 + src/pages/support/hooks/useSupportData.ts | 23 +++ src/pages/support/service/SupportService.ts | 17 ++ src/pages/support/types/SupportTypes.ts | 12 ++ src/router/Main.tsx | 4 + src/shared/SideBar.tsx | 12 +- 12 files changed, 370 insertions(+), 3 deletions(-) create mode 100644 src/pages/support/Create.tsx create mode 100644 src/pages/support/List.tsx create mode 100644 src/pages/support/components/PlanItem.tsx create mode 100644 src/pages/support/enum/SupportEnum.ts create mode 100644 src/pages/support/hooks/useSupportData.ts create mode 100644 src/pages/support/service/SupportService.ts create mode 100644 src/pages/support/types/SupportTypes.ts diff --git a/.env b/.env index 6a84cba..0b4d543 100644 --- a/.env +++ b/.env @@ -1,4 +1,4 @@ VITE_TOKEN_NAME = 'admin_token' VITE_REFRESH_TOKEN_NAME = 'admin_refresh_token' -VITE_BASE_URL = 'https://api.danakcorp.com' -# VITE_BASE_URL = 'http://192.168.1.117:4000' \ No newline at end of file +# VITE_BASE_URL = 'https://api.danakcorp.com' +VITE_BASE_URL = 'http://192.168.1.117:4000' \ No newline at end of file diff --git a/src/config/Pages.ts b/src/config/Pages.ts index 93585a2..46cdef6 100644 --- a/src/config/Pages.ts +++ b/src/config/Pages.ts @@ -106,4 +106,8 @@ export const Pages = { payment: { list: "/payments/list", }, + support: { + create: "/support/create", + list: "/support/list", + }, }; diff --git a/src/langs/fa.json b/src/langs/fa.json index 7bec43a..4a35c3a 100644 --- a/src/langs/fa.json +++ b/src/langs/fa.json @@ -763,5 +763,20 @@ "accept_confrim": "آیا از تایید این پرداخت مطمئن هستید؟", "reject_comment_error": "لطفا دلیل رد پرداخت را وارد کنید", "receip_image": "تصویر فیش واریزی" + }, + "support": { + "support_plan": "پلن پشتیبانی", + "support_plan_list": "لیست پلن پشتیبانی", + "support_plan_create": "ایجاد پلن پشتیبانی", + "support_plan_edit": "ویرایش پلن پشتیبانی", + "learning_docs": "راهنما و مستندات آموزشی", + "ticket_support": "ارسال تیکت", + "response_time": "زمان پاسخگویی به تیکت", + "phone_support": "پاسخگویی تلفنی", + "backup_version": "نسخه بکاپ", + "technical_expert_access": "دسترسی به متخصصین فنی", + "on_site_support": "پشتیبانی در محل", + "on_site_training": "آموزش در محل", + "ticket_limit": "ظرفیت ارسال تیکت" } } diff --git a/src/pages/support/Create.tsx b/src/pages/support/Create.tsx new file mode 100644 index 0000000..7b29220 --- /dev/null +++ b/src/pages/support/Create.tsx @@ -0,0 +1,212 @@ +import { FC, useState } from 'react' +import Input from '../../components/Input' +import SwitchComponent from '../../components/Switch' +import Textarea from '../../components/Textarea' +import Button from '../../components/Button' +import { SupportPlanFeatureKey } from './enum/SupportEnum' +import { useTranslation } from 'react-i18next' +import PlanItem from './components/PlanItem' +import { useFormik } from 'formik' +import { CreatePlanType } from './types/SupportTypes' +import * as Yup from 'yup' +import Select from '../../components/Select' +import { useCreateSupport } from './hooks/useSupportData' +import { toast } from 'react-toastify' +import { ErrorType } from '../../helpers/types' +import { useNavigate } from 'react-router-dom' +import { Pages } from '../../config/Pages' +interface PlanFeature { + featureKey: string; + featureValue: string | boolean; + featureType: 'boolean' | 'text'; + isEnabled: boolean; +} + +const CreatePlan: FC = () => { + + const navigate = useNavigate() + const { t } = useTranslation('global') + const createSupport = useCreateSupport() + const [features, setFeatures] = useState( + Object.values(SupportPlanFeatureKey).map(key => ({ + featureKey: key, + featureValue: true, + featureType: 'boolean', + isEnabled: true + })) + ) + + const handleFeatureChange = (id: string, value: string | boolean, isEnabled: boolean) => { + setFeatures(prevFeatures => + prevFeatures.map(feature => + feature.featureKey === id ? { ...feature, featureValue: value, isEnabled } : feature + ) + ) + } + + const handleFeatureTypeChange = (id: string, type: 'boolean' | 'text') => { + setFeatures(prevFeatures => + prevFeatures.map(feature => + feature.featureKey === id ? { + ...feature, + featureType: type, + featureValue: type === 'boolean' ? true : '', + isEnabled: type === 'boolean' ? true : false + } : feature + ) + ) + } + + const prepareFeaturesForSubmission = (features: PlanFeature[]) => { + return features.map(feature => { + if (feature.featureType === 'boolean') { + return { + featureKey: feature.featureKey, + featureValue: feature.isEnabled, + featureType: 'boolean', + } + } else { + return { + featureKey: feature.featureKey, + featureValue: feature.featureValue as string, + featureType: 'string', + } + } + }) + } + + const formik = useFormik({ + initialValues: { + name: '', + description: '', + price: 0, + duration: 0, + isActive: true, + features: [], + }, + validationSchema: Yup.object({ + name: Yup.string().required('نام پلن الزامی است'), + description: Yup.string().required('توضیحات پلن الزامی است'), + price: Yup.number().required('قیمت پلن الزامی است'), + duration: Yup.number().required('مدت پلن الزامی است'), + }), + onSubmit: (values) => { + values.price = Number(values.price) + values.duration = Number(values.duration) + const preparedFeatures = prepareFeaturesForSubmission(features) + const planData: CreatePlanType = { + ...values, + features: preparedFeatures.map(feature => ({ + featureKey: feature.featureKey, + featureValue: String(feature.featureValue), + featureType: feature.featureType as "string" | "boolean" + })) + } + createSupport.mutate(planData, { + onSuccess: () => { + toast.success('پلن با موفقیت ساخته شد') + navigate(Pages.support.list) + }, + onError: (error: ErrorType) => { + toast.error(error.response?.data?.error.message[0]) + } + }) + }, + }) + + return ( +
+
ساخت پلن
+ +
+
اطلاعات اصلی پلن
+
+
+ +
+ +
+ + + +
+ +
+