Após a criação do projeto e as configurações inicias vamos, finalmente, partir para o desenvolvimento das funcionalidades. Como primeira funcionalidade, pensei na implementação do login (registro e autenticação) com JWT (Json Web Token) para uma maior segurança do projeto.
Primeiro de tudo vamos configurar a migration Usuário, onde vão ser definidos os campos que vão ser criados na tabela.
'use strict';
/** @type {import('sequelize-cli').Migration} */
module.exports = {
async up (queryInterface, Sequelize) {
await queryInterface.createTable('Users', {
id: {
allowNull: false,
autoIncrement: true,
primaryKey: true,
type: Sequelize.INTEGER,
},
username: {
type: Sequelize.STRING,
allowNull: false,
},
email: {
type: Sequelize.STRING,
allowNull: false,
unique: true
},
password: {
type: Sequelize.STRING,
allowNull: false,
},
createdAt: {
allowNull: false,
type: Sequelize.DATE,
},
updatedAt: {
allowNull: false,
type: Sequelize.DATE,
}
})
},
async down (queryInterface, Sequelize) {
await queryInterface.dropTable('users');
}
};
Aqui é onde os campos da entidade são criados dentro do banco, sendo necessário informar o tipo do campo, se ele pode ser nulo, se ele vai se autocompletar, se é um campo único e tambem se ele é uma chave primária (usada para se relacionar com outras tabelas).
Com a migration criada, vamos partir para a criação da Model, onde vão ser definidos os tipos dos dados e também métodos para a alteração desses mesmos dados
const { Model } = require('sequelize');
const bcrypt = require('bcrypt');
module.exports = (sequelize, DataTypes) => {
class User extends Model {
static associate(models) {
}
}
User.init(
{
username: DataTypes.STRING,
email: DataTypes.STRING,
password: DataTypes.STRING,
},
{
sequelize,
modelName: 'User',
hooks: {
beforeCreate: async(user) => {
if(user.password) {
const salt = await bcrypt.genSalt(10);
user.password = await bcrypt.hash(user.password, salt);
}
},
},
}
);
return User;
}
Essa é uma estrutura básica de uma Model, onde eu defino os tipos de dados que cada campo pode aceitar e tambem crio uma função que encripta a senha antes de criar o usuário.
Logo depois da model, partimos para a criação do controller, parte que é responsável por receber e processar as requisições feitas através das rotas
const { User } = require('../models');
const bcrypt = require('bcrypt');
const jwt = require('jsonwebtoken');
module.exports = {
async register(req, res) {
try {
const { username, email, password } = req.body;
const user = await User.create({username, email, password});
res.status(201).json({user});
} catch (error) {
console.error(error);
req.status(500).json({ error: `Internal Server Error` });
}
},
async login(req, res) {
try {
const { email, password } = req.body;
const user = await User.findOne({ where: {email} });
if(!user) {
return res.status(404).json({ error: `Invalid email or password` });
}
const isPasswordValid = await bcrypt.compare(password, user.password);
if(!isPasswordValid) {
return res.status(404).json({ error: `Invalid email or password` });
}
const payload = {
user
};
const secretKey = 'yourSecretKey';
const options = {
expiresIn: '12h'
};
token = jwt.sign(payload, secretKey, options);
res.status(200).json({ success: `Successful Login`, user: user, token: token });
} catch (error) {
console.error(error);
res.status(500).json({ error: `Internal server error` });
}
},
}
E antes de finalizar vamos a criação do arquivo de rotas, nesse projeto eu optei por separar as rotas em diferentes arquivos, como ainda estamos no começo do projeto por agora teremos apenas o arquivo authRoutes.js
const express = require('express');
const router = express.Router();
const UserController = require('../controllers/UserController');
router.post('/register', UserController.register);
router.post('/login', UserController.login);
module.exports = router;
Agora para finalizar, criamos o arquivo principal do projeto, resolvi chamá-lo de index.js
.
const express = require('express');
const app = express();
const PORT = process.env.PORT || 3000;
app.use(express.json());
app.use('/auth', require('./routes/authRoutes'));
app.listen(PORT, () => {
console.log(`Server is running on port ${PORT}`);
})
Assim temos um login completamente funcional, que faz conexão com o banco de dados e tambem faz uso do JWT!
Até a próxima
Top comments (0)