fix(Task 2): add error handling and sync state with user

- AuthMethodsSection: show Alert on fetchAuthMethodsFx failure
- AvatarSection: sync selectedStyle with user.avatarStyle via Select key
- ProfileSection: reset form defaultValues when user.displayName changes
This commit is contained in:
Kirill
2026-05-22 15:15:50 +05:00
parent fa276eb7f3
commit be9a9bad8e
3 changed files with 20 additions and 2 deletions
@@ -1,4 +1,5 @@
import { useCallback, useEffect, useState } from 'react' import { useCallback, useEffect, useState } from 'react'
import Alert from '@mui/material/Alert'
import Box from '@mui/material/Box' import Box from '@mui/material/Box'
import Button from '@mui/material/Button' import Button from '@mui/material/Button'
import Chip from '@mui/material/Chip' import Chip from '@mui/material/Chip'
@@ -24,6 +25,7 @@ export function AuthMethodsSection() {
const [authMethods, setAuthMethods] = useState<AuthMethod[]>([]) const [authMethods, setAuthMethods] = useState<AuthMethod[]>([])
const [showSetPassword, setShowSetPassword] = useState(false) const [showSetPassword, setShowSetPassword] = useState(false)
const [fetchError, setFetchError] = useState<string | null>(null)
const passwordForm = useForm<{ password: string; passwordConfirm: string }>({ const passwordForm = useForm<{ password: string; passwordConfirm: string }>({
defaultValues: { password: '', passwordConfirm: '' }, defaultValues: { password: '', passwordConfirm: '' },
}) })
@@ -31,8 +33,9 @@ export function AuthMethodsSection() {
useEffect(() => { useEffect(() => {
fetchAuthMethodsFx() fetchAuthMethodsFx()
.then(setAuthMethods) .then(setAuthMethods)
.catch(() => { .catch((err) => {
setAuthMethods([]) setAuthMethods([])
setFetchError(err?.message || 'Не удалось загрузить методы авторизации')
}) })
}, []) }, [])
@@ -81,6 +84,11 @@ export function AuthMethodsSection() {
<Typography variant="h6" gutterBottom> <Typography variant="h6" gutterBottom>
Методы входа Методы входа
</Typography> </Typography>
{fetchError && (
<Alert severity="error" sx={{ mb: 2 }}>
{fetchError}
</Alert>
)}
<Stack spacing={1}> <Stack spacing={1}>
{authMethods.map((m) => ( {authMethods.map((m) => (
<Stack key={m.type} direction="row" spacing={2} sx={{ alignItems: 'center' }}> <Stack key={m.type} direction="row" spacing={2} sx={{ alignItems: 'center' }}>
@@ -66,7 +66,12 @@ export function AvatarSection() {
<Stack direction="row" spacing={1} sx={{ flexWrap: 'wrap', gap: 1, mb: 1 }}> <Stack direction="row" spacing={1} sx={{ flexWrap: 'wrap', gap: 1, mb: 1 }}>
<FormControl size="small" sx={{ minWidth: 140 }}> <FormControl size="small" sx={{ minWidth: 140 }}>
<InputLabel>Стиль</InputLabel> <InputLabel>Стиль</InputLabel>
<Select value={selectedStyle} label="Стиль" onChange={(e) => setSelectedStyle(e.target.value)}> <Select
key={user?.avatarStyle || 'none'}
value={selectedStyle}
label="Стиль"
onChange={(e) => setSelectedStyle(e.target.value)}
>
{AVATAR_STYLES.map((s) => ( {AVATAR_STYLES.map((s) => (
<MenuItem key={s.id} value={s.id}> <MenuItem key={s.id} value={s.id}>
{s.label} {s.label}
@@ -1,3 +1,4 @@
import { useEffect } from 'react'
import Alert from '@mui/material/Alert' import Alert from '@mui/material/Alert'
import Box from '@mui/material/Box' import Box from '@mui/material/Box'
import Button from '@mui/material/Button' import Button from '@mui/material/Button'
@@ -18,6 +19,10 @@ export function ProfileSection() {
mode: 'onChange', mode: 'onChange',
}) })
useEffect(() => {
profileForm.reset({ displayName: user?.displayName ? String(user.displayName) : '' })
}, [user?.displayName, profileForm])
return ( return (
<Box> <Box>
<Typography variant="h6" gutterBottom> <Typography variant="h6" gutterBottom>