首頁  >  文章  >  web前端  >  在前端和後端使用 JWT 進行身份驗證:使用 Node.js 和 ReactJS 實作(在 TypeScript 中)

在前端和後端使用 JWT 進行身份驗證:使用 Node.js 和 ReactJS 實作(在 TypeScript 中)

Barbara Streisand
Barbara Streisand原創
2024-11-01 15:18:02504瀏覽

Autenticação com JWT no Frontend e Backend: Implementando com Node.js e ReactJS (em TypeScript)

透過 JSON Web Token (JWT) 進行身份驗證廣泛用於保護 API 並確保只有授權使用者才能存取某些資料。在這篇文章中,我們將向您展示如何使用 Node.js 在後端配置 JWT,並使用 TypeScript 在 ReactJS 前端配置 JWT,從令牌生成到安全用戶會話管理。

使用 Node.js 配置後端

首先,讓我們使用 Node.js、Express 和 TypeScript 建立一個 API,用於產生和驗證 JWT 令牌。

步驟一:配置環境

建立一個新專案並安裝主要依賴項:

npm init -y
npm install express jsonwebtoken bcryptjs dotenv
npm install -D typescript @types/node @types/express @types/jsonwebtoken @types/bcryptjs ts-node

為 TypeScript 設定建立 tsconfig.json 檔案:

{
  "compilerOptions": {
    "target": "es6",
    "module": "commonjs",
    "outDir": "./dist",
    "strict": true,
    "esModuleInterop": true
  },
  "include": ["src/**/*.ts"],
  "exclude": ["node_modules"]
}

第 2 步:建構後端

建立一個簡單的結構,從 server.ts 檔案和路由資料夾開始來組織驗證路由。

伺服器.ts

import express, { Application } from 'express';
import dotenv from 'dotenv';
import authRoutes from './routes/authRoutes';

dotenv.config();

const app: Application = express();
app.use(express.json());

app.use('/api/auth', authRoutes);

const PORT = process.env.PORT || 5000;
app.listen(PORT, () => console.log(`Servidor rodando na porta ${PORT}`));

路線/authRoutes.ts

建立身份驗證路由檔案。這裡我們將有一個登入路由來驗證使用者並返回 JWT 令牌。

import express, { Request, Response } from 'express';
import jwt from 'jsonwebtoken';
import bcrypt from 'bcryptjs';

const router = express.Router();

// Simulação de banco de dados
const users = [{ username: 'usuario', password: 'senha123' }];

router.post('/login', async (req: Request, res: Response) => {
    const { username, password } = req.body;
    const user = users.find(u => u.username === username);

    if (!user || !(await bcrypt.compare(password, user.password))) {
        return res.status(401).json({ message: 'Credenciais inválidas' });
    }

    const token = jwt.sign({ username }, process.env.JWT_SECRET as string, { expiresIn: '1h' });
    res.json({ token });
});

export default router;

第 3 步:使用中介軟體保護路由

新增中間件來保護需要驗證的路由。

中間件/authMiddleware.ts

import { Request, Response, NextFunction } from 'express';
import jwt from 'jsonwebtoken';

interface JwtPayload {
    username: string;
}

export const authMiddleware = (req: Request, res: Response, next: NextFunction): void => {
    const token = req.headers['authorization'];
    if (!token) {
        res.status(403).json({ message: 'Token não fornecido' });
        return;
    }

    jwt.verify(token, process.env.JWT_SECRET as string, (err, decoded) => {
        if (err) {
            res.status(401).json({ message: 'Token inválido' });
            return;
        }
        req.user = decoded as JwtPayload;
        next();
    });
};

使用 ReactJS 配置前端

在前端,我們將使用 React 來處理身份驗證、發送憑證和儲存 JWT 令牌。

步驟1:設定登入介面

首先,建立一個 Login.tsx 元件來捕獲使用者的憑證並向後端發送登入請求。

登入.tsx

import React, { useState } from 'react';
import axios from 'axios';

const Login: React.FC = () => {
    const [username, setUsername] = useState<string>('');
    const [password, setPassword] = useState<string>('');
    const [error, setError] = useState<string>('');

    const handleLogin = async (e: React.FormEvent) => {
        e.preventDefault();
        try {
            const response = await axios.post('/api/auth/login', { username, password });
            localStorage.setItem('token', response.data.token);
            window.location.href = '/dashboard';
        } catch (err) {
            setError('Credenciais inválidas');
        }
    };

    return (
        <form onSubmit={handleLogin}>
            <input
                type="text"
                placeholder="Username"
                value={username}
                onChange={(e) => setUsername(e.target.value)}
            />
            <input
                type="password"
                placeholder="Password"
                value={password}
                onChange={(e) => setPassword(e.target.value)}
            />
            <button type="submit">Login</button>
            {error && <p>{error}</p>}
        </form>
    );
};

export default Login;

第 2 步:保護前端的路由

為受保護的路由建立一個函數,使用 JWT 令牌存取 API。

私有路由.tsx

import React from 'react';
import { Route, Redirect, RouteProps } from 'react-router-dom';

interface PrivateRouteProps extends RouteProps {
    component: React.ComponentType<any>;
}

const PrivateRoute: React.FC<PrivateRouteProps> = ({ component: Component, ...rest }) => (
    <Route
        {...rest}
        render={(props) =>
            localStorage.getItem('token') ? (
                <Component {...props} />
            ) : (
                <Redirect to="/login" />
            )
        }
    />
);

export default PrivateRoute;

步驟 3:在請求中發送 JWT 令牌

設定 axios 自動在受保護的請求中包含 JWT 令牌。

axiosConfig.ts

import axios from 'axios';

const token = localStorage.getItem('token');
if (token) {
    axios.defaults.headers.common['Authorization'] = token;
}

export default axios;

步驟 4:受保護路由的使用範例

現在,建立一個需要令牌才能存取的受保護頁面的範例。

儀表板.tsx

import React, { useEffect, useState } from 'react';
import axios from './axiosConfig';

const Dashboard: React.FC = () => {
    const [data, setData] = useState<string>('');

    useEffect(() => {
        const fetchData = async () => {
            try {
                const response = await axios.get('/api/protected');
                setData(response.data.message);
            } catch (error) {
                console.error(error);
            }
        };
        fetchData();
    }, []);

    return <h1>{data || 'Carregando...'}</h1>;
};

export default Dashboard;

結論

透過這些步驟,我們在 TypeScript 中為一個在後端使用 Node.js 並在前端使用 React 的專案設定了完整的 JWT 身份驗證。這種方法高度安全、高效,被廣泛用於保護現代應用程式。

以上是在前端和後端使用 JWT 進行身份驗證:使用 Node.js 和 ReactJS 實作(在 TypeScript 中)的詳細內容。更多資訊請關注PHP中文網其他相關文章!

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn