From 38c75eae922335271cbf075acc1a0aa5e11c52b2 Mon Sep 17 00:00:00 2001 From: vincentlu <t1341870251@gmail.com> Date: 星期六, 08 二月 2025 16:16:02 +0800 Subject: [PATCH] # --- rsf-admin/src/page/settings/SecuritySettings.jsx | 245 +++++++++++++++++++++++++++++++++++++++++++++++++ rsf-admin/src/page/settings/BaseSettings.jsx | 3 rsf-admin/src/page/settings/index.jsx | 39 +++---- 3 files changed, 261 insertions(+), 26 deletions(-) diff --git a/rsf-admin/src/page/settings/BaseSettings.jsx b/rsf-admin/src/page/settings/BaseSettings.jsx index 51e48da..bb680be 100644 --- a/rsf-admin/src/page/settings/BaseSettings.jsx +++ b/rsf-admin/src/page/settings/BaseSettings.jsx @@ -24,7 +24,7 @@ const BaseSettings = (props) => { const translate = useTranslate(); const notify = useNotify(); - const { children, value, userInfo } = props; + const { children, userInfo } = props; const { control, handleSubmit, watch, setValue, getValues, formState: { isDirty } } = useForm(); const [loading, setLoading] = useState(false); @@ -68,7 +68,6 @@ return ( <Box - hidden={value !== 0} sx={{ p: 3, flex: 1, diff --git a/rsf-admin/src/page/settings/SecuritySettings.jsx b/rsf-admin/src/page/settings/SecuritySettings.jsx new file mode 100644 index 0000000..0943613 --- /dev/null +++ b/rsf-admin/src/page/settings/SecuritySettings.jsx @@ -0,0 +1,245 @@ +import React, { useState, useRef, useEffect, useMemo } from "react"; +import { + useTranslate, + useNotify, +} from 'react-admin'; +import { useForm, Controller, useWatch, FormProvider, useFormContext } from "react-hook-form"; +import { + Stack, + Grid, + Box, + Typography, + TextField, + Button, + FormControl, + InputLabel, + Select, + MenuItem, + FormHelperText, + CircularProgress, +} from '@mui/material'; +import { updateUserInfo } from '@/api/auth'; +import avatar from '/avatar.jpg' + +const SecuritySettings = (props) => { + const translate = useTranslate(); + const notify = useNotify(); + const { children, userInfo } = props; + + const { control, handleSubmit, watch, setValue, getValues, formState: { isDirty } } = useForm(); + const [loading, setLoading] = useState(false); + + useEffect(() => { + if (userInfo) { + setValue("username", userInfo.username || "", { shouldDirty: false }); + setValue("nickname", userInfo.nickname || "", { shouldDirty: false }); + setValue("sex", userInfo.sex ?? "", { shouldDirty: false }); + setValue("code", userInfo.code || "", { shouldDirty: false }); + setValue("phone", userInfo.phone || "", { shouldDirty: false }); + setValue("email", userInfo.email || "", { shouldDirty: false }); + setValue("realName", userInfo.realName || "", { shouldDirty: false }); + setValue("idCard", userInfo.idCard || "", { shouldDirty: false }); + } + }, [userInfo, setValue]) + + const onSubmit = (data) => { + setLoading(true); + updateUserInfo({ id: userInfo.id, ...data }).then(res => { + setLoading(false); + const { code, msg, data } = res; + if (code === 200) { + notify(msg, { type: 'success', messageArgs: { _: msg } }); + const userToPersist = { + avatar: avatar, + fullName: data.nickname, + id: data.id, + username: data.username + } + localStorage.setItem("user", JSON.stringify(userToPersist)); + } else { + notify(msg, { type: 'error', messageArgs: { _: msg } }); + } + }).catch((error) => { + setLoading(false); + notify(error.message, { type: 'error', messageArgs: { _: error.message } }); + console.error(error); + }) + } + + return ( + <Box + sx={{ + p: 3, + flex: 1, + overflow: 'auto', + }} + > + <form onSubmit={handleSubmit(onSubmit)} noValidate> + <Stack + direction='column' + spacing={3} + sx={{ + width: '30%', + pt: 1 + }} + > + <Controller + name="username" + control={control} + defaultValue="" + rules={{ required: true }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.username')} + variant="outlined" + autoComplete="off" + helperText={error ? translate('ra.validation.required') : ""} + disabled + /> + )} + /> + <Controller + name="nickname" + control={control} + defaultValue="" + rules={{ required: true }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.nickname')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? translate('ra.validation.required') : ""} + /> + )} + /> + <Controller + name="sex" + control={control} + defaultValue="" + rules={{ required: true }} + render={({ field, fieldState: { error } }) => ( + <FormControl fullWidth variant="outlined" error={!!error}> + <InputLabel>{translate('table.field.user.sex')}</InputLabel> + <Select + {...field} + label={translate('table.field.user.sex')} + > + <MenuItem value={0}> + <em>{translate('table.field.user.sexes.unknown')}</em> + </MenuItem> + <MenuItem value={1}>{translate('table.field.user.sexes.male')}</MenuItem> + <MenuItem value={2}>{translate('table.field.user.sexes.female')}</MenuItem> + </Select> + {error && <FormHelperText>{translate('ra.validation.required')}</FormHelperText>} + </FormControl> + )} + /> + <Controller + name="code" + control={control} + defaultValue="" + rules={{ required: false }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.code')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? translate('ra.validation.required') : ""} + /> + )} + /> + <Controller + name="phone" + control={control} + defaultValue="" + rules={{ required: false }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.phone')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? translate('ra.validation.required') : ""} + /> + )} + /> + <Controller + name="email" + control={control} + defaultValue="" + rules={{ + required: false, + pattern: { + value: /^[^\s@]+@[^\s@]+\.[^\s@]+$/, + message: translate("ra.validation.email"), + }, + }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.email')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? error.message : ""} + /> + )} + /> + <Controller + name="realName" + control={control} + defaultValue="" + rules={{ required: false }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.realName')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? translate('ra.validation.required') : ""} + /> + )} + /> + <Controller + name="idCard" + control={control} + defaultValue="" + rules={{ required: false }} + render={({ field, fieldState: { error } }) => ( + <TextField + {...field} + label={translate('table.field.user.idCard')} + variant="outlined" + autoComplete="off" + error={!!error} + helperText={error ? translate('ra.validation.required') : ""} + /> + )} + /> + <Button + type="submit" + variant="contained" + disabled={loading || !isDirty} + sx={{ + alignSelf: 'flex-start', + width: '120px' + }} + > + {loading && <CircularProgress size={25} thickness={2} />} + {translate('ra.action.save')} + </Button> + </Stack> + </form> + + </Box> + ) +} + +export default SecuritySettings; \ No newline at end of file diff --git a/rsf-admin/src/page/settings/index.jsx b/rsf-admin/src/page/settings/index.jsx index bc2364c..a5bde35 100644 --- a/rsf-admin/src/page/settings/index.jsx +++ b/rsf-admin/src/page/settings/index.jsx @@ -22,6 +22,7 @@ import { Stack, Grid, Box, Typography, Card, CardContent, Tabs, Tab } from '@mui/material'; import * as Common from '@/utils/common'; import BaseSettings from "./BaseSettings"; +import SecuritySettings from "./SecuritySettings" import { queryUserInfo } from '@/api/auth'; const Index = () => { @@ -85,34 +86,24 @@ aria-controls='vertical-tabpanel-1' /> </Tabs> - <BaseSettings - value={value} - userInfo={userInfo} - /> - <SecuritySettings - value={value} - /> + + {value === 0 && ( + <BaseSettings + value={value} + userInfo={userInfo} + /> + )} + {value === 1 && ( + <SecuritySettings + value={value} + userInfo={userInfo} + /> + )} + </Box> </CardContent> </Card> </> - ) -} - -const SecuritySettings = (props) => { - const { children, value, ...other } = props; - - return ( - <Box - hidden={value !== 1} - sx={{ p: 3 }} - {...other} - > - <Typography> - Security Settings - </Typography> - </Box> - ) } -- Gitblit v1.9.1