Initial Commit
This commit is contained in:
commit
f54d97e4a9
30 changed files with 2532 additions and 0 deletions
60
routes/adminSettings/index.js
Normal file
60
routes/adminSettings/index.js
Normal file
|
@ -0,0 +1,60 @@
|
|||
const verifyAuth = require('../../middlewares/verifyAuth');
|
||||
const bcrypt = require('bcrypt-nodejs');
|
||||
const express = require('express');
|
||||
|
||||
module.exports = (db) => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/', verifyAuth(), (req, res) => {
|
||||
if (!req.user.admin) return res.redirect('/');
|
||||
db.allDocs({ include_docs: true })
|
||||
.then(docs => {
|
||||
res.render('adminSettings', { title: 'Admin Settings', users: docs.rows })
|
||||
})
|
||||
.catch(err => { throw err; });
|
||||
});
|
||||
|
||||
router.post('/add', verifyAuth(), async (req, res) => {
|
||||
if (!req.user.admin) return res.redirect('/');
|
||||
bcrypt.hash(req.body.newUserPassword, null, null, async (err, newUserPasswordHash) => {
|
||||
if (err) throw err;
|
||||
await db.put({
|
||||
_id: req.body.newUserUsername,
|
||||
password: newUserPasswordHash,
|
||||
admin: false,
|
||||
wishlist: []
|
||||
});
|
||||
req.flash('success', `Successfully added user ${req.body.newUserUsername}!`);
|
||||
res.redirect('/admin-settings');
|
||||
});
|
||||
});
|
||||
|
||||
router.get('/remove/:userToRemove', verifyAuth(), (req, res) => {
|
||||
if (!req.user.admin) return res.redirect('/');
|
||||
res.render('remove', { userToRemove: req.params.userToRemove });
|
||||
});
|
||||
|
||||
router.post('/remove/:userToRemove', verifyAuth(), async (req, res) => {
|
||||
if (!req.user.admin) return res.redirect('/');
|
||||
const doc = await db.get(req.params.userToRemove);
|
||||
if (doc.admin) {
|
||||
req.flash('error', 'Failed to remove: user is admin.');
|
||||
return res.redirect('/admin-settings');
|
||||
}
|
||||
await db.remove(doc);
|
||||
const docs = await db.allDocs({ include_docs: true });
|
||||
for (let i = 0; i < docs.length; i++) {
|
||||
for (let j = 0; j < docs[i].doc.wishlist.length; j++) {
|
||||
if (docs[i].doc.wishlist[j].pledgedBy === req.params.userToRemove) {
|
||||
docs[i].doc.wishlist[j].pledgedBy === undefined;
|
||||
if (docs[i].doc.wishlist[j].addedBy === req.params.userToRemove) await db.remove(doc);
|
||||
else await db.put(docs[i].doc);
|
||||
}
|
||||
}
|
||||
}
|
||||
req.flash('success', `Successfully removed user ${req.params.userToRemove}`);
|
||||
res.redirect('/admin-settings')
|
||||
});
|
||||
|
||||
return router;
|
||||
};
|
37
routes/index.js
Normal file
37
routes/index.js
Normal file
|
@ -0,0 +1,37 @@
|
|||
const verifyAuth = require('../middlewares/verifyAuth');
|
||||
const express = require('express');
|
||||
const path = require('path');
|
||||
|
||||
module.exports = (db) => {
|
||||
const router = express.Router();
|
||||
|
||||
router.use('/', express.static(path.join(__dirname, '../static')));
|
||||
|
||||
router.get('/',
|
||||
async (req, res, next) => {
|
||||
dbInfo = await db.info();
|
||||
if (dbInfo.doc_count === 0) {
|
||||
res.redirect('/setup');
|
||||
} else {
|
||||
next();
|
||||
}
|
||||
},
|
||||
verifyAuth(),
|
||||
(req, res) => {
|
||||
res.redirect('/wishlist');
|
||||
}
|
||||
);
|
||||
|
||||
router.use('/setup', require('./setup')(db));
|
||||
|
||||
router.use('/login', require('./login')());
|
||||
router.use('/logout', require('./logout')());
|
||||
|
||||
router.use('/wishlist', require('./wishlist')(db));
|
||||
|
||||
router.use('/profile', require('./profile')(db));
|
||||
|
||||
router.use('/admin-settings', require('./adminSettings')(db));
|
||||
|
||||
return router;
|
||||
}
|
29
routes/login/index.js
Normal file
29
routes/login/index.js
Normal file
|
@ -0,0 +1,29 @@
|
|||
const passport = require('passport');
|
||||
const express = require('express');
|
||||
|
||||
module.exports = () => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/',
|
||||
(req, res) => {
|
||||
if (req.isAuthenticated()) {
|
||||
res.redirect('/');
|
||||
} else {
|
||||
res.render('login');
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
router.post(
|
||||
'/',
|
||||
(req, res, next) => {
|
||||
next();
|
||||
},
|
||||
passport.authenticate('local', {
|
||||
successRedirect: '/',
|
||||
failureRedirect: '/login',
|
||||
failureFlash: 'Invalid username or password'
|
||||
})
|
||||
);
|
||||
return router;
|
||||
};
|
14
routes/logout/index.js
Normal file
14
routes/logout/index.js
Normal file
|
@ -0,0 +1,14 @@
|
|||
const verifyAuth = require('../../middlewares/verifyAuth');
|
||||
const express = require('express');
|
||||
|
||||
module.exports = () => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/', verifyAuth(), (req, res) => res.render('logout'));
|
||||
router.post('/', (req, res) => {
|
||||
req.logout();
|
||||
res.redirect('/');
|
||||
});
|
||||
|
||||
return router;
|
||||
};
|
39
routes/profile/index.js
Normal file
39
routes/profile/index.js
Normal file
|
@ -0,0 +1,39 @@
|
|||
const verifyAuth = require('../../middlewares/verifyAuth');
|
||||
const bcrypt = require('bcrypt-nodejs');
|
||||
const express = require('express');
|
||||
|
||||
module.exports = (db) => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/', verifyAuth(), (req, res) => res.render('profile', { title: `Profile Settings - ${req.user._id}`}));
|
||||
router.post('/', verifyAuth(), (req, res) => {
|
||||
if (req.body.oldPassword && req.body.newPassword) {
|
||||
bcrypt.compare(req.body.oldPassword, req.user.password, (err, correct) => {
|
||||
if (err) throw err;
|
||||
if (correct) {
|
||||
bcrypt.hash(req.body.newPassword, null, null, (err, hash) => {
|
||||
if (err) throw err;
|
||||
db.get(req.user._id)
|
||||
.then(doc => {
|
||||
doc.password = hash;
|
||||
db.put(doc)
|
||||
.then(() => {
|
||||
req.flash('success', 'Changes saved successfully!');
|
||||
res.redirect('/profile');
|
||||
})
|
||||
.catch(err => { throw err; });
|
||||
})
|
||||
.catch(err => { throw err; });
|
||||
});
|
||||
} else {
|
||||
req.flash('error', 'Incorrect old password');
|
||||
res.redirect('/profile');
|
||||
}
|
||||
});
|
||||
} else {
|
||||
res.redirect('/profile');
|
||||
}
|
||||
});
|
||||
|
||||
return router;
|
||||
};
|
39
routes/setup/index.js
Normal file
39
routes/setup/index.js
Normal file
|
@ -0,0 +1,39 @@
|
|||
const bcrypt = require('bcrypt-nodejs')
|
||||
const express = require('express');
|
||||
|
||||
module.exports = (db) => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/',
|
||||
async (req, res) => {
|
||||
const dbInfo = await db.info();
|
||||
if (dbInfo.doc_count === 0) {
|
||||
res.render('setup', { title: 'Setup' });
|
||||
} else {
|
||||
res.redirect('/');
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
router.post('/',
|
||||
async (req, res) => {
|
||||
const dbInfo = await db.info();
|
||||
if (dbInfo.doc_count === 0) {
|
||||
bcrypt.hash(req.body.adminPassword, null, null, (err, adminPasswordHash) => {
|
||||
if (err) throw err;
|
||||
db.put({
|
||||
_id: req.body.adminUsername,
|
||||
password: adminPasswordHash,
|
||||
admin: true,
|
||||
wishlist: []
|
||||
})
|
||||
res.redirect('/');
|
||||
});
|
||||
} else {
|
||||
res.redirect('/');
|
||||
}
|
||||
}
|
||||
);
|
||||
|
||||
return router;
|
||||
}
|
119
routes/wishlist/index.js
Normal file
119
routes/wishlist/index.js
Normal file
|
@ -0,0 +1,119 @@
|
|||
const verifyAuth = require('../../middlewares/verifyAuth');
|
||||
const getProductName = require('get-product-name');
|
||||
const bcrypt = require('bcrypt-nodejs');
|
||||
const express = require('express');
|
||||
const uuid = require('uuid/v4');
|
||||
|
||||
const totals = wishlist => {
|
||||
let unpledged = 0;
|
||||
let pledged = 0;
|
||||
wishlist.forEach(wishItem => {
|
||||
if (wishItem.pledgedBy) pledged += 1;
|
||||
else unpledged += 1;
|
||||
});
|
||||
return { unpledged, pledged };
|
||||
};
|
||||
|
||||
const ValidURL = (string) => { // Ty SO
|
||||
try {
|
||||
new URL(string);
|
||||
return true;
|
||||
} catch (_) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
module.exports = (db) => {
|
||||
const router = express.Router();
|
||||
|
||||
router.get('/', verifyAuth(), async (req, res) => {
|
||||
const docs = await db.allDocs({ include_docs: true })
|
||||
res.render('wishlists', { title: 'Wishlists', users: docs.rows, totals})
|
||||
});
|
||||
|
||||
router.get('/:user', verifyAuth(), async (req, res) => {
|
||||
try {
|
||||
const dbUser = await db.get(req.params.user);
|
||||
res.render('wishlist', { title: `Wishlist - ${dbUser._id}`, wishlist: dbUser.wishlist });
|
||||
} catch (error) {
|
||||
res.redirect('/wishlist');
|
||||
}
|
||||
});
|
||||
|
||||
router.post('/:user', verifyAuth(), async (req, res) => {
|
||||
const isUrl = ValidURL(req.body.itemUrlOrName);
|
||||
const item = {};
|
||||
let productData;
|
||||
try {
|
||||
if (isUrl) productData = await getProductName(req.body.itemUrlOrName);
|
||||
} catch (err) {}
|
||||
item.name = (productData ? productData.name : req.body.itemUrlOrName);
|
||||
item.addedBy = req.user._id;
|
||||
item.pledgedBy = (req.user._id === req.params.user ? undefined : req.user._id);
|
||||
if (isUrl) item.url = req.body.itemUrlOrName;
|
||||
item.id = uuid();
|
||||
const doc = await db.get(req.params.user);
|
||||
doc.wishlist.push(item);
|
||||
await db.put(doc);
|
||||
req.flash('success', (req.user._id === req.params.user ? 'Added item to wishlist' : `Pleged item for ${req.params.user}`));
|
||||
res.redirect(`/wishlist/${req.params.user}`);
|
||||
});
|
||||
|
||||
router.post('/:user/pledge/:itemId', verifyAuth(), async (req, res) => {
|
||||
const docs = await db.allDocs({ include_docs: true });
|
||||
for (let i = 0; i < docs.rows.length; i++) {
|
||||
for (let j = 0; j < docs.rows[i].doc.wishlist.length; j++) {
|
||||
if (docs.rows[i].doc.wishlist[j].id === req.params.itemId) {
|
||||
if (docs.rows[i].doc.wishlist[j].pledgedBy !== undefined) {
|
||||
req.flash('error', 'Item already pledged for');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
}
|
||||
docs.rows[i].doc.wishlist[j].pledgedBy = req.user._id;
|
||||
await db.put(docs.rows[i].doc);
|
||||
req.flash('success', 'Successfully pledged for item!');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
router.post('/:user/unpledge/:itemId', verifyAuth(), async (req, res) => {
|
||||
const docs = await db.allDocs({ include_docs: true });
|
||||
for (let i = 0; i < docs.rows.length; i++) {
|
||||
for (let j = 0; j < docs.rows[i].doc.wishlist.length; j++) {
|
||||
if (docs.rows[i].doc.wishlist[j].id === req.params.itemId) {
|
||||
if (docs.rows[i].doc.wishlist[j].pledgedBy !== req.user._id) {
|
||||
req.flash('error', 'You did not pledge for this');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
}
|
||||
docs.rows[i].doc.wishlist[j].pledgedBy = undefined;
|
||||
if (docs.rows[i].doc.wishlist[j].addedBy === req.user._id) docs.rows[i].doc.wishlist.pop(j);
|
||||
await db.put(docs.rows[i].doc);
|
||||
req.flash('success', 'Successfully unpledged for item');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
}
|
||||
}
|
||||
}
|
||||
req.flash('error', 'Failed to find item');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
});
|
||||
|
||||
router.post('/:user/remove/:itemId', verifyAuth(), async (req, res) => {
|
||||
if (req.user._id !== req.params.user) {
|
||||
req.flash('error', 'Not correct user');
|
||||
return res.redirect(`/wishlists/${req.params.user}`);
|
||||
}
|
||||
const doc = await db.get(req.user._id);
|
||||
for (let i = 0; i < doc.wishlist.length; i++) {
|
||||
if (doc.wishlist[i].id === req.params.itemId) {
|
||||
doc.wishlist.pop(i);
|
||||
await db.put(doc);
|
||||
req.flash('success', 'Successfully removed from wishlist');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
}
|
||||
}
|
||||
req.flash('error', 'Failed to find item');
|
||||
return res.redirect(`/wishlist/${req.params.user}`);
|
||||
});
|
||||
|
||||
return router;
|
||||
};
|
Loading…
Add table
Add a link
Reference in a new issue