adminFront/src/pages/dashboard/Content/DiscountManagement/CreateDiscount.tsx

521 lines
25 KiB
TypeScript
Raw Normal View History

2023-08-31 12:46:34 +00:00
import {
2023-11-28 16:12:12 +00:00
Box,
Typography,
Button,
useTheme,
FormControl,
FormLabel,
RadioGroup,
FormControlLabel,
Radio,
InputLabel, TextField,
2023-08-31 12:46:34 +00:00
} from "@mui/material";
2023-05-24 16:27:10 +00:00
import MenuItem from "@mui/material/MenuItem";
import Select, { SelectChangeEvent } from "@mui/material/Select";
import { SERVICE_LIST, ServiceType } from "@root/model/tariff";
2023-08-31 12:46:34 +00:00
import {
resetPrivilegeArray,
usePrivilegeStore,
} from "@root/stores/privilegesStore";
2023-07-03 10:39:55 +00:00
import { addDiscount } from "@root/stores/discounts";
2023-05-24 16:27:10 +00:00
import { enqueueSnackbar } from "notistack";
import { DiscountType, discountTypes } from "@root/model/discount";
2023-07-03 10:39:55 +00:00
import { createDiscount } from "@root/api/discounts";
import usePrivileges from "@root/utils/hooks/usePrivileges";
import { Formik, Field, Form, FormikHelpers } from "formik";
import { mutate } from "swr";
interface Values {
discountNameField: string,
discountDescriptionField: string,
discountFactorField: string,
serviceType: string,
discountType: DiscountType,
purchasesAmountField: string,
cartPurchasesAmountField: string,
discountMinValueField: string,
privilegeIdField: string,
}
2023-05-24 16:27:10 +00:00
export default function CreateDiscount() {
2023-08-31 12:46:34 +00:00
const theme = useTheme();
const privileges = usePrivilegeStore((state) => state.privileges);
usePrivileges({ onNewPrivileges: resetPrivilegeArray });
2023-05-24 16:27:10 +00:00
const initialValues: Values = {
discountNameField: "",
discountDescriptionField: "",
discountFactorField: "",
serviceType: "",
discountType: "purchasesAmount",
purchasesAmountField: "",
cartPurchasesAmountField: "",
discountMinValueField: "",
privilegeIdField: "",
}
2023-11-28 16:12:12 +00:00
const handleCreateDiscount = async(
values: Values,
formikHelpers: FormikHelpers<Values>
2023-11-28 16:12:12 +00:00
) => {
console.log("работаю")
const purchasesAmount = Number(parseFloat(values.purchasesAmountField.replace(",", "."))) * 100;
2023-08-31 12:46:34 +00:00
const discountFactor =
(100 - parseFloat(values.discountFactorField.replace(",", "."))) / 100;
const cartPurchasesAmount = Number(parseFloat(
values.cartPurchasesAmountField.replace(",", ".")) * 100
2023-08-31 12:46:34 +00:00
);
const discountMinValue = Number(parseFloat(
values.discountMinValueField.replace(",", ".")) * 100
2023-08-31 12:46:34 +00:00
);
2023-05-24 16:27:10 +00:00
2023-08-31 12:46:34 +00:00
const [createdDiscountResponse, createdDiscountError] =
await createDiscount({
cartPurchasesAmount,
discountFactor,
discountMinValue,
purchasesAmount,
discountDescription: values.discountDescriptionField,
discountName: values.discountNameField,
2023-08-31 12:46:34 +00:00
startDate: new Date().toISOString(),
endDate: new Date(Date.now() + 1000 * 3600 * 24 * 30).toISOString(),
serviceType: values.serviceType,
discountType: values.discountType,
privilegeId: values.privilegeIdField,
2023-08-31 12:46:34 +00:00
});
2023-05-24 16:27:10 +00:00
2023-08-31 12:46:34 +00:00
if (createdDiscountError) {
console.log("Error creating discount", createdDiscountError);
2023-05-24 16:27:10 +00:00
2023-08-31 12:46:34 +00:00
return enqueueSnackbar(createdDiscountError);
2023-05-24 16:27:10 +00:00
}
2023-08-31 12:46:34 +00:00
if (createdDiscountResponse) {
mutate("discounts");
2023-08-31 12:46:34 +00:00
addDiscount(createdDiscountResponse);
}
}
2023-11-28 16:12:12 +00:00
const validateFulledFields = (values: Values) => {
const errors = {} as any;
if (values.discountNameField.length === 0) {
errors.discountNameField = 'Поле "Имя" пустое'
}
if (values.discountDescriptionField.length === 0) {
errors.discountDescriptionField = 'Поле "Описание" пустое'
}
if (((100 - parseFloat(values.discountFactorField.replace(",", "."))) / 100) < 0) {
errors.discountFactorField = "Процент скидки не может быть больше 100"
}
if (!isFinite(((100 - parseFloat(values.discountFactorField.replace(",", "."))) / 100))) {
errors.discountFactorField = 'Поле "Процент скидки" не число'
}
if (values.discountType === "privilege" && !values.privilegeIdField) {
2023-11-28 16:12:12 +00:00
errors.privilegeIdField = "Привилегия не выбрана"
}
if (values.discountType === "service" && !values.serviceType) {
errors.serviceType = "Сервис не выбран"
}
2023-11-28 16:12:12 +00:00
if (values.discountType === "purchasesAmount" && !isFinite(parseFloat(values.purchasesAmountField.replace(",", ".")))) {
errors.purchasesAmountField = 'Поле "Внесено больше" не число'
}
if (values.discountType === "cartPurchasesAmount" && !isFinite(parseFloat(values.cartPurchasesAmountField.replace(",", ".")))) {
errors.cartPurchasesAmountField = 'Поле "Объём в корзине" не число'
}
if (values.discountType === ("service" || "privilege") && !isFinite(parseFloat(values.discountMinValueField.replace(",", ".")))) {
errors.discountMinValueField = 'Поле "Минимальное значение" не число'
}
console.log(errors)
return errors;
}
2023-11-28 16:12:12 +00:00
return (
<Formik
initialValues={initialValues}
onSubmit={handleCreateDiscount}
validate={validateFulledFields}
>
{(props) => (
<Form style={{width: "100%", display: "flex", justifyContent: "center"}}>
<Box
sx={{
display: "flex",
flexDirection: "column",
justifyContent: "left",
alignItems: "left",
marginTop: "15px",
width: "100%",
padding: "16px",
maxWidth: "600px",
gap: "1em",
}}
>
<Field
as={TextField}
2023-11-28 16:12:12 +00:00
id="discount-name"
label="Название"
variant="filled"
2023-11-28 16:12:12 +00:00
name="discountNameField"
error={props.touched.discountNameField && !!props.errors.discountNameField}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.discountNameField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
2023-11-28 16:12:12 +00:00
/>
<Field
as={TextField}
id="discount-desc"
label="Описание"
variant="filled"
name="discountDescriptionField"
type="text"
error={props.touched.discountDescriptionField && !!props.errors.discountDescriptionField}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.discountDescriptionField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
/>
<Typography
variant="h4"
sx={{
width: "90%",
fontWeight: "normal",
color: theme.palette.grayDisabled.main,
paddingLeft: "10px",
}}
>
Условия:
</Typography>
<Field
as={TextField}
2023-11-28 16:12:12 +00:00
id="discount-factor"
label="Процент скидки"
variant="filled"
2023-11-28 16:12:12 +00:00
name="discountFactorField"
error={props.touched.discountFactorField && !!props.errors.discountFactorField}
value={props.values.discountFactorField}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.discountFactorField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
2023-11-28 16:12:12 +00:00
}}
/>
<FormControl>
<FormLabel
id="discount-type"
sx={{
color: "white",
"&.Mui-focused": {
color: "white",
},
}}
>
Тип скидки
</FormLabel>
<RadioGroup
row
aria-labelledby="discount-type"
name="discountType"
value={props.values.discountType}
onChange={(
event: React.ChangeEvent<HTMLInputElement>
) => {
props.setFieldValue("discountType", event.target.value as DiscountType);
}}
onBlur={props.handleBlur}
>
{Object.keys(discountTypes).map((type) => (
<FormControlLabel
key={type}
value={type}
control={<Radio color="secondary"/>}
label={discountTypes[type as DiscountType]}
/>
))}
</RadioGroup>
</FormControl>
{props.values.discountType === "purchasesAmount" && (
<TextField
2023-11-28 16:12:12 +00:00
id="discount-purchases"
name="purchasesAmountField"
variant="filled"
2023-11-28 16:12:12 +00:00
error={props.touched.purchasesAmountField && !!props.errors.purchasesAmountField}
label="Внесено больше"
onChange={(e) => {
props.setFieldValue("purchasesAmountField", e.target.value.replace(/[^\d]/g, ''))
}}
value={props.values.purchasesAmountField}
onBlur={props.handleBlur}
sx={{
marginTop: "15px",
}}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.purchasesAmountField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
2023-11-28 16:12:12 +00:00
/>
)}
{props.values.discountType === "cartPurchasesAmount" && (
<TextField
2023-11-28 16:12:12 +00:00
id="discount-cart-purchases"
label="Объем в корзине"
name="cartPurchasesAmountField"
variant="filled"
2023-11-28 16:12:12 +00:00
error={props.touched.cartPurchasesAmountField && !!props.errors.cartPurchasesAmountField}
onChange={(e) => {
props.setFieldValue("cartPurchasesAmountField", e.target.value.replace(/[^\d]/g, ''))
}}
value={props.values.cartPurchasesAmountField}
onBlur={props.handleBlur}
sx={{
marginTop: "15px",
}}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.cartPurchasesAmountField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
2023-11-28 16:12:12 +00:00
/>
)}
{props.values.discountType === "service" && (
<>
<Select
labelId="discount-service-label"
id="discount-service"
name="serviceType"
onBlur={props.handleBlur}
onChange={(e) => {
props.setFieldValue("serviceType", e.target.value as ServiceType);
}}
error={props.touched.serviceType && !!props.errors.serviceType}
sx={{
color: theme.palette.secondary.main,
borderColor: theme.palette.secondary.main,
"&.Mui-focused .MuiOutlinedInput-notchedOutline": {
borderColor: theme.palette.secondary.main,
},
".MuiSvgIcon-root ": {
fill: theme.palette.secondary.main,
},
}}
>
{SERVICE_LIST.map((service) => (
<MenuItem key={service.serviceKey} value={service.serviceKey}>
{service.displayName}
</MenuItem>
))}
</Select>
<TextField
2023-11-28 16:12:12 +00:00
id="discount-min-value"
name="discountMinValueField"
label="Минимальное значение"
onBlur={props.handleBlur}
variant="filled"
2023-11-28 16:12:12 +00:00
onChange={(e) => {
props.setFieldValue("discountMinValueField", e.target.value.replace(/[^\d]/g, ''))
}}
value={props.values.discountMinValueField}
error={props.touched.discountMinValueField && !!props.errors.discountMinValueField}
sx={{
marginTop: "15px",
}}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.discountMinValueField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
2023-11-28 16:12:12 +00:00
/>
</>
)}
{props.values.discountType === "privilege" && (
<>
<FormControl
fullWidth
sx={{
color: theme.palette.secondary.main,
"& .MuiInputLabel-outlined": {
color: theme.palette.secondary.main,
},
"& .MuiInputLabel-outlined.MuiInputLabel-shrink": {
color: theme.palette.secondary.main,
},
}}
>
<InputLabel
id="privilege-select-label"
sx={{
color: theme.palette.secondary.main,
fontSize: "16px",
lineHeight: "19px",
}}
>
Привилегия
</InputLabel>
<Select
labelId="privilege-select-label"
id="privilege-select"
name="privilegeIdField"
onBlur={props.handleBlur}
onChange={(e) => {
props.setFieldValue("privilegeIdField", e.target.value);
}}
error={props.touched.privilegeIdField && !!props.errors.privilegeIdField}
label="Привилегия"
sx={{
color: theme.palette.secondary.main,
borderColor: theme.palette.secondary.main,
"&.Mui-focused .MuiOutlinedInput-notchedOutline": {
borderColor: theme.palette.secondary.main,
},
".MuiSvgIcon-root ": {
fill: theme.palette.secondary.main,
},
}}
inputProps={{sx: {pt: "12px"}}}
>
{privileges.map((privilege, index) => (
<MenuItem key={index} value={privilege.privilegeId}>
{privilege.description}
</MenuItem>
))}
</Select>
</FormControl>
<TextField
2023-11-28 16:12:12 +00:00
id="discount-min-value"
name="discountMinValueField"
label="Минимальное значение"
onBlur={props.handleBlur}
variant="filled"
2023-11-28 16:12:12 +00:00
onChange={(e) => {
props.setFieldValue("discountMinValueField", e.target.value.replace(/[^\d]/g, ''))
}}
value={props.values.discountMinValueField}
error={props.touched.discountMinValueField && !!props.errors.discountMinValueField}
2023-11-28 16:12:12 +00:00
sx={{
marginTop: "15px",
}}
helperText={
<Typography sx={{fontSize: "12px", width: "200px"}}>
{props.errors.discountMinValueField}
</Typography>
}
InputProps={{
style: {
backgroundColor: theme.palette.content.main,
color: theme.palette.secondary.main,
}
}}
InputLabelProps={{
style: {
color: theme.palette.secondary.main
}
}}
2023-11-28 16:12:12 +00:00
/>
</>
)}
<Box
sx={{
width: "90%",
marginTop: "55px",
display: "flex",
flexDirection: "column",
justifyContent: "center",
alignItems: "center",
}}
>
<Button
variant="contained"
type='submit'
sx={{
backgroundColor: theme.palette.menu.main,
height: "52px",
fontWeight: "normal",
fontSize: "17px",
"&:hover": {
backgroundColor: theme.palette.grayMedium.main,
},
}}
>
Создать
</Button>
</Box>
</Box>
</Form>
)}
</Formik>
2023-11-28 16:12:12 +00:00
);
2023-07-03 23:13:50 +00:00
}