Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- В данной конфигурации используется один основной токен - JWT (JSON Web Token). Когда я говорю "Токен генерируется сервером авторизации", это означает следующее:
- В системе есть отдельный сервер авторизации (IdentityServer), который отвечает за аутентификацию пользователей и выдачу токенов.
- Когда пользователь успешно проходит аутентификацию, IdentityServer создает JWT токен, содержащий информацию о пользователе и его правах.
- Этот JWT токен затем используется клиентом (например, веб-приложением) для доступа к защищенным ресурсам API.
- API проверяет подлинность этого токена при каждом запросе, используя настройки, указанные в методе AddAuthentication.
- Таким образом, основной поток работы с токеном централизован и управляется сервером авторизации, что повышает безопасность и упрощает управление доступом в распределенной системе.
- Теперь напиши код с учетом этих данных.
- Понял вас. Учитывая предоставленную информацию, давайте реализуем подход, аналогичный C# коду, но для нашего TypeScript/Next.js приложения. Вот обновленная версия кода:
- Создадим файл auth-server.ts для имитации функциональности IdentityServer:
- import jwt from 'jsonwebtoken';
- const JWT_SECRET = process.env.JWT_SECRET!;
- const JWT_EXPIRY = '1h';
- export function generateToken(userId: string, claims: object) {
- return jwt.sign({ sub: userId, ...claims }, JWT_SECRET, { expiresIn: JWT_EXPIRY });
- }
- export function verifyToken(token: string) {
- try {
- return jwt.verify(token, JWT_SECRET);
- } catch {
- return null;
- }
- }
- Обновим функцию logInLucia в LoginForm.funcs.tsx:
- import { generateToken } from './auth-server';
- export async function logInLucia(userName: string, password: string): Promise<LoginLuciaResult> {
- const existingUser = await getUserByUserName(userName.toLowerCase());
- if (!existingUser || !await verify(existingUser.PasswordHash!, password, {...})) {
- return { isSuccess: false, message: "Incorrect username or password" };
- }
- const token = generateToken(existingUser.Id, {
- userName: existingUser.UserName,
- // Добавьте другие необходимые claims
- });
- return {
- isSuccess: true,
- user: JSON.parse(JSON.stringify(existingUser)) as User,
- token
- };
- }
- В компоненте LoginForm на клиенте:
- const onSubmit: SubmitHandler<Login> = useCallback(
- async (data) => {
- const result = await logInLucia(data.UserName, data.Password);
- if (!result.isSuccess) {
- setErrorMessage(result.message);
- return;
- }
- localStorage.setItem('token', result.token);
- authContext.setLoginState({
- loggedIn: true,
- userId: result.user!.Id,
- displayName: result.user!.UserName,
- });
- router.push(`/${routeConstants.list}?${resourceNameApiParam}=${resourceNames.Person}`);
- },
- [router, authContext]
- );
- Обновим api-client.ts для использования JWT:
- import { verifyToken } from './auth-server';
- @injectable()
- export class ApiClient {
- // ... существующий код ...
- #getHeaders(headers?: Headers, skipContentType = false) {
- const newHeaders = headers ? headers : new Headers();
- // ... существующий код ...
- const token = localStorage.getItem('token');
- if (token) {
- const decodedToken = verifyToken(token);
- if (decodedToken) {
- newHeaders.set('Authorization', `Bearer ${token}`);
- } else {
- // Токен недействителен, нужно перенаправить на страницу входа
- // Здесь можно использовать глобальное состояние или событие для обработки этой ситуации
- }
- }
- return newHeaders;
- }
- // ... остальной код ...
- }
- Создадим middleware для проверки JWT на сервере (например, в файле auth-middleware.ts):
- import { NextApiRequest, NextApiResponse } from 'next';
- import { verifyToken } from './auth-server';
- export function authMiddleware(handler: (req: NextApiRequest, res: NextApiResponse) => Promise<void>) {
- return async (req: NextApiRequest, res: NextApiResponse) => {
- const authHeader = req.headers.authorization;
- if (!authHeader || !authHeader.startsWith('Bearer ')) {
- return res.status(401).json({ message: 'Unauthorized' });
- }
- const token = authHeader.split(' ')[1];
- const decodedToken = verifyToken(token);
- if (!decodedToken) {
- return res.status(401).json({ message: 'Invalid token' });
- }
- // Добавляем информацию о пользователе в запрос
- (req as any).user = decodedToken;
- return handler(req, res);
- };
- }
- Этот код реализует централизованный подход к управлению токенами, аналогичный вашему C# коду с IdentityServer. JWT генерируется на сервере, используется клиентом для аутентификации и проверяется при каждом запросе к API.
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement