Skip to content

Commit

Permalink
feat(carrinhos): implementação do GET e POST da rota /carrinhos
Browse files Browse the repository at this point in the history
  • Loading branch information
PauloGoncalvesBH committed May 3, 2020
1 parent 3935ded commit b888561
Show file tree
Hide file tree
Showing 14 changed files with 254 additions and 8 deletions.
2 changes: 1 addition & 1 deletion bin/server.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ server.on('listening', onListening)
console.log(colors.blue.bold(`\nServeRest está em execução na porta ${port}`))
console.log(colors.cyan('Made with'), colors.red('♥'), colors.cyan('by'), colors.cyan.italic('npx paulogoncalves\n'))

open(`http://localhost:${port}/swagger`)
// open(`http://localhost:${port}/swagger`)

function normalizePort (val) {
const port = parseInt(val, 10)
Expand Down
2 changes: 1 addition & 1 deletion src/app.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ app.use(logger('dev'))
app.use('/login', require('./routes/login-route'))
app.use('/usuarios', require('./routes/usuarios-route'))
app.use('/produtos', require('./routes/produtos-route'))
// app.use('/carrinhos', require('./routes/turmas-route'))
app.use('/carrinhos', require('./routes/carrinhos-route'))

app.use((error, req, res, next) => {
const ocorreuErroNaValidacaoDoSchema = error.name === 'ValidationError'
Expand Down
11 changes: 11 additions & 0 deletions src/controllers/auth-controller.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,3 +19,14 @@ exports.checkAdm = async (req, res, next) => {
res.status(500).send({ message: constant.INTERNAL_ERROR, error })
}
}

exports.checkToken = async (req, res, next) => {
try {
if (!tokenValido(req.headers)) {
return res.status(401).send({ message: constant.TOKEN_INVALID })
}
next()
} catch (error) {
res.status(500).send({ message: constant.INTERNAL_ERROR, error })
}
}
96 changes: 96 additions & 0 deletions src/controllers/carrinhos-controller.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,96 @@
'use strict'

const authService = require('../services/auth-service')
const constant = require('../utils/constants')
const produtosService = require('../services/produtos-service')
const service = require('../services/carrinhos-service')
const usuariosService = require('../services/usuarios-service')

exports.get = async (req, res) => {
try {
const carrinhos = await service.getAll(req.query)
res.status(200).send({ quantidade: carrinhos.length, carrinhos })
} catch (error) {
res.status(500).send({ message: constant.INTERNAL_ERROR, error })
}
}

/*
X 1 carrinho por user
X validar idproduto
X verificar estoque do produto
X subtrair estoque do produto
X pegar e cadastrar idUsuario
X pegar e cadastrar preço do produto
*/

exports.post = async (req, res) => {
try {
const { email, password } = authService.verifyToken(req.headers.authorization)
const { _id } = await usuariosService.getDadosDoUsuario({ email, password })
const usuarioJaPossuiCarrinho = await service.existeCarrinho({ idusuario: _id })

if (usuarioJaPossuiCarrinho) {
return res.status(400).send({ message: constant.USUARIO_POSSUI_CARRINHO })
}

const produtos = req.body.produtos
for (let index = 0; index < produtos.length; index++) {
const { idproduto, quantidade } = produtos[index]
if (!await produtosService.existeProduto({ _id: idproduto })) {
return res.status(400).send({ message: constant.IDPRODUTO_INVALIDO, item: { index, idproduto, quantidade } })
}

const { quantidade: quantidadeEmEstoque, preco } = await produtosService.getDadosDoProduto({ _id: idproduto })
if (quantidade > quantidadeEmEstoque) {
return res.status(400).send({ message: constant.ESTOQUE_INSUFICIENTE, item: { index, idproduto, quantidade, quantidadeEmEstoque } })
}
Object.assign(produtos[index], { precounitario: preco })
}
let precototal = 0
for (let index = 0; index < produtos.length; index++) {
const { idproduto, quantidade } = produtos[index]
const { quantidade: quantidadeEmEstoque, preco } = await produtosService.getDadosDoProduto({ _id: idproduto })
const novaQuantidade = quantidadeEmEstoque - quantidade
await produtosService.updateById(idproduto, { $set: { quantidade: novaQuantidade } })
precototal += preco * quantidade
}

Object.assign(req.body, { precototal, idusuario: _id })

const dadosCadastrados = await service.criarCarrinho(req.body)
res.status(201).send({ message: constant.POST_SUCESS, _id: dadosCadastrados._id })
} catch (error) {
res.status(500).send({ message: constant.INTERNAL_ERROR, error })
}
}

// user tem que ser dono do carrinho

// exports.delete = async (req, res) => {
// try {
// const quantidadeRegistrosExcluidos = await service.deleteById(req.params.id)
// const message = quantidadeRegistrosExcluidos === 0 ? constant.DELETE_NONE : constant.DELETE_SUCESS
// res.status(200).send({ message })
// } catch (error) {
// res.status(500).send({ message: constant.INTERNAL_ERROR, error })
// }
// }

/*
se user tiver carrinho > edita
se user n tiver carrinho > cadastra
verificar estoque do produto
pegar e cadastrar idUsuario
pegar e cadastrar preço do produto
*/

// exports.put = async (req, res) => {
// try {
// const registroCriado = await service.createOrUpdateById(req.params.id, req.body)
// if (registroCriado) { return res.status(201).send({ message: constant.POST_SUCESS, _id: registroCriado._id }) }
// res.status(200).send({ message: constant.PUT_SUCESS })
// } catch (error) {
// res.status(500).send({ message: constant.INTERNAL_ERROR, error })
// }
// }
1 change: 1 addition & 0 deletions src/data/carrinhos.db
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"produtos":[{"idproduto":"BeeJh5lz3k6kSIzA","quantidade":1,"precounitario":123}],"precototal":123,"idusuario":"oUb7aGkMtSEPf6BZ","_id":"8y7oMpY9tWFXUQWY"}
1 change: 1 addition & 0 deletions src/data/produtos.db
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"nome":"Logitech MX Vertical","preco":123,"descricao":"Mouse bom","quantidade":383,"_id":"BeeJh5lz3k6kSIzA"}
1 change: 1 addition & 0 deletions src/data/usuarios.db
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
{"nome":"Paulo","email":"paulo@g.com","password":"teste","administrador":"true","_id":"oUb7aGkMtSEPf6BZ","createdAt":{"$$date":1588459955988},"updatedAt":{"$$date":1588459992115}}
37 changes: 37 additions & 0 deletions src/models/carrinhos-model.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
'use strict'

const { Joi } = require('express-validation')

exports.schemaGet = {
query: Joi.object({
_id: Joi.any(),
produtos: Joi.any(),
idusuario: Joi.any(),
idproduto: Joi.any(),
quantidade: Joi.any(),
precounitario: Joi.any(),
precototal: Joi.any()
})
}

exports.schemaPost = {
body: Joi.object({
produtos: Joi.array().unique('idproduto').items(
Joi.object({
idproduto: Joi.string().required(),
quantidade: Joi.number().positive().integer().required()
}).required()
).required()
})
}

exports.schemaDelete = {
params: Joi.object({
id: Joi.string().required()
})
}

exports.schemaPut = {
params: this.schemaDelete.params,
body: this.schemaPost.body
}
16 changes: 16 additions & 0 deletions src/routes/carrinhos-route.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
'use strict'

const express = require('express')

const authController = require('../controllers/auth-controller')
const controller = require('../controllers/carrinhos-controller')
const model = require('../models/carrinhos-model')
const validateSchema = require('../services/validateSchema-service')

const router = express.Router()
router.get('/', validateSchema(model.schemaGet), controller.get)
router.post('/', authController.checkToken, validateSchema(model.schemaPost), controller.post)
// router.delete('/:id', authController.checkAdm, validateSchema(model.schemaDelete), controller.delete)
// router.put('/:id', authController.checkAdm, validateSchema(model.schemaPut), controller.put)

module.exports = router
2 changes: 1 addition & 1 deletion src/services/auth-service.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ const jwt = require('jsonwebtoken')
const PRIVATE_KEY = 'f5b99242-6504-4ca3-90f2-05e78e5761ef'

function createToken (emailSenha) {
return jwt.sign(emailSenha, PRIVATE_KEY, { noTimestamp: true }, { expiresIn: '1000ms' })
return jwt.sign(emailSenha, PRIVATE_KEY, { expiresIn: '1d' })
}

function verifyToken (authorization) {
Expand Down
60 changes: 60 additions & 0 deletions src/services/carrinhos-service.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
'use strict'

const Nedb = require('nedb')
const { join } = require('path')

const datastore = new Nedb({ filename: join(__dirname, '../data/carrinhos.db'), autoload: true })

exports.getAll = queryString => {
return new Promise((resolve, reject) => {
datastore.find(queryString, (err, resultado) => {
if (err) reject(err)
else resolve(resultado)
})
})
}

exports.existeCarrinho = pesquisa => {
return new Promise((resolve, reject) => {
datastore.count(pesquisa, (err, count) => {
if (err) reject(err)
else resolve(count !== 0)
})
})
}

exports.criarCarrinho = async body => {
// body = formatarValores(body)
return new Promise((resolve, reject) => {
datastore.insert(body, (err, novoProduto) => {
if (err) reject(err)
else resolve(novoProduto)
})
})
}

// exports.deleteById = async id => {
// return new Promise((resolve, reject) => {
// datastore.remove({ _id: id }, {}, (err, quantidadeRegistrosExcluidos) => {
// if (err) reject(err)
// else resolve(quantidadeRegistrosExcluidos)
// })
// })
// }

// exports.createOrUpdateById = async (idDoUsuarioQueSeraAlterado, body) => {
// body = formatarValores(body)
// return new Promise((resolve, reject) => {
// datastore.update({ _id: idDoUsuarioQueSeraAlterado }, body, { upsert: true }, (err, quantidadeRegistrosAlterados, registroCriado) => {
// if (err) reject(err)
// else resolve(registroCriado)
// })
// })
// }

// function formatarValores (body) {
// body.nome = body.nome.trim()
// body.preco = parseInt(body.preco)
// body.quantidade = parseInt(body.quantidade)
// return body
// }
19 changes: 15 additions & 4 deletions src/services/produtos-service.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,9 +14,16 @@ exports.getAll = queryString => {
})
}

exports.existeProduto = pesquisa => {
console.log(pesquisa)
exports.getDadosDoProduto = queryString => {
return new Promise((resolve, reject) => {
datastore.findOne(queryString, (err, resultado) => {
if (err) reject(err)
else resolve(resultado)
})
})
}

exports.existeProduto = pesquisa => {
return new Promise((resolve, reject) => {
datastore.count(pesquisa, (err, count) => {
if (err) reject(err)
Expand Down Expand Up @@ -44,10 +51,14 @@ exports.deleteById = async id => {
})
}

exports.createOrUpdateById = async (idDoUsuarioQueSeraAlterado, body) => {
exports.createOrUpdateById = async (idDoProdutoQueSeraAlterado, body) => {
body = formatarValores(body)
return this.updateById(idDoProdutoQueSeraAlterado, body)
}

exports.updateById = async (idDoProdutoQueSeraAlterado, body) => {
return new Promise((resolve, reject) => {
datastore.update({ _id: idDoUsuarioQueSeraAlterado }, body, { upsert: true }, (err, quantidadeRegistrosAlterados, registroCriado) => {
datastore.update({ _id: idDoProdutoQueSeraAlterado }, body, { upsert: true }, (err, quantidadeRegistrosAlterados, registroCriado) => {
if (err) reject(err)
else resolve(registroCriado)
})
Expand Down
9 changes: 9 additions & 0 deletions src/services/usuarios-service.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,15 @@ exports.getAll = queryString => {
})
}

exports.getDadosDoUsuario = queryString => {
return new Promise((resolve, reject) => {
datastore.findOne(queryString, (err, resultado) => {
if (err) reject(err)
else resolve(resultado)
})
})
}

exports.existeUsuario = pesquisa => {
return new Promise((resolve, reject) => {
datastore.count(pesquisa, (err, count) => {
Expand Down
5 changes: 4 additions & 1 deletion src/utils/constants.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,5 +11,8 @@ module.exports = {
EMAIL_JA_USADO: 'Este email já está sendo usado',
NOME_JA_USADO: 'Já existe produto com esse nome',
NECESSARIO_ADM: 'Rota exclusiva para administradores',
TOKEN_INVALID: 'Token de acesso inválido ou expirado'
TOKEN_INVALID: 'Token de acesso inexistente, inválido ou expirado',
USUARIO_POSSUI_CARRINHO: 'Não é permitido ter mais de 1 carrinho',
IDPRODUTO_INVALIDO: 'Id de produto inexistente',
ESTOQUE_INSUFICIENTE: 'Produto não possui quantidade suficiente'
}

0 comments on commit b888561

Please sign in to comment.