Introdução ao OAuth 2.0 e JWT em TypeScript
\n\nNo desenvolvimento web moderno, a autorização segura de usuários é a base de qualquer aplicação. Os dois padrões mais populares — OAuth 2.0 e JWT (JSON Web Token) — permitem implementar um sistema robusto de autenticação e controle de acesso. Neste artigo, vamos explorar como combinar essas tecnologias em TypeScript para criar uma API segura do zero.
\n\nEste artigo é destinado a desenvolvedores iniciantes que já conhecem os fundamentos do TypeScript e desejam entender como a autorização funciona na prática. Não vamos nos aprofundar em teorias complexas, mas sim focar em exemplos concretos de código.
\n\nO que é OAuth 2.0?
\nOAuth 2.0 é um protocolo de autorização que permite que aplicativos de terceiros obtenham acesso limitado aos recursos do usuário sem transmitir sua senha. Imagine que você queira entrar em um site usando o Google: você não fornece sua senha do Google ao site, apenas permite que ele obtenha seu e-mail e nome. Isso é OAuth 2.0.
\n\nO que é JWT?
\nJWT (JSON Web Token) é um formato de token compacto e autossuficiente que contém todas as informações necessárias sobre o usuário de forma criptografada. O token consiste em três partes: cabeçalho, payload (carga útil) e assinatura. Graças à assinatura, o servidor pode ter certeza de que o token não foi adulterado.
\n\n1. Configuração do projeto e instalação de dependências
\n\nPara começar, vamos criar um novo projeto em TypeScript. Abra o terminal e execute os seguintes comandos:
\n\nmkdir oauth-jwt-ts\ncd oauth-jwt-ts\nnpm init -y\nnpm install express jsonwebtoken bcrypt dotenv cors\nnpm install -D typescript ts-node @types/express @types/jsonwebtoken @types/bcrypt @types/cors @types/node nodemon\n\nCrie o arquivo tsconfig.json com a configuração básica:
{\n "compilerOptions": {\n "target": "ES2020",\n "module": "commonjs",\n "outDir": "./dist",\n "rootDir": "./src",\n "strict": true,\n "esModuleInterop": true,\n "skipLibCheck": true,\n "forceConsistentCasingInFileNames": true\n },\n "include": ["src/**/*"],\n "exclude": ["node_modules"]\n}\n\nA estrutura de pastas será assim:
\n- \n
src/— código-fonte \n src/controllers/— controladores \n src/middleware/— middleware para verificação de tokens \n src/models/— modelos de dados \n src/routes/— rotas \n .env— variáveis de ambiente \n
2. Implementação da autenticação básica com JWT
\n\nVamos começar criando um mecanismo simples de registro e login usando JWT. Crie o arquivo src/config.ts para armazenar constantes:
import dotenv from 'dotenv';\ndotenv.config();\n\nexport const config = {\n jwtSecret: process.env.JWT_SECRET || 'your-secret-key',\n jwtExpiresIn: process.env.JWT_EXPIRES_IN || '15m',\n refreshTokenExpiresIn: process.env.REFRESH_TOKEN_EXPIRES_IN || '7d',\n port: process.env.PORT || 3000\n};\n\nAgora, vamos criar o middleware para verificar o token JWT. Arquivo src/middleware/auth.middleware.ts:
import { Request, Response, NextFunction } from 'express';\nimport jwt from 'jsonwebtoken';\nimport { config } from '../config';\n\nexport interface AuthRequest extends Request {\n user?: { userId: string; email: string };\n}\n\nexport const authenticateToken = (req: AuthRequest, res: Response, next: NextFunction) => {\n const authHeader = req.headers['authorization'];\n const token = authHeader && authHeader.split(' ')[1]; // Bearer TOKEN\n\n if (!token) {\n return res.status(401).json({ message: 'Token não fornecido' });\n }\n\n try {\n const decoded = jwt.verify(token, config.jwtSecret) as { userId: string; email: string };\n req.user = decoded;\n next