Files
talk/migrations/1510174676_user_status.js
T
2017-11-17 09:17:43 -07:00

220 lines
4.9 KiB
JavaScript

const UserModel = require('../models/user');
const merge = require('lodash/merge');
const getUserBatch = async () => {
let query = {
status: {
$in: [
'ACTIVE',
'BANNED',
'PENDING',
'APPROVED'
]
}
};
// Find all the users that need migrating.
return UserModel.collection.find(query);
};
module.exports = {
async up() {
const created_at = Date.now();
// Get the first batch of users.
let cursor = await getUserBatch();
const updates = [];
while (await cursor.hasNext()) {
const user = await cursor.next();
const {id, status, canEditName, suspension, disabled} = user;
let update = {
$unset: {
canEditName: '',
suspension: '',
disabled: '',
},
$set: {
status: {
// The username status is specific to each case.
username: {
history: []
},
// The user is not banned by default.
banned: {
status: false,
history: []
},
// The user is not suspended by default.
suspension: {
until: null,
history: []
},
},
updated_at: created_at
},
};
if (disabled) {
update = merge(update, {
$set: {
status: {
banned: {
status: true,
history: [{
status: true,
created_at
}]
},
}
}
});
}
// If the user has an "until" property of their suspension, then we need
// to reflect that in the new status object.
if (suspension && suspension.until !== null) {
update = merge(update, {
$set: {
status: {
suspension: {
until: suspension.until,
history: [{
until: suspension.until,
created_at,
}]
}
}
}
});
}
switch (status) {
case 'ACTIVE':
if (canEditName) {
update = merge(update, {
$set: {
status: {
username: {
status: 'UNSET',
history: [{
status: 'UNSET',
created_at
}]
}
}
}
});
} else {
update = merge(update, {
$set: {
status: {
username: {
status: 'SET',
history: [{
status: 'SET',
created_at
}]
}
}
}
});
}
break;
case 'BANNED':
if (canEditName) {
update = merge(update, {
$set: {
status: {
username: {
status: 'REJECTED',
history: [{
status: 'REJECTED',
created_at
}]
}
}
}
});
} else {
update = merge(update, {
$set: {
status: {
banned: {
status: true,
history: [{
status: true,
created_at
}]
},
username: {
status: 'SET',
history: [{
status: 'SET',
created_at
}]
}
}
}
});
}
break;
case 'PENDING':
update = merge(update, {
$set: {
status: {
username: {
status: 'CHANGED',
history: [{
status: 'CHANGED',
created_at
}]
}
}
}
});
break;
case 'APPROVED':
update = merge(update, {
$set: {
status: {
username: {
status: 'APPROVED',
history: [{
status: 'APPROVED',
created_at
}]
}
}
}
});
break;
default:
throw new Error(`${status} is an invalid status`);
}
updates.push({query: {id}, update});
}
if (updates.length > 0) {
// Create a new batch operation.
let bulk = UserModel.collection.initializeUnorderedBulkOp();
for (const {query, update} of updates) {
bulk.find(query).updateOne(update);
}
// Execute the bulk update operation.
await bulk.execute();
}
}
};