Added database files.
This commit is contained in:
parent
6303a1b715
commit
2073e6eb14
11 changed files with 783 additions and 0 deletions
32
src/database/mongoose.js
Normal file
32
src/database/mongoose.js
Normal file
|
@ -0,0 +1,32 @@
|
|||
const mongoose = require("mongoose");
|
||||
const { log, success, error } = require("../helpers/Logger");
|
||||
|
||||
mongoose.set("strictQuery", true);
|
||||
|
||||
module.exports = {
|
||||
async initializeMongoose() {
|
||||
log(`Connecting to MongoDb...`);
|
||||
|
||||
try {
|
||||
await mongoose.connect(process.env.MONGO_CONNECTION);
|
||||
|
||||
success("Mongoose: Database connection established");
|
||||
|
||||
return mongoose.connection;
|
||||
} catch (err) {
|
||||
error("Mongoose: Failed to connect to database", err);
|
||||
process.exit(1);
|
||||
}
|
||||
},
|
||||
|
||||
schemas: {
|
||||
Giveaways: require("./schemas/Giveaways"),
|
||||
Guild: require("./schemas/Guild"),
|
||||
Member: require("./schemas/Member"),
|
||||
ReactionRoles: require("./schemas/ReactionRoles").model,
|
||||
ModLog: require("./schemas/ModLog").model,
|
||||
TranslateLog: require("./schemas/TranslateLog").model,
|
||||
User: require("./schemas/User"),
|
||||
Suggestions: require("./schemas/Suggestions").model,
|
||||
},
|
||||
};
|
39
src/database/schemas/AutomodLogs.js
Normal file
39
src/database/schemas/AutomodLogs.js
Normal file
|
@ -0,0 +1,39 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const reqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
}
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: reqString,
|
||||
member_id: reqString,
|
||||
content: String,
|
||||
reason: String,
|
||||
strikes: Number,
|
||||
},
|
||||
{
|
||||
versionKey: false,
|
||||
autoIndex: false,
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: false,
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.Model("automod-logs", Schema);
|
||||
|
||||
module.exports = {
|
||||
addAutoModLogToDb: async (member, content, reason, strikes) => {
|
||||
if (!member) throw new Error("Member is undefined");
|
||||
await new Model({
|
||||
guild_id: member.guild.id,
|
||||
member_id: member.id,
|
||||
content,
|
||||
reason,
|
||||
strikes,
|
||||
}).save();
|
||||
},
|
||||
};
|
64
src/database/schemas/Giveaways.js
Normal file
64
src/database/schemas/Giveaways.js
Normal file
|
@ -0,0 +1,64 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
messageId: String,
|
||||
channelId: String,
|
||||
guildId: String,
|
||||
startAt: Number,
|
||||
endAt: Number,
|
||||
ended: Boolean,
|
||||
winnerCount: Number,
|
||||
prize: String,
|
||||
messages: {
|
||||
giveaway: String,
|
||||
giveawayEnded: String,
|
||||
inviteToParticipate: String,
|
||||
drawing: String,
|
||||
dropMessage: String,
|
||||
winMessage: mongoose.Mixed,
|
||||
embedFooter: mongoose.Mixed,
|
||||
noWinner: String,
|
||||
winners: String,
|
||||
endedAt: String,
|
||||
hostedBy: String,
|
||||
},
|
||||
thumbnail: String,
|
||||
hostedBy: String,
|
||||
winnerIds: { type: [String], default: undefined },
|
||||
reaction: mongoose.Mixed,
|
||||
botsCanWin: Boolean,
|
||||
embedColor: mongoose.Mixed,
|
||||
embedColorEnd: mongoose.Mixed,
|
||||
exemptPermissions: { type: [], default: undefined },
|
||||
exemptMembers: String,
|
||||
bonusEntries: String,
|
||||
extraData: mongoose.Mixed,
|
||||
lastChance: {
|
||||
enabled: Boolean,
|
||||
content: String,
|
||||
threshold: Number,
|
||||
embedColor: mongoose.Mixed,
|
||||
},
|
||||
pauseOptions: {
|
||||
isPaused: Boolean,
|
||||
content: String,
|
||||
unPauseAfter: Number,
|
||||
embedColor: mongoose.Mixed,
|
||||
durationAfterPause: Number,
|
||||
},
|
||||
isDrop: Boolean,
|
||||
allowedMentions: {
|
||||
parse: { type: [String], default: undefined },
|
||||
users: { type: [String], default: undefined },
|
||||
roles: { type: [String], default: undefined },
|
||||
},
|
||||
},
|
||||
{
|
||||
id: false,
|
||||
autoIndex: false,
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("giveaways", Schema);
|
||||
module.exports = Model;
|
153
src/database/schemas/Guild.js
Normal file
153
src/database/schemas/Guild.js
Normal file
|
@ -0,0 +1,153 @@
|
|||
const mongoose = require("mongoose");
|
||||
const { CACHE_SIZE, PREFIX_COMMANDS, STATS } = require("@root/config.js");
|
||||
const FixedSizeMap = require("fixedsize-map");
|
||||
const { getUser } = require("./User");
|
||||
|
||||
const cache = new FixedSizeMap(CACHE_SIZE.GUILDS);
|
||||
|
||||
const Schema = new mongoose.Schema({
|
||||
_id: String,
|
||||
data: {
|
||||
name: String,
|
||||
region: String,
|
||||
owner: { type: String, ref: "users" },
|
||||
joinedAt: Date,
|
||||
leftAt: Date,
|
||||
bots: { type: Number, default: 0 },
|
||||
},
|
||||
prefix: { type: String, default: PREFIX_COMMANDS.DEFAULT_PREFIX },
|
||||
stats: {
|
||||
enabled: Boolean,
|
||||
xp: {
|
||||
message: { type: String, default: STATS.DEFAULT_LVL_UP_MSG },
|
||||
channel: String,
|
||||
},
|
||||
},
|
||||
ticket: {
|
||||
log_channel: String,
|
||||
limit: { type: Number, default: 10 },
|
||||
categories: [
|
||||
{
|
||||
_id: false,
|
||||
name: String,
|
||||
staff_roles: [String],
|
||||
},
|
||||
],
|
||||
},
|
||||
automod: {
|
||||
debug: Boolean,
|
||||
strikes: { type: Number, default: 10 },
|
||||
action: { type: String, default: "TIMEOUT" },
|
||||
wh_channels: [String],
|
||||
anti_attachments: Boolean,
|
||||
anti_invites: Boolean,
|
||||
anti_links: Boolean,
|
||||
anti_spam: Boolean,
|
||||
anti_ghostping: Boolean,
|
||||
anti_massmention: Number,
|
||||
max_lines: Number,
|
||||
},
|
||||
invite: {
|
||||
tracking: Boolean,
|
||||
ranks: [
|
||||
{
|
||||
invites: { type: Number, required: true },
|
||||
_id: { type: String, required: true },
|
||||
},
|
||||
],
|
||||
},
|
||||
flag_translation: {
|
||||
enabled: Boolean,
|
||||
},
|
||||
modlog_channel: String,
|
||||
max_warn: {
|
||||
action: {
|
||||
type: String,
|
||||
enum: ["TIMEOUT", "KICK", "BAN"],
|
||||
default: "KICK",
|
||||
},
|
||||
limit: { type: Number, default: 5 },
|
||||
},
|
||||
counters: [
|
||||
{
|
||||
_id: false,
|
||||
counter_type: String,
|
||||
name: String,
|
||||
channel_id: String,
|
||||
},
|
||||
],
|
||||
welcome: {
|
||||
enabled: Boolean,
|
||||
channel: String,
|
||||
content: String,
|
||||
embed: {
|
||||
description: String,
|
||||
color: String,
|
||||
thumbnail: Boolean,
|
||||
footer: String,
|
||||
image: String,
|
||||
},
|
||||
},
|
||||
farewell: {
|
||||
enabled: Boolean,
|
||||
channel: String,
|
||||
content: String,
|
||||
embed: {
|
||||
description: String,
|
||||
color: String,
|
||||
thumbnail: Boolean,
|
||||
footer: String,
|
||||
image: String,
|
||||
},
|
||||
},
|
||||
autorole: String,
|
||||
suggestions: {
|
||||
enabled: Boolean,
|
||||
channel_id: String,
|
||||
approved_channel: String,
|
||||
rejected_channel: String,
|
||||
staff_roles: [String],
|
||||
},
|
||||
});
|
||||
|
||||
const Model = mongoose.model("guild", Schema);
|
||||
|
||||
module.exports = {
|
||||
/**
|
||||
* @param {import('discord.js').Guild} guild
|
||||
*/
|
||||
getSettings: async (guild) => {
|
||||
if (!guild) throw new Error("Guild is undefined");
|
||||
if (!guild.id) throw new Error("Guild Id is undefined");
|
||||
|
||||
const cached = cache.get(guild.id);
|
||||
if (cached) return cached;
|
||||
|
||||
let guildData = await Model.findById(guild.id);
|
||||
if (!guildData) {
|
||||
// save owner details
|
||||
guild
|
||||
.fetchOwner()
|
||||
.then(async (owner) => {
|
||||
const userDb = await getUser(owner);
|
||||
await userDb.save();
|
||||
})
|
||||
.catch((ex) => {});
|
||||
|
||||
// create a new guild model
|
||||
guildData = new Model({
|
||||
_id: guild.id,
|
||||
data: {
|
||||
name: guild.name,
|
||||
region: guild.preferredLocale,
|
||||
owner: guild.ownerId,
|
||||
joinedAt: guild.joinedAt,
|
||||
},
|
||||
});
|
||||
|
||||
await guildData.save();
|
||||
}
|
||||
cache.add(guild.id, guildData);
|
||||
return guildData;
|
||||
},
|
||||
};
|
72
src/database/schemas/Member.js
Normal file
72
src/database/schemas/Member.js
Normal file
|
@ -0,0 +1,72 @@
|
|||
const mongoose = require("mongoose");
|
||||
const { CACHE_SIZE } = require("@root/config.js");
|
||||
const FixedSizeMap = require("fixedsize-map");
|
||||
|
||||
const cache = new FixedSizeMap(CACHE_SIZE.MEMBERS);
|
||||
|
||||
const ReqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
};
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: ReqString,
|
||||
member_id: ReqString,
|
||||
strikes: { type: Number, default: 0 },
|
||||
warnings: { type: Number, default: 0 },
|
||||
invite_data: {
|
||||
inviter: String,
|
||||
code: String,
|
||||
tracked: { type: Number, default: 0 },
|
||||
fake: { type: Number, default: 0 },
|
||||
left: { type: Number, default: 0 },
|
||||
added: { type: Number, default: 0 },
|
||||
},
|
||||
},
|
||||
{
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: "updated_at",
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("members", Schema);
|
||||
|
||||
module.exports = {
|
||||
getMember: async (guildId, memberId) => {
|
||||
const key = `${guildId}|${memberId}`;
|
||||
if (cache.contains(key)) return cache.get(key);
|
||||
|
||||
let member = await Model.findOne({ guild_id: guildId, member_id: memberId });
|
||||
if (!member) {
|
||||
member = new Model({
|
||||
guild_id: guildId,
|
||||
member_id: memberId,
|
||||
});
|
||||
}
|
||||
|
||||
cache.add(key, member);
|
||||
return member;
|
||||
},
|
||||
|
||||
getInvitesLb: async (guildId, limit = 10) =>
|
||||
Model.aggregate([
|
||||
{ $match: { guild_id: guildId } },
|
||||
{
|
||||
$project: {
|
||||
member_id: "$member_id",
|
||||
invites: {
|
||||
$subtract: [
|
||||
{ $add: ["$invite_data.tracked", "$invite_data.added"] },
|
||||
{ $add: ["$invite_data.left", "$invite_data.fake"] },
|
||||
],
|
||||
},
|
||||
},
|
||||
},
|
||||
{ $match: { invites: { $gt: 0 } } },
|
||||
{ $sort: { invites: -1 } },
|
||||
{ $limit: limit },
|
||||
]),
|
||||
};
|
66
src/database/schemas/MemberStats.js
Normal file
66
src/database/schemas/MemberStats.js
Normal file
|
@ -0,0 +1,66 @@
|
|||
const mongoose = require("mongoose");
|
||||
const { CACHE_SIZE } = require("@root/config.js");
|
||||
const FixedSizeMap = require("fixedsize-map");
|
||||
|
||||
const cache = new FixedSizeMap(CACHE_SIZE.MEMBERS);
|
||||
|
||||
const ReqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
};
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: ReqString,
|
||||
member_id: ReqString,
|
||||
messages: { type: Number, default: 0 },
|
||||
voice: {
|
||||
connections: { type: Number, default: 0 },
|
||||
time: { type: Number, default: 0 },
|
||||
},
|
||||
commands: {
|
||||
prefix: { type: Number, default: 0 },
|
||||
slash: { type: Number, default: 0 },
|
||||
},
|
||||
contexts: {
|
||||
message: { type: Number, default: 0 },
|
||||
user: { type: Number, default: 0 },
|
||||
},
|
||||
xp: { type: Number, default: 0 },
|
||||
level: { type: Number, default: 1 },
|
||||
},
|
||||
{
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: "updated_at",
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("member-stats", Schema);
|
||||
|
||||
module.exports = {
|
||||
getMemberStats: async (guildId, memberId) => {
|
||||
const key = `${guildId}|${memberId}`;
|
||||
if (cache.contains(key)) return cache.get(key);
|
||||
|
||||
let member = await Model.findOne({ guild_id: guildId, member_id: memberId });
|
||||
if (!member) {
|
||||
member = new Model({
|
||||
guild_id: guildId,
|
||||
member_id: memberId,
|
||||
});
|
||||
}
|
||||
|
||||
cache.add(key, member);
|
||||
return member;
|
||||
},
|
||||
|
||||
getXpLb: async (guildId, limit = 10) =>
|
||||
Model.find({
|
||||
guild_id: guildId,
|
||||
})
|
||||
.limit(limit)
|
||||
.sort({ level: -1, xp: -1 })
|
||||
.lean(),
|
||||
};
|
78
src/database/schemas/ModLog.js
Normal file
78
src/database/schemas/ModLog.js
Normal file
|
@ -0,0 +1,78 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const reqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
};
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: reqString,
|
||||
member_id: String,
|
||||
reason: String,
|
||||
admin: {
|
||||
id: reqString,
|
||||
tag: reqString,
|
||||
},
|
||||
type: {
|
||||
type: String,
|
||||
required: true,
|
||||
enum: [
|
||||
"PURGE",
|
||||
"WARN",
|
||||
"TIMEOUT",
|
||||
"UNTIMEOUT",
|
||||
"KICK",
|
||||
"SOFTBAN",
|
||||
"BAN",
|
||||
"UNBAN",
|
||||
"VMUTE",
|
||||
"VUNMUTE",
|
||||
"DEAFEN",
|
||||
"UNDEAFEN",
|
||||
"DISCONNECT",
|
||||
"MOVE",
|
||||
],
|
||||
},
|
||||
},
|
||||
{
|
||||
versionKey: false,
|
||||
autoIndex: false,
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: false,
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("mod-logs", Schema);
|
||||
|
||||
module.exports = {
|
||||
model: Model,
|
||||
|
||||
addModLogToDb: async (admin, target, reason, type) =>
|
||||
await new Model({
|
||||
guild_id: admin.guild.id,
|
||||
member_id: target.id,
|
||||
reason,
|
||||
admin: {
|
||||
id: admin.id,
|
||||
tag: admin.user.tag,
|
||||
},
|
||||
type,
|
||||
}).save(),
|
||||
|
||||
getWarningLogs: async (guildId, targetId) =>
|
||||
Model.find({
|
||||
guild_id: guildId,
|
||||
member_id: targetId,
|
||||
type: "WARN",
|
||||
}).lean(),
|
||||
|
||||
clearWarningLogs: async (guildId, targetId) =>
|
||||
Model.deleteMany({
|
||||
guild_id: guildId,
|
||||
member_id: targetId,
|
||||
type: "WARN",
|
||||
}),
|
||||
};
|
92
src/database/schemas/ReactionRoles.js
Normal file
92
src/database/schemas/ReactionRoles.js
Normal file
|
@ -0,0 +1,92 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const reqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
};
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: reqString,
|
||||
channel_id: reqString,
|
||||
message_id: reqString,
|
||||
roles: [
|
||||
{
|
||||
_id: false,
|
||||
emote: reqString,
|
||||
role_id: reqString,
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: false,
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("reaction-roles", Schema);
|
||||
|
||||
// Cache
|
||||
const rrCache = new Map();
|
||||
const getKey = (guildId, channelId, messageId) => `${guildId}|${channelId}|${messageId}`;
|
||||
|
||||
module.exports = {
|
||||
model: Model,
|
||||
|
||||
cacheReactionRoles: async (client) => {
|
||||
// clear previous cache
|
||||
rrCache.clear();
|
||||
|
||||
// load all docs from database
|
||||
const docs = await Model.find().lean();
|
||||
|
||||
// validate and cache docs
|
||||
for (const doc of docs) {
|
||||
const guild = client.guilds.cache.get(doc.guild_id);
|
||||
if (!guild) {
|
||||
// await Model.deleteMany({ guild_id: doc.guild_id });
|
||||
continue;
|
||||
}
|
||||
if (!guild.channels.cache.has(doc.channel_id)) {
|
||||
// await Model.deleteMany({ guild_id: doc.guild_id, channel_id: doc.channel_id });
|
||||
continue;
|
||||
}
|
||||
const key = getKey(doc.guild_id, doc.channel_id, doc.message_id);
|
||||
rrCache.set(key, doc.roles);
|
||||
}
|
||||
},
|
||||
|
||||
getReactionRoles: (guildId, channelId, messageId) => rrCache.get(getKey(guildId, channelId, messageId)) || [],
|
||||
|
||||
addReactionRole: async (guildId, channelId, messageId, emote, roleId) => {
|
||||
const filter = { guild_id: guildId, channel_id: channelId, message_id: messageId };
|
||||
|
||||
// Pull if existing configuration is present
|
||||
await Model.updateOne(filter, { $pull: { roles: { emote } } });
|
||||
|
||||
const data = await Model.findOneAndUpdate(
|
||||
filter,
|
||||
{
|
||||
$push: {
|
||||
roles: { emote, role_id: roleId },
|
||||
},
|
||||
},
|
||||
{ upsert: true, new: true }
|
||||
).lean();
|
||||
|
||||
// update cache
|
||||
const key = getKey(guildId, channelId, messageId);
|
||||
rrCache.set(key, data.roles);
|
||||
},
|
||||
|
||||
removeReactionRole: async (guildId, channelId, messageId) => {
|
||||
await Model.deleteOne({
|
||||
guild_id: guildId,
|
||||
channel_id: channelId,
|
||||
message_id: messageId,
|
||||
});
|
||||
rrCache.delete(getKey(guildId, channelId, messageId));
|
||||
},
|
||||
};
|
70
src/database/schemas/Suggestions.js
Normal file
70
src/database/schemas/Suggestions.js
Normal file
|
@ -0,0 +1,70 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: String,
|
||||
channel_id: String,
|
||||
message_id: String,
|
||||
user_id: String,
|
||||
suggestion: String,
|
||||
status: {
|
||||
type: String,
|
||||
enum: ["PENDING", "APPROVED", "REJECTED", "DELETED"],
|
||||
default: "PENDING",
|
||||
},
|
||||
stats: {
|
||||
upvotes: { type: Number, default: 0 },
|
||||
downvotes: { type: Number, default: 0 },
|
||||
},
|
||||
status_updates: [
|
||||
{
|
||||
_id: false,
|
||||
user_id: String,
|
||||
status: {
|
||||
type: String,
|
||||
enum: ["APPROVED", "REJECTED", "DELETED"],
|
||||
},
|
||||
reason: String,
|
||||
timestamp: { type: Date, default: new Date() },
|
||||
},
|
||||
],
|
||||
},
|
||||
{
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: "updated_at",
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("suggestions", Schema);
|
||||
|
||||
module.exports = {
|
||||
model: Model,
|
||||
|
||||
addSuggestion: async (message, userId, suggestion) => {
|
||||
return new Model({
|
||||
guild_id: message.guildId,
|
||||
channel_id: message.channelId,
|
||||
message_id: message.id,
|
||||
user_id: userId,
|
||||
suggestion: suggestion,
|
||||
}).save();
|
||||
},
|
||||
|
||||
findSuggestion: async (guildId, messageId) => {
|
||||
return Model.findOne({ guild_id: guildId, message_id: messageId });
|
||||
},
|
||||
|
||||
deleteSuggestionDb: async (guildId, messageId, memberId, reason) => {
|
||||
return Model.updateOne(
|
||||
{ guild_id: guildId, message_id: messageId },
|
||||
{
|
||||
status: "DELETED",
|
||||
$push: {
|
||||
status_updates: { user_id: memberId, status: "DELETED", reason },
|
||||
},
|
||||
}
|
||||
);
|
||||
},
|
||||
};
|
45
src/database/schemas/TranslateLog.js
Normal file
45
src/database/schemas/TranslateLog.js
Normal file
|
@ -0,0 +1,45 @@
|
|||
const mongoose = require("mongoose");
|
||||
|
||||
const reqString = {
|
||||
type: String,
|
||||
required: true,
|
||||
};
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
guild_id: reqString,
|
||||
channel_id: reqString,
|
||||
message_id: reqString,
|
||||
emoji: reqString,
|
||||
},
|
||||
{
|
||||
versionKey: false,
|
||||
autoIndex: false,
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: false,
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("logs-translation", Schema);
|
||||
|
||||
module.exports = {
|
||||
model: Model,
|
||||
|
||||
isTranslated: async (message, code) =>
|
||||
Model.findOne({
|
||||
guild_id: message.guildId,
|
||||
channel_id: message.channelId,
|
||||
message_id: message.id,
|
||||
emoji: code,
|
||||
}).lean(),
|
||||
|
||||
logTranslation: async (message, code) =>
|
||||
new Model({
|
||||
guild_id: message.guildId,
|
||||
channel_id: message.channelId,
|
||||
message_id: message.id,
|
||||
emoji: code,
|
||||
}).save(),
|
||||
};
|
72
src/database/schemas/User.js
Normal file
72
src/database/schemas/User.js
Normal file
|
@ -0,0 +1,72 @@
|
|||
const mongoose = require("mongoose");
|
||||
const { CACHE_SIZE } = require("@root/config.js");
|
||||
const FixedSizeMap = require("fixedsize-map");
|
||||
|
||||
const cache = new FixedSizeMap(CACHE_SIZE.USERS);
|
||||
|
||||
const Schema = new mongoose.Schema(
|
||||
{
|
||||
_id: String,
|
||||
username: String,
|
||||
discriminator: String,
|
||||
logged: Boolean,
|
||||
coins: { type: Number, default: 0 },
|
||||
bank: { type: Number, default: 0 },
|
||||
reputation: {
|
||||
received: { type: Number, default: 0 },
|
||||
given: { type: Number, default: 0 },
|
||||
timestamp: Date,
|
||||
},
|
||||
daily: {
|
||||
streak: { type: Number, default: 0 },
|
||||
timestamp: Date,
|
||||
},
|
||||
},
|
||||
{
|
||||
timestamps: {
|
||||
createdAt: "created_at",
|
||||
updatedAt: "updated_at",
|
||||
},
|
||||
}
|
||||
);
|
||||
|
||||
const Model = mongoose.model("user", Schema);
|
||||
|
||||
module.exports = {
|
||||
/**
|
||||
* @param {import('discord.js').User} user
|
||||
*/
|
||||
getUser: async (user) => {
|
||||
if (!user) throw new Error("User is required.");
|
||||
if (!user.id) throw new Error("User Id is required.");
|
||||
|
||||
const cached = cache.get(user.id);
|
||||
if (cached) return cached;
|
||||
|
||||
let userDb = await Model.findById(user.id);
|
||||
if (!userDb) {
|
||||
userDb = new Model({
|
||||
_id: user.id,
|
||||
username: user.username,
|
||||
discriminator: user.discriminator,
|
||||
});
|
||||
}
|
||||
|
||||
// Temporary fix for users who where added to DB before v5.0.0
|
||||
// Update username and discriminator in previous DB
|
||||
else if (!userDb.username || !userDb.discriminator) {
|
||||
userDb.username = user.username;
|
||||
userDb.discriminator = user.discriminator;
|
||||
}
|
||||
|
||||
cache.add(user.id, userDb);
|
||||
return userDb;
|
||||
},
|
||||
|
||||
getReputationLb: async (limit = 10) => {
|
||||
return Model.find({ "reputation.received": { $gt: 0 } })
|
||||
.sort({ "reputation.received": -1, "reputation.given": 1 })
|
||||
.limit(limit)
|
||||
.lean();
|
||||
},
|
||||
};
|
Loading…
Reference in a new issue