Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
44 commits
Select commit Hold shift + click to select a range
0aabc58
init sequelize and create MVC
caturprasatya Apr 16, 2021
a350f20
add errorhandler
caturprasatya Apr 16, 2021
f0011d9
TDD Marco done
markkerss Apr 16, 2021
9efa1d9
server done hit database
caturprasatya Apr 17, 2021
508a33c
add route get user
caturprasatya Apr 17, 2021
d78a1de
update error in controller
caturprasatya Apr 17, 2021
170d662
server testing done
caturprasatya Apr 18, 2021
a4b29b4
delete file dummy
caturprasatya Apr 18, 2021
aafc683
add new controller
caturprasatya Apr 19, 2021
9f40772
add midtrans endpoint
mufendew Apr 19, 2021
0b485d7
line 39 expence => expance
fahmialis Apr 19, 2021
793a756
testing with coverage 94%
caturprasatya Apr 19, 2021
67b75c2
Merge branch 'development' into testing
caturprasatya Apr 19, 2021
e276db6
Merge pull request #4 from Final-Project-RUKUN/testing
caturprasatya Apr 19, 2021
50cabbf
add column in suggestions
caturprasatya Apr 19, 2021
9a8ef22
Merge pull request #5 from Final-Project-RUKUN/update-table
caturprasatya Apr 19, 2021
3485b23
update status typo catur
mufendew Apr 19, 2021
d651a23
Merge branch 'update_transaction_dikit' into development
mufendew Apr 19, 2021
b8d389a
update model suggestion and create
mufendew Apr 19, 2021
dba8d7d
Merge pull request #7 from Final-Project-RUKUN/update_suggestion
mufendew Apr 19, 2021
9be27fc
want deploy heroku
caturprasatya Apr 19, 2021
c301460
Merge pull request #8 from Final-Project-RUKUN/deploy
caturprasatya Apr 19, 2021
cc09fd2
change response login
caturprasatya Apr 19, 2021
9f81cc1
handle response admin login
caturprasatya Apr 19, 2021
82e1cc0
solve controller login user and admin
caturprasatya Apr 20, 2021
5c823ae
fetch data from desc
caturprasatya Apr 20, 2021
9472caf
solve controller sugestion and transaction
caturprasatya Apr 20, 2021
ab60a64
add new controller update village
caturprasatya Apr 20, 2021
172cc6b
Merge branch 'midtrans' into development
mufendew Apr 20, 2021
193e3b3
solve testing get coverage 95%
caturprasatya Apr 20, 2021
3d4017c
Finish
mufendew Apr 20, 2021
3003356
Merge pull request #10 from Final-Project-RUKUN/finish-midtrans
mufendew Apr 20, 2021
31d4997
Revert "solve testing get coverage 95%"
mufendew Apr 20, 2021
76a4a92
Revert "Merge pull request #10 from Final-Project-RUKUN/finish-midtrans"
mufendew Apr 20, 2021
1407c56
Update midtransRoute.js
mufendew Apr 20, 2021
f818c6a
solve midtrans caannot use in heroku
caturprasatya Apr 20, 2021
2a19181
Merge pull request #12 from Final-Project-RUKUN/solve-midtrans
caturprasatya Apr 20, 2021
7db6de6
solve testing in midtrans
caturprasatya Apr 21, 2021
292667c
Merge branch 'development' into solve-midtrans
caturprasatya Apr 21, 2021
e0ec844
Merge pull request #13 from Final-Project-RUKUN/solve-midtrans
caturprasatya Apr 21, 2021
ab3ec66
delete syntax not use in app.ja
caturprasatya Apr 21, 2021
8450e63
add validate in amount
caturprasatya Apr 23, 2021
435b030
Merge branch 'development' into validate-controller
caturprasatya Apr 23, 2021
a966eed
Merge pull request #15 from Final-Project-RUKUN/validate-controller
caturprasatya Apr 23, 2021
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -102,3 +102,6 @@ dist

# TernJS port file
.tern-port

sandbox.js
failed.zip
20 changes: 20 additions & 0 deletions app.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
if (process.env.NODE_ENV !== 'production') {
require('dotenv').config()
}

const express = require('express')
const cors = require('cors')
const route = require('./routes/')
const handleError = require('./middlewares/errHandler')
const app = express()

app.set('view engine','ejs')

app.use(cors())
app.use(express.urlencoded({ extended: true }))
app.use(express.json())

app.use(route)
app.use(handleError)

module.exports = app
4 changes: 4 additions & 0 deletions bin/http.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
const app = require('../app')
const port = process.env.PORT || 4000

app.listen(port, ()=> console.log('App run in port : ', port))
28 changes: 28 additions & 0 deletions config/config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
const env = process.env.NODE_ENV || 'development'

if (env == 'development' || env =='test') {
require('dotenv').config()
}

let capsEnv = env.toUpperCase()
let database = {
username : process.env["DB_USERNAME_" + capsEnv],
password : process.env["DB_PASSWORD_" + capsEnv],
database : process.env["DB_NAME_" + capsEnv],
host : process.env["DB_HOST_" + capsEnv],
dialect : process.env["DB_DIALECT_" + capsEnv],
logging: true
}

module.exports = {
"development": database,
"test": database,
"production": {
"use_env_variable" : "DATABASE_URL",
"dialectOptions" : {
"ssl": {
"rejectUnauthorized": false
}
}
}
}
72 changes: 72 additions & 0 deletions controllers/adminController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
const { User, Village } = require('../models')
const { comparePassword } = require('../helpers/useBcrypt')
const { generateToken } = require('../helpers/useJwt')
const createToken = require('../helpers/useToken')


class AdminController {

static async registerAdmin(req, res, next) {
const { name, username, password, nameVillage, location, balance } = req.body

try {
const role = 'admin'
const invitation_code = createToken()
const user = await User.create({ name, username, password, role })

const village = await Village.create({ name: nameVillage, location, invitation_code, balance, UserId: user.id})

await User.update({ VillageId: village.id } ,{ where: { id: user.id }})

res.status(201).json({ message: 'Success Crete User and Village', invitation_code})
} catch (error) {
if (Array.isArray(error)) {
next({ name : 'SequelizeValidationError', errors: error })
} else {
next(error)
}
}
}

static async loginAdmin(req, res, next) {
const { username, password } = req.body
try {
const user = await User.findOne({ where: { username }})

if (user) {
const isPassword = comparePassword( password, user.password )

if (isPassword && user.role === 'admin') {
const access_token = generateToken({ id: user.id, username: user.username })

res.status(200).json(access_token)
} else {
next({ code: 404, message: "Invalid Username/Password" })
}
} else {
next({ code: 404, message: "Invalid Username/Password" })
}
} catch (error) {
next(error)
}
}

static async changeAdmin(req, res, next) {
const { id } = req.params
const { VillageId, id : AdminId } = req.currentUser

try {
await Village.update({ UserId: id }, { where: { id: VillageId }})

await User.update({ role: 'admin' }, { where: { id }})

await User.update({ role: 'member' }, { where: { id: AdminId }})

res.status(200).json({ message: "Successfully change role admin" })
} catch (error) {
next(error)
}
}
}

module.exports = AdminController
47 changes: 47 additions & 0 deletions controllers/suggestionController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
const { Suggestion, Village, User } = require('../models')
class SuggestionConroller {
static async fetchSuggestions(req, res, next){
try {
const { VillageId } = req.currentUser
const villageSuggestions = await Village.findOne({where : { id : VillageId},
include: {
model: Suggestion,
separate: true,
order: [['createdAt', 'DESC']],
include: User
}
})

res.status(200).json(villageSuggestions)
} catch (error) {
next(error)
}
}

static async addSuggestion(req, res, next){
const { title, description, type } = req.body
const { id, VillageId } = req.currentUser

try {
const suggestion = await Suggestion.create({title, description, type, UserId: id, VillageId})

res.status(201).json(suggestion)
} catch (error) {
next(error)
}
}

static async deleteSuggestion(req, res, next){
const { id } = req.params

try {
await Suggestion.destroy({ where : { id }, returning : true })

res.status(200).json({ message: 'Suggestion has been successfully deleted.'})
} catch (error) {
next(error)
}
}
}

module.exports = SuggestionConroller
75 changes: 75 additions & 0 deletions controllers/transactionController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
const { Transaction, Village, User } = require('../models')

class TransactionController {

static async fetchTransactions(req, res, next) {
try {
const { VillageId } = req.currentUser

const village = await Village.findOne({where : { id : VillageId }, include: {
model: Transaction,
separate: true,
order: [['createdAt', 'DESC']],
include: User
}})
res.status(200).json(village)
} catch (error) {
next(error)
}
}

static async fetchTransactionsUser(req, res, next) {
try {
const { id, VillageId } = req.currentUser

const transactions = await Transaction.findAll({
where: { UserId: id, VillageId },
order: [['id', 'DESC']]
})

res.status(200).json(transactions)
} catch (error) {
next(error)
}
}

static async addTransaction(req, res, next) {
const { title, amount, category, note, type, status } = req.body
const { id, VillageId } = req.currentUser

try {
if(+amount === 0){
next({
code: 400,
message: 'Invalid Input Payment'
})
}
if (type === 'expanse') {
const { balance } = await Village.findByPk(VillageId)
const newBalance = balance - +amount

await Village.update({ balance: newBalance }, { where: { id: VillageId }})

const dataCreate = await Transaction.create({ title, amount, category, note, type, VillageId, UserId: id, status })
res.status(201).json(dataCreate)
} else if(type === 'income') {
const { balance } = await Village.findByPk(VillageId)
const newBalance = +balance + +amount

await Village.update({ balance: newBalance }, { where: { id: VillageId }})

const dataCreate = await Transaction.create({ title, amount, category, note, type, VillageId, UserId: id, status })
res.status(201).json(dataCreate)
} else {
next({
code: 400,
message: 'Invalid Data Type Payment'
})
}
} catch (error) {
next(error)
}
}
}

module.exports = TransactionController
73 changes: 73 additions & 0 deletions controllers/userController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
const { User, Village } = require('../models/')
const { comparePassword } = require('../helpers/useBcrypt')
const { generateToken } = require('../helpers/useJwt')
class UserController {

static async login(req, res, next) {
const { username, password, push_token } = req.body
try {
const user = await User.findOne({ where: { username } })

if (user) {
const isPassword = comparePassword( password, user.password )

if (isPassword) {
await User.update({ push_token }, { where: { username } })

const token = generateToken({ id: user.id, username: user.username })

res.status(200).json(token)
} else {
next({ code: 404, message: "Invalid Username/Password" })
}
} else {
next({ code: 404, message: "Invalid Username/Password" })
}
} catch (error) {
next(error)
}
}

static async getUser(req, res, next) {
const { id } = req.currentUser
try {
const user = await User.findByPk(id)
res.status(200).json(user)
} catch (error) {
next(error)
}
}

static async register(req, res, next) {
const { name, username, password, invitation_code } = req.body
try {
const role = 'member'

const village = await Village.findOne({ where: { invitation_code }})

if (village) {
const user = await User.create({ name, username, password, role, VillageId: village.id })

res.status(201).json(user)
} else {
next({ code: 404, message: 'Cannot Found Village' })
}
} catch (error) {
next(error)
}
}

static async deleteUser(req, res, next) {
const { id } = req.params

try {
await User.destroy({ where: { id } })

res.status(200).json({ message: "Successfully deleted user" })
} catch (error) {
next(error)
}
}
}

module.exports = UserController
29 changes: 29 additions & 0 deletions controllers/villageController.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,29 @@
const { Village, User } = require('../models/')
class VillageController {

static async getDataVillage(req, res, next) {
const { VillageId } = req.currentUser
try {

const data = await Village.findByPk(VillageId, { include: User })

res.status(200).json(data)
} catch (error) {
next(error)
}
}

static async updateVillage(req, res, next){
const { VillageId } = req.currentUser
const { location, name } = req.body
try {
await Village.update( { location, name } ,{ where : { id: VillageId }})

res.status(200).json({ message: "Success Update Village" })
} catch (error) {
next(error)
}
}
}

module.exports = VillageController
11 changes: 11 additions & 0 deletions helpers/useBcrypt.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
const bcrypt = require('bcryptjs')

const hashPassword = (password) => {
return bcrypt.hashSync(password, 10)
}

const comparePassword =(password, hashedPass) => {
return bcrypt.compareSync(password, hashedPass)
}

module.exports = { hashPassword, comparePassword }
11 changes: 11 additions & 0 deletions helpers/useJwt.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
const jwt = require('jsonwebtoken')

const generateToken = (payload) => {
return jwt.sign(payload, process.env.KEY)
}

const verifyToken = (token) => {
return jwt.verify(token, process.env.KEY)
}

module.exports = { generateToken, verifyToken }
5 changes: 5 additions & 0 deletions helpers/useToken.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
function createToken() {
return Math.random().toString(36).substr(7); // remove `0.`
};

module.exports = createToken
Loading