This commit is contained in:
Daniel Odendahl Jr
2017-06-02 00:46:18 +00:00
parent f97990ee18
commit d1131d6092
2 changed files with 133 additions and 136 deletions
+7 -8
View File
@@ -1,6 +1,6 @@
{ {
"name": "xiaobot", "name": "xiaobot",
"version": "22.0.2", "version": "22.0.3",
"description": "A Discord Bot", "description": "A Discord Bot",
"main": "Shard.js", "main": "Shard.js",
"scripts": { "scripts": {
@@ -34,23 +34,22 @@
"node": "8.0.0" "node": "8.0.0"
}, },
"dependencies": { "dependencies": {
"bufferutil": "^3.0.0", "bufferutil": "^3.0.1",
"canvas": "automattic/node-canvas", "canvas": "automattic/node-canvas",
"cheerio": "^0.22.0", "cheerio": "^1.0.0",
"cleverio": "dragonfire535/cleverio", "cleverio": "dragonfire535/cleverio",
"custom-translate": "dragonfire535/custom-translate", "custom-translate": "dragonfire535/custom-translate",
"discord.js": "hydrabolt/discord.js", "discord.js": "hydrabolt/discord.js",
"discord.js-commando": "gawdl3y/discord.js-commando", "discord.js-commando": "gawdl3y/discord.js-commando",
"erlpack": "hammerandchisel/erlpack", "erlpack": "hammerandchisel/erlpack",
"ffmpeg-binaries": "^3.2.2", "mathjs": "^3.13.3",
"mathjs": "^3.12.2",
"moment": "^2.18.1", "moment": "^2.18.1",
"moment-duration-format": "^1.3.0", "moment-duration-format": "^1.3.0",
"node-opus": "^0.2.6", "node-opus": "^0.2.6",
"pg": "^6.1.5", "pg": "^6.2.3",
"sequelize": "^3.30.4", "sequelize": "^3.30.4",
"snekfetch": "^3.1.7", "snekfetch": "^3.1.8",
"tsubaki": "^1.1.0", "tsubaki": "^1.1.1",
"xml2js": "^0.4.17", "xml2js": "^0.4.17",
"zalgolize": "^1.2.4" "zalgolize": "^1.2.4"
}, },
+126 -128
View File
@@ -1,5 +1,3 @@
/* eslint-disable indent */
const { SettingProvider } = require('discord.js-commando'); const { SettingProvider } = require('discord.js-commando');
const Sequelize = require('sequelize'); const Sequelize = require('sequelize');
@@ -16,14 +14,14 @@ class SequelizeProvider extends SettingProvider {
/** /**
* @param {SQLDatabase} db - Database for the provider * @param {SQLDatabase} db - Database for the provider
*/ */
constructor(db) { constructor(db) {
super(); super();
/** /**
* Database that will be used for storing/retrieving settings * Database that will be used for storing/retrieving settings
* @type {SQLDatabase} * @type {SQLDatabase}
*/ */
this.db = db; this.db = db;
/** /**
* Client that the provider is for (set once the client is ready, after using {@link CommandoClient#setProvider}) * Client that the provider is for (set once the client is ready, after using {@link CommandoClient#setProvider})
@@ -31,139 +29,139 @@ class SequelizeProvider extends SettingProvider {
* @type {CommandoClient} * @type {CommandoClient}
* @readonly * @readonly
*/ */
Object.defineProperty(this, 'client', { value: null, writable: true }); Object.defineProperty(this, 'client', { value: null, writable: true });
/** /**
* Settings cached in memory, mapped by guild ID (or 'global') * Settings cached in memory, mapped by guild ID (or 'global')
* @type {Map} * @type {Map}
* @private * @private
*/ */
this.settings = new Map(); this.settings = new Map();
/** /**
* Listeners on the Client, mapped by the event name * Listeners on the Client, mapped by the event name
* @type {Map} * @type {Map}
* @private * @private
*/ */
this.listeners = new Map(); this.listeners = new Map();
/** /**
* Sequelize Model Object * Sequelize Model Object
* @type {SequelizeModel} * @type {SequelizeModel}
* @private * @private
*/ */
this.model = this.db.define('settings', { this.model = this.db.define('settings', {
guild: { guild: {
type: Sequelize.STRING, type: Sequelize.STRING,
allowNull: false, allowNull: false,
unique: true, unique: true,
primaryKey: true primaryKey: true
}, },
settings: { type: Sequelize.TEXT } settings: { type: Sequelize.TEXT }
}); });
/** /**
* @external SequelizeModel * @external SequelizeModel
* @see {@link http://docs.sequelizejs.com/en/latest/api/model/} * @see {@link http://docs.sequelizejs.com/en/latest/api/model/}
*/ */
} }
async init(client) { async init(client) {
this.client = client; this.client = client;
await this.db.sync(); await this.db.sync();
// Load all settings // Load all settings
const rows = await this.model.findAll(); const rows = await this.model.findAll();
for (const row of rows) { for (const row of rows) {
let settings; let settings;
try { try {
settings = JSON.parse(row.dataValues.settings); settings = JSON.parse(row.dataValues.settings);
} catch (err) { } catch (err) {
client.emit('warn', `SequelizeProvider couldn't parse the settings stored for guild ${row.dataValues.guild}.`); client.emit('warn', `SequelizeProvider couldn't parse the settings stored for guild ${row.dataValues.guild}.`); // eslint-disable-line max-len
continue; continue;
} }
const guild = row.dataValues.guild !== '0' ? row.dataValues.guild : 'global'; const guild = row.dataValues.guild !== '0' ? row.dataValues.guild : 'global';
this.settings.set(guild, settings); this.settings.set(guild, settings);
if (guild !== 'global' && !client.guilds.has(row.dataValues.guild)) continue; if (guild !== 'global' && !client.guilds.has(row.dataValues.guild)) continue;
this.setupGuild(guild, settings); this.setupGuild(guild, settings);
} }
// Listen for changes // Listen for changes
this.listeners this.listeners
.set('commandPrefixChange', (guild, prefix) => this.set(guild, 'prefix', prefix)) .set('commandPrefixChange', (guild, prefix) => this.set(guild, 'prefix', prefix))
.set('commandStatusChange', (guild, command, enabled) => this.set(guild, `cmd-${command.name}`, enabled)) .set('commandStatusChange', (guild, command, enabled) => this.set(guild, `cmd-${command.name}`, enabled))
.set('groupStatusChange', (guild, group, enabled) => this.set(guild, `grp-${group.id}`, enabled)) .set('groupStatusChange', (guild, group, enabled) => this.set(guild, `grp-${group.id}`, enabled))
.set('guildCreate', (guild) => { .set('guildCreate', (guild) => {
const settings = this.settings.get(guild.id); const settings = this.settings.get(guild.id);
if (!settings) return; if (!settings) return;
this.setupGuild(guild.id, settings); this.setupGuild(guild.id, settings);
}) })
.set('commandRegister', (command) => { .set('commandRegister', (command) => {
for (const [guild, settings] of this.settings) { for (const [guild, settings] of this.settings) {
if (guild !== 'global' && !client.guilds.has(guild)) continue; if (guild !== 'global' && !client.guilds.has(guild)) continue;
this.setupGuildCommand(client.guilds.get(guild), command, settings); this.setupGuildCommand(client.guilds.get(guild), command, settings);
} }
}) })
.set('groupRegister', (group) => { .set('groupRegister', (group) => {
for (const [guild, settings] of this.settings) { for (const [guild, settings] of this.settings) {
if (guild !== 'global' && !client.guilds.has(guild)) continue; if (guild !== 'global' && !client.guilds.has(guild)) continue;
this.setupGuildGroup(client.guilds.get(guild), group, settings); this.setupGuildGroup(client.guilds.get(guild), group, settings);
} }
}); });
for (const [event, listener] of this.listeners) client.on(event, listener); for (const [event, listener] of this.listeners) client.on(event, listener);
} }
destroy() { destroy() {
// Remove all listeners from the client // Remove all listeners from the client
for (const [event, listener] of this.listeners) this.client.removeListener(event, listener); for (const [event, listener] of this.listeners) this.client.removeListener(event, listener);
this.listeners.clear(); this.listeners.clear();
} }
get(guild, key, defVal) { get(guild, key, defVal) {
const settings = this.settings.get(this.constructor.getGuildID(guild)); const settings = this.settings.get(this.constructor.getGuildID(guild));
return settings ? typeof settings[key] !== 'undefined' ? settings[key] : defVal : defVal; return settings ? typeof settings[key] !== 'undefined' ? settings[key] : defVal : defVal;
} }
async set(guild, key, val) { async set(guild, key, val) {
guild = this.constructor.getGuildID(guild); guild = this.constructor.getGuildID(guild);
let settings = this.settings.get(guild); let settings = this.settings.get(guild);
if (!settings) { if (!settings) {
settings = {}; settings = {};
this.settings.set(guild, settings); this.settings.set(guild, settings);
} }
settings[key] = val; settings[key] = val;
await this.model.upsert( await this.model.upsert(
{ guild: guild !== 'global' ? guild : '0', settings: JSON.stringify(settings) }, { guild: guild !== 'global' ? guild : '0', settings: JSON.stringify(settings) },
{ where: { guild: guild !== 'global' ? guild : '0' } } { where: { guild: guild !== 'global' ? guild : '0' } }
); );
if (guild === 'global') this.updateOtherShards(key, val); if (guild === 'global') this.updateOtherShards(key, val);
return val; return val;
} }
async remove(guild, key) { async remove(guild, key) {
guild = this.constructor.getGuildID(guild); guild = this.constructor.getGuildID(guild);
const settings = this.settings.get(guild); const settings = this.settings.get(guild);
if (!settings || typeof settings[key] === 'undefined') return undefined; if (!settings || typeof settings[key] === 'undefined') return undefined;
const val = settings[key]; const val = settings[key];
settings[key] = undefined; settings[key] = undefined;
await this.model.upsert( await this.model.upsert(
{ guild: guild !== 'global' ? guild : '0', settings: JSON.stringify(settings) }, { guild: guild !== 'global' ? guild : '0', settings: JSON.stringify(settings) },
{ where: { guild: guild !== 'global' ? guild : '0' } } { where: { guild: guild !== 'global' ? guild : '0' } }
); );
if (guild === 'global') this.updateOtherShards(key, undefined); if (guild === 'global') this.updateOtherShards(key, undefined);
return val; return val;
} }
async clear(guild) { async clear(guild) {
guild = this.constructor.getGuildID(guild); guild = this.constructor.getGuildID(guild);
if (!this.settings.has(guild)) return; if (!this.settings.has(guild)) return;
this.settings.delete(guild); this.settings.delete(guild);
await this.model.destroy({ where: { guild: guild !== 'global' ? guild : '0' } }); await this.model.destroy({ where: { guild: guild !== 'global' ? guild : '0' } });
} }
/** /**
* Loads all settings for a guild * Loads all settings for a guild
@@ -171,20 +169,20 @@ class SequelizeProvider extends SettingProvider {
* @param {Object} settings - Settings to load * @param {Object} settings - Settings to load
* @private * @private
*/ */
setupGuild(guild, settings) { setupGuild(guild, settings) {
if (typeof guild !== 'string') throw new TypeError('The guild must be a guild ID or "global".'); if (typeof guild !== 'string') throw new TypeError('The guild must be a guild ID or "global".');
guild = this.client.guilds.get(guild) || null; guild = this.client.guilds.get(guild) || null;
// Load the command prefix // Load the command prefix
if (typeof settings.prefix !== 'undefined') { if (typeof settings.prefix !== 'undefined') {
if (guild) guild._commandPrefix = settings.prefix; if (guild) guild._commandPrefix = settings.prefix;
else this.client._commandPrefix = settings.prefix; else this.client._commandPrefix = settings.prefix;
} }
// Load all command/group statuses // Load all command/group statuses
for (const command of this.client.registry.commands.values()) this.setupGuildCommand(guild, command, settings); for (const command of this.client.registry.commands.values()) this.setupGuildCommand(guild, command, settings);
for (const group of this.client.registry.groups.values()) this.setupGuildGroup(guild, group, settings); for (const group of this.client.registry.groups.values()) this.setupGuildGroup(guild, group, settings);
} }
/** /**
* Sets up a command's status in a guild from the guild's settings * Sets up a command's status in a guild from the guild's settings
@@ -193,15 +191,15 @@ class SequelizeProvider extends SettingProvider {
* @param {Object} settings - Settings of the guild * @param {Object} settings - Settings of the guild
* @private * @private
*/ */
setupGuildCommand(guild, command, settings) { setupGuildCommand(guild, command, settings) {
if (typeof settings[`cmd-${command.name}`] === 'undefined') return; if (typeof settings[`cmd-${command.name}`] === 'undefined') return;
if (guild) { if (guild) {
if (!guild._commandsEnabled) guild._commandsEnabled = {}; if (!guild._commandsEnabled) guild._commandsEnabled = {};
guild._commandsEnabled[command.name] = settings[`cmd-${command.name}`]; guild._commandsEnabled[command.name] = settings[`cmd-${command.name}`];
} else { } else {
command._globalEnabled = settings[`cmd-${command.name}`]; command._globalEnabled = settings[`cmd-${command.name}`];
} }
} }
/** /**
* Sets up a group's status in a guild from the guild's settings * Sets up a group's status in a guild from the guild's settings
@@ -210,15 +208,15 @@ class SequelizeProvider extends SettingProvider {
* @param {Object} settings - Settings of the guild * @param {Object} settings - Settings of the guild
* @private * @private
*/ */
setupGuildGroup(guild, group, settings) { setupGuildGroup(guild, group, settings) {
if (typeof settings[`grp-${group.id}`] === 'undefined') return; if (typeof settings[`grp-${group.id}`] === 'undefined') return;
if (guild) { if (guild) {
if (!guild._groupsEnabled) guild._groupsEnabled = {}; if (!guild._groupsEnabled) guild._groupsEnabled = {};
guild._groupsEnabled[group.id] = settings[`grp-${group.id}`]; guild._groupsEnabled[group.id] = settings[`grp-${group.id}`];
} else { } else {
group._globalEnabled = settings[`grp-${group.id}`]; group._globalEnabled = settings[`grp-${group.id}`];
} }
} }
/** /**
* Updates a global setting on all other shards if using the {@link ShardingManager}. * Updates a global setting on all other shards if using the {@link ShardingManager}.
@@ -226,16 +224,16 @@ class SequelizeProvider extends SettingProvider {
* @param {*} val - Value of the setting * @param {*} val - Value of the setting
* @private * @private
*/ */
updateOtherShards(key, val) { updateOtherShards(key, val) {
if (!this.client.shard) return; if (!this.client.shard) return;
key = JSON.stringify(key); key = JSON.stringify(key);
val = typeof val !== 'undefined' ? JSON.stringify(val) : 'undefined'; val = typeof val !== 'undefined' ? JSON.stringify(val) : 'undefined';
this.client.shard.broadcastEval(` this.client.shard.broadcastEval(`
if(this.shard.id !== ${this.client.shard.id} && this.provider && this.provider.settings) { if(this.shard.id !== ${this.client.shard.id} && this.provider && this.provider.settings) {
this.provider.settings.global[${key}] = ${val}; this.provider.settings.global[${key}] = ${val};
} }
`); `);
} }
} }
module.exports = SequelizeProvider; module.exports = SequelizeProvider;