Added opt-in option for promotional emails
This commit is contained in:
@@ -2,10 +2,16 @@ const express = require('express');
|
||||
const router = express.Router();
|
||||
|
||||
//basic account management
|
||||
router.get('/', require('./query'));
|
||||
router.patch('/', require('./update'));
|
||||
|
||||
//signup -> login -> logout
|
||||
router.post('/signup', require('./signup'));
|
||||
router.get('/validation', require('./validation'));
|
||||
router.post('/login', require('./login'));
|
||||
router.post('/logout', require('./logout'));
|
||||
router.post('/deletion', require('./deletion'));
|
||||
|
||||
//account deletion
|
||||
router.delete('/deletion', require('./deletion'));
|
||||
|
||||
module.exports = router;
|
||||
|
||||
@@ -37,7 +37,7 @@ const route = async (req, res) => {
|
||||
}
|
||||
|
||||
//save the session and cookie data
|
||||
req.session.account = account;
|
||||
req.session.account = JSON.parse(JSON.stringify(account.dataValues));
|
||||
res.cookie('loggedin', process.env.WEB_ADDRESS);
|
||||
|
||||
if (account.privilege == 'administrator') {
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
const { accounts } = require('../database/models');
|
||||
|
||||
const route = async (req, res) => {
|
||||
if (!req.session.account || !req.session.account.id) {
|
||||
res.status(401).send('Unknown account');
|
||||
}
|
||||
|
||||
//update the reference
|
||||
req.session.account = (await accounts.findOne({
|
||||
where: {
|
||||
id: req.session.account.id
|
||||
}
|
||||
})).dataValues;
|
||||
|
||||
//respond with the private-facing data
|
||||
res.status(200).json({
|
||||
contact: req.session.account.contact
|
||||
});
|
||||
};
|
||||
|
||||
module.exports = route;
|
||||
@@ -101,6 +101,7 @@ const registerPendingSignup = async (fields, hash, token) => {
|
||||
email: fields.email,
|
||||
username: fields.username,
|
||||
hash: hash,
|
||||
contact: fields.contact,
|
||||
token: token
|
||||
});
|
||||
|
||||
@@ -109,7 +110,12 @@ const registerPendingSignup = async (fields, hash, token) => {
|
||||
|
||||
const sendValidationEmail = async (email, username, token) => {
|
||||
const addr = `${process.env.WEB_PROTOCOL}://${process.env.WEB_ADDRESS}/api/accounts/validation?username=${username}&token=${token}`;
|
||||
const msg = `Hello! Please visit the following address to validate your account: ${addr}`;
|
||||
const msg = `Hello ${username}!
|
||||
|
||||
Please visit the following link to validate your account: ${addr}
|
||||
|
||||
You can contact us directly at our physical mailing address here: ${process.env.MAIL_PHYSICAL}
|
||||
`;
|
||||
|
||||
let transporter, info;
|
||||
|
||||
@@ -143,7 +149,7 @@ const sendValidationEmail = async (email, username, token) => {
|
||||
}
|
||||
|
||||
if (info.accepted[0] != email) {
|
||||
return 'validation email failed';
|
||||
return 'validation email failed to send';
|
||||
}
|
||||
|
||||
return null;
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
const { accounts } = require('../database/models');
|
||||
|
||||
const route = async (req, res) => {
|
||||
if (!req.session.account.id) {
|
||||
return res.status(500).send('missing account data');
|
||||
}
|
||||
|
||||
//update the account
|
||||
await accounts.update({
|
||||
contact: req.fields.contact
|
||||
}, {
|
||||
where: {
|
||||
id: req.session.account.id
|
||||
}
|
||||
});
|
||||
|
||||
//update the reference
|
||||
req.session.account = (await accounts.findOne({
|
||||
where: {
|
||||
id: req.session.account.id
|
||||
}
|
||||
})).dataValues;
|
||||
|
||||
//respond with an OK
|
||||
res.status(200).send('Information updated');
|
||||
};
|
||||
|
||||
module.exports = route;
|
||||
@@ -29,7 +29,8 @@ const route = async (req, res) => {
|
||||
accounts.create({
|
||||
email: info.email,
|
||||
username: info.username,
|
||||
hash: info.hash
|
||||
hash: info.hash,
|
||||
contact: info.contact
|
||||
});
|
||||
|
||||
//finally
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
//DOCS: this whole file is just a big bugfix
|
||||
//DOCS: ensure that there is at least one administration account
|
||||
const bcrypt = require('bcryptjs');
|
||||
const { accounts } = require('../database/models');
|
||||
|
||||
const defaultAdminAccount = async () => {
|
||||
const admin = await accounts.findOne({
|
||||
where: {
|
||||
privilege: 'administrator'
|
||||
}
|
||||
});
|
||||
|
||||
if (admin == null) {
|
||||
await accounts.create({
|
||||
privilege: 'administrator',
|
||||
email: `admin@${process.env.WEB_ADDRESS}`,
|
||||
username: `admin`,
|
||||
hash: await bcrypt.hash('password', await bcrypt.genSalt(11))
|
||||
});
|
||||
|
||||
console.log(`Created default admin account (email: admin@${process.env.WEB_ADDRESS}; password: password)`);
|
||||
}
|
||||
};
|
||||
|
||||
module.exports = defaultAdminAccount;
|
||||
@@ -16,27 +16,4 @@ router.get('/banned', require('./banned'));
|
||||
router.post('/ban', require('./ban'));
|
||||
router.post('/unban', require('./unban'));
|
||||
|
||||
//DOCS: ensure that there is at least one administration account
|
||||
const bcrypt = require('bcryptjs');
|
||||
const { accounts } = require('../database/models');
|
||||
|
||||
(async () => {
|
||||
const admin = await accounts.findOne({
|
||||
where: {
|
||||
privilege: 'administrator'
|
||||
}
|
||||
});
|
||||
|
||||
if (admin == null) {
|
||||
await accounts.create({
|
||||
privilege: 'administrator',
|
||||
email: `admin@${process.env.WEB_ADDRESS}`,
|
||||
username: `admin`,
|
||||
hash: await bcrypt.hash('password', await bcrypt.genSalt(11))
|
||||
});
|
||||
|
||||
console.log(`Created default admin account (email: admin@${process.env.WEB_ADDRESS}; password: password)`);
|
||||
}
|
||||
})();
|
||||
|
||||
module.exports = router;
|
||||
@@ -28,6 +28,12 @@ module.exports = sequelize.define('accounts', {
|
||||
|
||||
hash: 'varchar(100)', //for passwords
|
||||
|
||||
contact: {
|
||||
type: Sequelize.BOOLEAN,
|
||||
allowNull: false,
|
||||
defaultValue: false
|
||||
},
|
||||
|
||||
deletion: {
|
||||
type: 'DATETIME',
|
||||
allowNull: true,
|
||||
|
||||
@@ -14,5 +14,11 @@ module.exports = sequelize.define('pendingSignups', {
|
||||
|
||||
hash: 'varchar(100)', //for passwords
|
||||
|
||||
contact: {
|
||||
type: Sequelize.BOOLEAN,
|
||||
allowNull: false,
|
||||
defaultValue: false
|
||||
},
|
||||
|
||||
token: Sequelize.INTEGER(11)
|
||||
});
|
||||
|
||||
+14
-4
@@ -11,19 +11,29 @@ const path = require('path');
|
||||
const formidable = require('express-formidable');
|
||||
const cookieParser = require('cookie-parser');
|
||||
const session = require('express-session');
|
||||
|
||||
app.use(formidable());
|
||||
app.use(cookieParser());
|
||||
app.use(session({ secret: process.env.SESSION_SECRET, resave: true, saveUninitialized: true }));
|
||||
const SequelizeStore = require("connect-session-sequelize")(session.Store);
|
||||
|
||||
//database connection
|
||||
const database = require('./database');
|
||||
const models = require('./database/models'); //invoke all models
|
||||
|
||||
app.use(formidable());
|
||||
app.use(cookieParser());
|
||||
app.use(session({
|
||||
secret: process.env.SESSION_SECRET,
|
||||
resave: true,
|
||||
saveUninitialized: true,
|
||||
store: new SequelizeStore({
|
||||
db: database
|
||||
})
|
||||
}));
|
||||
|
||||
//account management
|
||||
app.use('/api/accounts', require('./accounts'));
|
||||
|
||||
//administration
|
||||
app.use('/api/admin', require('./admin'));
|
||||
require('./admin/bookkeeper')(); //BUGFIX
|
||||
|
||||
//send static files
|
||||
app.use('/', express.static(path.resolve(__dirname, '..', 'public')));
|
||||
|
||||
Reference in New Issue
Block a user