/
viktorphp
/
front-socket
Обзор
Документация
Войти
/
viktorphp
/
front-socket
Код
Запросы
0
Задачи
Вики
Пакеты
0
Релизы
0
CI/CD
Аналитика
Безопасность
master
src/features/auth/model/actions.ts
196 строк
6 KB
Иванов Виктор Евгеньевич
[master]: поправить авторизацию и редиректы
19 май 2026, 03:10
19 май 2026, 03:10
822137c
Код
Авторство
О чём код?
'use server'; import { isAxiosError } from 'axios'; import { revalidatePath } from 'next/cache'; import { cookies } from 'next/headers'; import { ILoginRequest } from '@features/auth'; import { IUser } from '@shared/types'; import { authServices } from '../api'; const getActionErrorMessage = (error: unknown, fallback: string): string => { if (isAxiosError(error)) { const data = error.response?.data as { message?: string | string[] }; if (Array.isArray(data?.message)) { return data.message.join(', '); } if (typeof data?.message === 'string') { return data.message; } } if (error instanceof Error && error.message) { return error.message; } return fallback; }; export const loginSessionAction = async ( _prevState: { status: string | null; message: string | null; userData: IUser | null; }, formData: FormData ): Promise<{ status: string; message: string; userData: IUser | null }> => { try { const userData = new FormData(); if (formData.get('login')) { userData.append('login', formData.get('login') as string); } if (formData.get('password')) { userData.append('password', formData.get('password') as string); } if (formData.get('username')) { userData.append('username', formData.get('username') as string); } if (formData.get('email')) { userData.append('email', formData.get('email') as string); } const loginData: ILoginRequest = {}; // Собираем данные из FormData в объект, т.к. authServices.loginSession ожидает объект for (const [key, value] of formData.entries()) { if (typeof value === 'string') { loginData[key as keyof ILoginRequest] = value; } } const cookieStore = await cookies(); const response = await authServices.loginSession(loginData); // Пробрасываем cookie из ответа от бэкенда const setCookieHeader = response.headers['set-cookie']; if (setCookieHeader) { const cookieStrings = Array.isArray(setCookieHeader) ? setCookieHeader : [setCookieHeader]; cookieStrings.forEach((cookie) => { const [name, ...valueParts] = cookie.split(';')[0].split('='); if (name && valueParts.length > 0) { cookieStore.set(name.trim(), valueParts.join('=').trim()); } }); } // Добавляем ревалидацию layout чтобы Navigation перечитала cookie revalidatePath('/', 'layout'); return { status: 'success', message: 'Пользователь успешно авторизован', userData: response.data.user, }; } catch (error) { console.error('Ошибка авторизации', error); return { status: 'error', message: getActionErrorMessage(error, 'Ошибка авторизации пользователя'), userData: null, }; } }; export const logoutAction = async () => { try { await authServices.logout(); } catch (error) { console.error('Ошибка выхода', error); } // Очищаем cookie в браузере через Next.js сервер. const cookieStore = await cookies(); const allCookies = cookieStore.getAll(); allCookies.forEach((cookie) => { cookieStore.delete(cookie.name); }); // Ревалидируем все пути, чтобы сбросить кешированные данные пользователя. revalidatePath('/', 'layout'); }; export const registerAction = async ( _prevState: { status: string | null; message: string | null; userData: IUser | null; }, formData: FormData ): Promise<{ status: string; message: string; userData: IUser | null }> => { try { const userData = new FormData(); if (formData.get('login')) { userData.append('login', formData.get('login') as string); } if (formData.get('password')) { userData.append('password', formData.get('password') as string); } if (formData.get('username')) { userData.append('username', formData.get('username') as string); } if (formData.get('email')) { userData.append('email', formData.get('email') as string); } const loginData: ILoginRequest = {}; // Собираем данные из FormData в объект, т.к. authServices.loginSession ожидает объект for (const [key, value] of formData.entries()) { if (typeof value === 'string') { loginData[key as keyof ILoginRequest] = value; } } const cookieStore = await cookies(); const response = await authServices.register(loginData); // Пробрасываем cookie из ответа от бэкенда const setCookieHeader = response.headers['set-cookie']; if (setCookieHeader) { const cookieStrings = Array.isArray(setCookieHeader) ? setCookieHeader : [setCookieHeader]; cookieStrings.forEach((cookie) => { const [name, ...valueParts] = cookie.split(';')[0].split('='); if (name && valueParts.length > 0) { cookieStore.set(name.trim(), valueParts.join('=').trim()); } }); } // Добавляем ревалидацию layout чтобы Navigation перечитала cookie revalidatePath('/', 'layout'); return { status: 'success', message: 'Пользователь успешно зарегистрирован', userData: response.data.user, }; } catch (error) { console.error('Ошибка регистрации', error); return { status: 'error', message: getActionErrorMessage(error, 'Ошибка регистрации пользователя'), userData: null, }; } };