├── .gitignore ├── authController.js ├── authRouter.js ├── config.json ├── helper └── db.js ├── index.js ├── middleware └── authMiddleware.js ├── package.json ├── postController.js ├── postsRouter.js └── readme.txt /.gitignore: -------------------------------------------------------------------------------- 1 | /package-lock.json -------------------------------------------------------------------------------- /authController.js: -------------------------------------------------------------------------------- 1 | const { validationResult } = require('express-validator') 2 | const db = require('./helper/db').connection; 3 | const bcrypt = require('bcrypt'); 4 | const jwt = require('jsonwebtoken'); 5 | 6 | class authController { 7 | async registration(req, res) { 8 | try { 9 | const errors = validationResult(req); 10 | if (!errors.isEmpty()) { 11 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 12 | } 13 | const {login, password, name} = req.body; 14 | db.query( 15 | `SELECT * INTO users WHERE login = ?`, 16 | [login], (err, result) => { 17 | if(result) return res.status(400).json({message: "User already registred"}) 18 | bcrypt.hash(password, 1, (err, hashpassword) => { 19 | db.query( 20 | `INSERT INTO users (login, passhash, name) VALUES (?, ?, ?)`, 21 | [login, hashpassword, name], (err, result) => { 22 | if(!err) return res.status(200).json({message: "User registration successful"}) 23 | res.status(400).json({message: "User registration failed"}) 24 | } 25 | ) 26 | }) 27 | } 28 | ) 29 | } catch (e) { 30 | console.log(e) 31 | res.status(400).json({message: 'Registration error'}) 32 | } 33 | } 34 | 35 | async login(req, res) { 36 | try { 37 | const errors = validationResult(req); 38 | if (!errors.isEmpty()) { 39 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 40 | } 41 | const {login, password} = req.body; 42 | db.query( 43 | `SELECT * FROM users WHERE login = ?`, 44 | [login], (err, result) => { 45 | if(!result) return res.status(400).json({message: "User not found"}) 46 | bcrypt.compare(password, result[0].passhash, (err, result) => { 47 | if(result) { 48 | let token = jwt.sign({id: result[0]}, "MAJESTIC", {expiresIn: "24h"}) 49 | return res.json({token: token}) 50 | } 51 | res.status(400).json({message: "Incorrect password"}) 52 | }) 53 | }) 54 | } catch (e) { 55 | console.log(e) 56 | res.status(400).json({message: 'Login error'}) 57 | } 58 | } 59 | } 60 | 61 | module.exports = new authController() 62 | -------------------------------------------------------------------------------- /authRouter.js: -------------------------------------------------------------------------------- 1 | const Router = require('express') 2 | const router = new Router() 3 | const authController = require('./authController') 4 | const {check} = require("express-validator") 5 | 6 | router.post('/registration', [ 7 | check('login', "Логин пользователя не может быть пустым").notEmpty(), 8 | check('password', "Пароль должен быть больше 5 и меньше 10 символов").isLength({min:5, max:15}), 9 | check('name', "Имя пользователя не может быть пустым").notEmpty() 10 | ], authController.registration) 11 | router.post('/login', [ 12 | check('login', "Логин пользователя не может быть пустым").notEmpty(), 13 | check('password', "Пароль должен быть больше 5 и меньше 10 символов").isLength({min:5, max:15}) 14 | ], authController.login) 15 | 16 | module.exports = router 17 | -------------------------------------------------------------------------------- /config.json: -------------------------------------------------------------------------------- 1 | { 2 | "host": "localhost", 3 | "user": "mysql", 4 | "password":"" 5 | } -------------------------------------------------------------------------------- /helper/db.js: -------------------------------------------------------------------------------- 1 | const config = require('../config.json') 2 | 3 | const mysql2 = require('mysql2') 4 | 5 | let db = exports 6 | 7 | db.connection = mysql2.createConnection({ 8 | host: `${config.host}`, 9 | user: `${config.user}`, 10 | password: `${config.password}` 11 | }); 12 | 13 | function initBase() { 14 | try{ 15 | db.connection.query(`CREATE DATABASE IF NOT EXISTS api;`, (err, result) => {if(err) return console.log(err)}) 16 | 17 | db.connection.query(`USE api`) 18 | 19 | db.connection.query(`CREATE TABLE IF NOT EXISTS users ( 20 | id INT auto_increment, 21 | login VARCHAR(255), 22 | passhash VARCHAR(255), 23 | name VARCHAR(255), 24 | primary key (id) 25 | );`, (err, result) => {if(err) return console.log(err)}) 26 | 27 | db.connection.query(`CREATE TABLE IF NOT EXISTS posts ( 28 | id INT auto_increment, 29 | title VARCHAR(255), 30 | content VARCHAR(255), 31 | timestamp VARCHAR(255), 32 | primary key (id) 33 | );`, (err, result) => {if(err) return console.log(err)}) 34 | } catch (err) { 35 | console.log(err) 36 | } 37 | } 38 | 39 | initBase() 40 | -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | const express = require('express') 2 | const authRouter = require('./authRouter') 3 | const postsRouter = require('./postsRouter') 4 | const PORT = process.env.PORT || 5000 5 | 6 | const app = express() 7 | 8 | app.use(express.json()) 9 | app.use("/auth", authRouter) 10 | app.use("/posts", postsRouter) 11 | 12 | const start = async () => { 13 | try { 14 | app.listen(PORT, () => console.log(`server started on port ${PORT}`)) 15 | } catch (e) { 16 | console.log(e) 17 | } 18 | } 19 | 20 | start() 21 | 22 | -------------------------------------------------------------------------------- /middleware/authMiddleware.js: -------------------------------------------------------------------------------- 1 | const jwt = require(`jsonwebtoken`) 2 | 3 | module.exports = function (req, res, next) { 4 | if(req.method == "OPTIONS") next() 5 | 6 | try { 7 | const token = req.headers.authorization.split(" ")[1] 8 | if(!token) return res.status(403).json({message: "User not authenticated"}) 9 | 10 | const decoded = jwt.verify(token, `MAJESTIC`) 11 | req.user = decoded 12 | 13 | next() 14 | } catch(e) { 15 | return res.status(403).json({message: "User not authenticated"}) 16 | } 17 | } -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "profi_auth_nodejs", 3 | "version": "1.0.0", 4 | "description": "", 5 | "main": "index.js", 6 | "scripts": { 7 | "start": "nodemon index.js" 8 | }, 9 | "keywords": [], 10 | "author": "", 11 | "license": "ISC", 12 | "dependencies": { 13 | "bcrypt": "^5.0.1", 14 | "express": "^4.17.1", 15 | "express-validator": "^6.7.0", 16 | "jsonwebtoken": "^8.5.1", 17 | "mysql2": "^2.3.3", 18 | "nodemon": "^2.0.6" 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /postController.js: -------------------------------------------------------------------------------- 1 | const db = require('./helper/db').connection; 2 | const { validationResult } = require('express-validator') 3 | 4 | class postController { 5 | newPost(req, res) { 6 | try { 7 | const errors = validationResult(req); 8 | if (!errors.isEmpty()) { 9 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 10 | } 11 | const {title, content} = req.body; 12 | const timestamp = new Date() 13 | db.query( 14 | `INSERT INTO posts (title, content, timestamp) VALUES (?, ?, ?)`, 15 | [title, content, timestamp], (err, results) => { 16 | if(err) return res.status(400).json({message: "Something went wrong..."}) 17 | res.status(200).json({message: `Post created successfully at id ${results.insertId}`}) 18 | } 19 | ) 20 | } catch(e) { 21 | console.log(e) 22 | return res.status(400).json({message: "Post error"}) 23 | } 24 | } 25 | 26 | getById(req, res) { 27 | try { 28 | const errors = validationResult(req); 29 | if (!errors.isEmpty()) { 30 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 31 | } 32 | const { id } = req.body 33 | db.query( 34 | 'SELECT * FROM posts WHERE id = ?', 35 | [id], (err, results) => { 36 | if(!results[0]) return res.status(404).json({message: `Post with id ${id} not found`}) 37 | res.status(200).json(results[0]) 38 | } 39 | ) 40 | } catch(e) { 41 | console.log(e) 42 | return res.status(400).json({message: "Search Post error"}) 43 | } 44 | } 45 | 46 | getPosts(req, res) { 47 | try { 48 | const errors = validationResult(req); 49 | if (!errors.isEmpty()) { 50 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 51 | } 52 | db.query( 53 | `SELECT * FROM posts`, 54 | (err, results) => { 55 | let json = {} 56 | results.forEach(result => json[result.id] = { 57 | title: result.title, 58 | content: result.content, 59 | timestamp: result.timestamp 60 | }) 61 | res.status(200).json(json) 62 | } 63 | ) 64 | } catch(e) { 65 | console.log(e) 66 | return res.status(400).json({message: "Search Posts error"}) 67 | } 68 | } 69 | 70 | deleteById(req, res) { 71 | try { 72 | const errors = validationResult(req); 73 | if (!errors.isEmpty()) { 74 | return res.status(400).json({message: "Ошибка при регистрации", errors}); 75 | } 76 | const { id } = req.body 77 | db.query(`SELECT id FROM posts WHERE id = ?`, 78 | [id], (err, results) => { 79 | if(!results[0]) return res.status(404).json({message: `Post with id ${id} not found`}) 80 | db.query( 81 | 'DELETE FROM posts WHERE id = ?', 82 | [id], (err, results) => { 83 | if(err) return res.status(400).json({message: `Error`}) 84 | res.status(200).json({message: "Post deleted"}) 85 | } 86 | ) 87 | }) 88 | } catch(e) { 89 | console.log(e) 90 | return res.status(400).json({message: "Delete Post error"}) 91 | } 92 | } 93 | } 94 | 95 | module.exports = new postController() -------------------------------------------------------------------------------- /postsRouter.js: -------------------------------------------------------------------------------- 1 | const Router = require('express') 2 | const router = new Router() 3 | const postController = require('./postController') 4 | const authMiddleware = require("./middleware/authMiddleware") 5 | const {check} = require("express-validator") 6 | 7 | router.post('/newpost', [ 8 | check('title', "Заголовок не может быть пустым").notEmpty(), 9 | check('content', "Контент пользователя не может быть пустым").notEmpty() 10 | ], authMiddleware, postController.newPost) 11 | router.post('/getbyid', [ 12 | check('id', "id пользователя не может быть пустым").notEmpty(), 13 | ], authMiddleware, postController.getById) 14 | router.post('/deletebyid', [ 15 | check('id', "id пользователя не может быть пустым").notEmpty(), 16 | ], authMiddleware, postController.deleteById) 17 | router.get('/getposts', authMiddleware, postController.getPosts) 18 | 19 | module.exports = router 20 | -------------------------------------------------------------------------------- /readme.txt: -------------------------------------------------------------------------------- 1 | Кратко. 2 | 3 | 4 | В файле config.json надо ввести данные БД MySql 5 | Cервер стартует на http://localhost:5000 6 | 7 | Запросы: 8 | Метод POST 9 | 1)Регистрация - http://localhost:5000/auth/registration 10 | Принимает JSON объект: 11 | { 12 | "login": "qwerty", 13 | "password": "123456", 14 | "name": "qwerty" 15 | } 16 | 17 | 2)Авторизация - http://localhost:5000/auth/login 18 | Принимает JSON объект: 19 | { 20 | "login": "qwerty", 21 | "password": "123456" 22 | } 23 | 24 | 3)Сделать новй пост - http://localhost:5000/posts/newpost 25 | Принимает JSON объект: 26 | { 27 | "title": "qwerty", 28 | "content": "123456" 29 | } 30 | Требует токен авторизации, полученный в ходе авторизации. Вставленный таким образом - https://i.yapx.ru/QMaVS.png где token - тот самый токен(postman). 31 | 32 | 4)Получить пост по ид - http://localhost:5000/posts/getbyid 33 | Принимает JSON объект: 34 | { 35 | "id": 1 36 | } 37 | Требует токен авторизации, полученный в ходе авторизации. Вставленный таким образом - https://i.yapx.ru/QMaVS.png где token - тот самый токен(postman). 38 | 39 | 5)Удалить пост по ид - http://localhost:5000/posts/deletebyid 40 | Принимает JSON объект: 41 | { 42 | "id": 1 43 | } 44 | Требует токен авторизации, полученный в ходе авторизации. Вставленный таким образом - https://i.yapx.ru/QMaVS.png где token - тот самый токен(postman). 45 | Метод GET 46 | 6)Получить все посты - http://localhost:5000/posts/getposts 47 | Требует токен авторизации, полученный в ходе авторизации. Вставленный таким образом - https://i.yapx.ru/QMaVS.png где token - тот самый токен(postman). --------------------------------------------------------------------------------