forked from engineering/cloudservices
Merge branch 'master' of https://gitlab.libraryofcode.org/engineering/cloudservices
commit
e342734317
|
@ -1,3 +1,4 @@
|
|||
import { randomBytes } from 'crypto';
|
||||
import { AccountInterface } from '../models';
|
||||
import { Client } from '..';
|
||||
|
||||
|
@ -22,20 +23,22 @@ export default class AccountUtil {
|
|||
let passHash = await this.client.util.createHash(tempPass); passHash = passHash.replace(/[$]/g, '\\$').replace('\n', '');
|
||||
const acctName = this.client.users.get(data.userID).username.replace(/[!@#$%^&*(),.?":{}|<>]/g, '-').replace(/\s/g, '-');
|
||||
const etcPasswd = `${acctName},${data.userID},,`;
|
||||
const code = randomBytes(3).toString('hex').toUpperCase();
|
||||
|
||||
const accountInterface = await this.client.util.createAccount(passHash, etcPasswd, data.username, data.userID, data.emailAddress, moderator);
|
||||
const accountInterface = await this.client.util.createAccount(passHash, etcPasswd, data.username, data.userID, data.emailAddress, moderator, code);
|
||||
await this.client.util.createModerationLog(data.userID, moderatorMember, 0);
|
||||
|
||||
this.client.util.transport.sendMail({
|
||||
to: data.emailAddress,
|
||||
from: 'Library of Code sp-us | Cloud Services <help@libraryofcode.org>',
|
||||
subject: 'Your account has been created',
|
||||
subject: 'Your account has been created!',
|
||||
html: `
|
||||
<body>
|
||||
<style>* {font-family: 'Calibri';}</style>
|
||||
<h1>Library of Code | Cloud Services</h1>
|
||||
<h2>Your Cloud Account has been created, welcome! Please see below for some details regarding your account and our services</h2>
|
||||
<p><b>Username:</b> ${data.username}</p>
|
||||
<p><b>Support Key:</b> ${code} || <i>You may be asked for this support key when contacting Library of Code, please keep the code in a safe area.</i></p>
|
||||
<p><b>SSH Login:</b> <pre><code style="font-family: Courier;">ssh ${data.username}@cloud.libraryofcode.org</code></pre>
|
||||
<h2>Useful information</h2>
|
||||
<h3>How to log in:</h3>
|
||||
|
@ -61,13 +64,15 @@ export default class AccountUtil {
|
|||
`,
|
||||
});
|
||||
|
||||
this.client.guilds.get('446067825673633794').members.get(data.userID).addRole('546457886440685578');
|
||||
const dmChannel = await this.client.getDMChannel(data.userID).catch();
|
||||
dmChannel.createMessage('<:loc:607695848612167700> **Thank you for creating an account with us!** <:loc:607695848612167700>\n'
|
||||
+ `Please log into your account by running \`ssh ${data.username}@cloud.libraryofcode.org\` in your terminal, then use the password \`${tempPass}\` to log in.\n`
|
||||
+ `You will be asked to change your password, \`(current) UNIX password\` is \`${tempPass}\`, then create a password that is at least 12 characters long, with at least one number, special character, and an uppercase letter\n`
|
||||
+ 'Bear in mind that when you enter your password, it will be blank, so be careful not to type in your password incorrectly.\n'
|
||||
+ 'You may now return to Modmail, and continue setting up your account from there.\n\n'
|
||||
+ 'An email containing some useful information has also been sent').catch();
|
||||
+ 'An email containing some useful information has also been sent.\n'
|
||||
+ `Your support key is \`${code}\`. Pin this message, you may need this key to contact Library of Code in the future.`).catch();
|
||||
return { account: accountInterface, tempPass };
|
||||
}
|
||||
}
|
||||
|
|
|
@ -147,12 +147,12 @@ export default class Util {
|
|||
return tempPass;
|
||||
}
|
||||
|
||||
public async createAccount(hash: string, etcPasswd: string, username: string, userID: string, emailAddress: string, moderatorID: string): Promise<AccountInterface> {
|
||||
public async createAccount(hash: string, etcPasswd: string, username: string, userID: string, emailAddress: string, moderatorID: string, code: string): Promise<AccountInterface> {
|
||||
await this.exec(`useradd -m -p ${hash} -c ${etcPasswd} -s /bin/bash ${username}`);
|
||||
await this.exec(`chage -d0 ${username}`);
|
||||
|
||||
const account = new this.client.db.Account({
|
||||
username, userID, emailAddress, createdBy: moderatorID, createdAt: new Date(), locked: false, tier: 1, ssInit: false, homepath: `/home/${username}`,
|
||||
username, userID, emailAddress, createdBy: moderatorID, createdAt: new Date(), locked: false, tier: 1, supportKey: code, ssInit: false, homepath: `/home/${username}`,
|
||||
});
|
||||
return account.save();
|
||||
}
|
||||
|
|
|
@ -24,17 +24,17 @@ export default class CreateAccount extends Command {
|
|||
try {
|
||||
if (message.channel instanceof PrivateChannel || message.channel instanceof GroupChannel) return message; // Stop TS being gay
|
||||
if (!args[2]) return this.client.commands.get('help').run(message, [this.name]);
|
||||
if (!message.channel.guild.members.has(args[0])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***User not found***`);
|
||||
if (message.channel.guild.members.get(args[0]).bot) return message.channel.createMessage(`${this.client.stores.emojis.error} ***I cannot create accounts for bots***`);
|
||||
if (!message.channel.guild.members.has(args[0])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***User not found.***`);
|
||||
if (message.channel.guild.members.get(args[0]).bot) return message.channel.createMessage(`${this.client.stores.emojis.error} ***I cannot create accounts for bots.***`);
|
||||
const checkUser = await this.client.db.Account.findOne({ userID: args[0] });
|
||||
if (checkUser) return message.channel.createMessage(`${this.client.stores.emojis.error} ***<@${args[0]}> already has an account***`);
|
||||
if (checkUser) return message.channel.createMessage(`${this.client.stores.emojis.error} ***<@${args[0]}> already has an account.***`);
|
||||
const checkEmail = await this.client.db.Account.findOne({ emailAddress: args[1] });
|
||||
if (checkEmail) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Account already exists with this email address***`);
|
||||
if (checkEmail) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Account already exists with this email address.***`);
|
||||
const checkAccount = await this.client.db.Account.findOne({ username: args[2] });
|
||||
if (checkAccount) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Account already exists with this username***`);
|
||||
if (checkAccount) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Account already exists with this username.***`);
|
||||
|
||||
if (!this.client.util.isValidEmail(args[1])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Invalid email address supplied***`);
|
||||
if (!/^[a-z][-a-z0-9]*$/.test(args[2])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Invalid username supplied***`);
|
||||
if (!this.client.util.isValidEmail(args[1])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Invalid email address supplied.***`);
|
||||
if (!/^[a-z][-a-z0-9]*$/.test(args[2])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Invalid username supplied.***`);
|
||||
|
||||
const confirmation = await message.channel.createMessage(`${this.client.stores.emojis.loading} ***Creating account...***`);
|
||||
const data = await this.client.util.accounts.createAccount({ userID: args[0], username: args[2], emailAddress: args[1] }, message.author.id);
|
||||
|
|
|
@ -0,0 +1,43 @@
|
|||
/* eslint-disable consistent-return */
|
||||
import { randomBytes } from 'crypto';
|
||||
import { Message } from 'eris';
|
||||
import { Client } from '..';
|
||||
import { Command, RichEmbed } from '../class';
|
||||
|
||||
export default class EmailCode extends Command {
|
||||
constructor(client: Client) {
|
||||
super(client);
|
||||
this.name = 'emailcode';
|
||||
this.description = 'Sends a code to an email address to use for address verification.';
|
||||
this.usage = `${this.client.config.prefix}emailcode <email address>`;
|
||||
this.permissions = { roles: ['446104438969466890'] };
|
||||
this.aliases = ['code'];
|
||||
this.enabled = true;
|
||||
}
|
||||
|
||||
public async run(message: Message, args: string[]) {
|
||||
try {
|
||||
const code = randomBytes(5).toString('hex');
|
||||
if (!this.client.util.isValidEmail(args[0])) return message.channel.createMessage(`${this.client.stores.emojis.error} ***Invalid email address supplied.***`);
|
||||
this.client.util.transport.sendMail({
|
||||
to: args[0],
|
||||
from: 'Library of Code sp-us | Cloud Services <help@libraryofcode.org>',
|
||||
subject: 'Email Verification Code',
|
||||
html: `
|
||||
<body>
|
||||
<style>* {font-family: 'Calibri';}</style>
|
||||
<h1>Library of Code | Cloud Services</h1>
|
||||
<p>Please provide the code provided below to the Staff member working with you on account creation.</p>
|
||||
<h2>${code}</h2>
|
||||
<h3>Want to support us?</h3>
|
||||
<p>You can support us on Patreon! Head to <a target="_blank" href="https://www.patreon.com/libraryofcode">our Patreon page</a> and feel free to donate as much or as little as you want!<br>Donating $5 or more will grant you Tier 3, which means we will manage your account at your request, longer certificates, increased Tier limits as well as some roles in the server!</p>
|
||||
<b><i>Library of Code sp-us | Support Team</i></b>
|
||||
</body>
|
||||
`,
|
||||
});
|
||||
message.channel.createMessage(`***${this.client.stores.emojis.success} Code: \`${code}\` | Email Address: ${args[0]}***`);
|
||||
} catch (error) {
|
||||
await this.client.util.handleError(error, message, this);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -4,6 +4,7 @@ export { default as createaccount } from './createaccount';
|
|||
export { default as cwg } from './cwg';
|
||||
export { default as deleteaccount } from './deleteaccount';
|
||||
export { default as disk } from './disk';
|
||||
export { default as emailcode } from './emailcode';
|
||||
export { default as eval } from './eval';
|
||||
export { default as exec } from './exec';
|
||||
export { default as help } from './help';
|
||||
|
@ -19,6 +20,7 @@ export { default as resetpassword } from './resetpassword';
|
|||
export { default as restart } from './restart';
|
||||
export { default as securesign } from './securesign';
|
||||
export { default as sysinfo } from './sysinfo';
|
||||
export { default as tier } from './tier';
|
||||
export { default as unban } from './unban';
|
||||
export { default as unlock } from './unlock';
|
||||
export { default as warn } from './warn';
|
||||
|
|
|
@ -0,0 +1,41 @@
|
|||
/* eslint-disable consistent-return */
|
||||
import { Message } from 'eris';
|
||||
import { Client } from '..';
|
||||
import { Command, RichEmbed } from '../class';
|
||||
|
||||
export default class Tier extends Command {
|
||||
constructor(client: Client) {
|
||||
super(client);
|
||||
this.name = 'tier';
|
||||
this.description = 'Changes the tier level for an account.';
|
||||
this.usage = `${this.client.config.prefix}tier <username | user ID> <1 | 2 | 3>`;
|
||||
this.permissions = { roles: ['446104438969466890'] };
|
||||
this.enabled = true;
|
||||
}
|
||||
|
||||
public async run(message: Message, args: string[]) {
|
||||
try {
|
||||
if (!args.length) return this.client.commands.get('help').run(message, [this.name]);
|
||||
const edit = await message.channel.createMessage(`***${this.client.stores.emojis.loading} Editing tier...***`);
|
||||
const account = await this.client.db.Account.findOne({ $or: [{ username: args[0] }, { userID: args[0].replace(/[<@!>]/gi, '') }] });
|
||||
if (!account) return edit.edit(`***${this.client.stores.emojis.error} Cannot find user.***`);
|
||||
if (account.root) return edit.edit(`***${this.client.stores.emojis.error} Permission denied.***`);
|
||||
if (Number.isNaN(Number(args[1]))) return edit.edit(`***${this.client.stores.emojis.error} The tier you provided is not a valid number. It should be between 1 and 3.***`);
|
||||
if (Number(args[1]) > 3 || Number(args[1]) < 1) return edit.edit(`***${this.client.stores.emojis.error} You can only choose a Tier between 1 and 3.***`);
|
||||
message.delete();
|
||||
await account.updateOne({ $set: { tier: Number(args[1]) } });
|
||||
message.channel.createMessage(`***${this.client.stores.emojis.success} Tier for ${account.username} has been changed to ${args[1]}.***`);
|
||||
const embed = new RichEmbed();
|
||||
embed.setTitle('Cloud Account | Tier Change');
|
||||
embed.setColor('#0099ff');
|
||||
embed.addField('User', `${account.username} | <@${account.userID}>`, true);
|
||||
embed.addField('Moderator', `<@${message.author.id}>`, true);
|
||||
embed.addField('Old Tier -> New Tier', `${account.tier} -> ${args[1]}`, true);
|
||||
embed.setFooter(this.client.user.username, this.client.user.avatarURL);
|
||||
embed.setTimestamp();
|
||||
this.client.createMessage('580950455581147146', { embed }); this.client.getDMChannel(account.userID).then((channel) => channel.createMessage({ embed })).catch();
|
||||
} catch (error) {
|
||||
await this.client.util.handleError(error, message, this);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -39,6 +39,7 @@ export default class Whois extends Command {
|
|||
embed.addField('ID', account.userID, true);
|
||||
embed.addField('Email Address', account.emailAddress, true);
|
||||
embed.addField('Tier', String(account.tier), true);
|
||||
embed.addField('Support Key', account.supportKey, true);
|
||||
embed.addField('Created By', `<@${this.client.users.get(account.createdBy).id}>`, true);
|
||||
embed.addField('Created At', moment(account.createdAt).format('dddd, MMMM Do YYYY, h:mm:ss A'), true);
|
||||
const cpuUsage = await this.client.util.exec(`top -b -n 1 -u ${account.username} | awk 'NR>7 { sum += $9; } END { print sum; }'`);
|
||||
|
|
|
@ -1,5 +1,6 @@
|
|||
/* eslint-disable no-await-in-loop */
|
||||
import { Client } from '..';
|
||||
import { RichEmbed } from '../class';
|
||||
|
||||
export default function checkStaffStatus(client: Client) {
|
||||
setInterval(async () => {
|
||||
|
@ -26,8 +27,17 @@ export default function checkStaffStatus(client: Client) {
|
|||
await client.db.Account.updateOne({ username: acc.username }, { $set: { 'permissions.staff': false } });
|
||||
}
|
||||
|
||||
if (acc.permissions.staff && acc.tier > 3) {
|
||||
if (acc.permissions.staff && acc.tier < 3) {
|
||||
await client.db.Account.updateOne({ username: acc.username }, { $set: { tier: 3 } });
|
||||
const embed = new RichEmbed();
|
||||
embed.setTitle('Cloud Account | Tier Change');
|
||||
embed.setColor('#0099ff');
|
||||
embed.addField('User', `${acc.username} | <@${acc.userID}>`, true);
|
||||
embed.addField('Moderator', `<@${client.user.id}>`, true);
|
||||
embed.addField('Old Tier -> New Tier', `${acc.tier} -> 3`, true);
|
||||
embed.setFooter(this.client.user.username, this.client.user.avatarURL);
|
||||
embed.setTimestamp();
|
||||
this.client.createMessage('580950455581147146', { embed });
|
||||
client.getDMChannel(acc.userID).then((chan) => {
|
||||
chan.createMessage('***Your account has automatically been upgraded to Tier 3 since you are a Staff member.***');
|
||||
});
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
/* eslint-disable no-continue */
|
||||
/* eslint-disable no-await-in-loop */
|
||||
import { Client } from '..';
|
||||
import { RichEmbed } from '../class';
|
||||
|
||||
const channelID = '691824484230889546';
|
||||
|
||||
export const memoryLimits = {
|
||||
const memoryLimits = {
|
||||
TIER_1_SOFT: 200,
|
||||
TIER_1_HARD: 350,
|
||||
TIER_2_SOFT: 350,
|
||||
|
@ -15,61 +16,76 @@ export const memoryLimits = {
|
|||
|
||||
export default function memory(client: Client) {
|
||||
setInterval(async () => {
|
||||
const accounts = await client.db.Account.find();
|
||||
for (const acc of accounts) {
|
||||
if (acc.root) return;
|
||||
// memory in bytes
|
||||
const mem = Number(await client.util.exec(`memory ${acc.username}`)) * 1000;
|
||||
// memory in megabytes
|
||||
const memoryConversion = mem / 1024 / 1024;
|
||||
let userLimits: { soft: number, hard: number };
|
||||
if (acc.tier === 1) {
|
||||
userLimits = { soft: memoryLimits.TIER_1_SOFT, hard: memoryLimits.TIER_1_HARD };
|
||||
} else if (acc.tier === 2) {
|
||||
userLimits = { soft: memoryLimits.TIER_2_SOFT, hard: memoryLimits.TIER_2_HARD };
|
||||
} else if (acc.tier === 3) {
|
||||
userLimits = { soft: memoryLimits.TIER_3_SOFT, hard: memoryLimits.TIER_3_HARD };
|
||||
}
|
||||
|
||||
/* if the user has exceeded their soft memory limit, which is the one described in the
|
||||
resource limit guidelines, we'll inform staff.
|
||||
*/
|
||||
if (acc.tier === 1 && memoryConversion >= userLimits.soft) {
|
||||
const embed = new RichEmbed();
|
||||
if (client.users.get(acc.userID)) embed.setThumbnail(client.users.get(acc.userID).avatarURL);
|
||||
embed.addField('User', `${acc.username} | <@${acc.userID}> | ${acc.userID}`, true);
|
||||
embed.addField('Tier', String(acc.tier), true);
|
||||
embed.addField('Memory Usage', `${String(memoryConversion)} MB`, true);
|
||||
embed.addField('Memory Limit', `${String(userLimits.soft)} MB`, true);
|
||||
embed.setFooter(client.user.username, client.user.avatarURL);
|
||||
embed.setTimestamp();
|
||||
|
||||
// if they exceed the hard limit, we'll kill all of their processes.
|
||||
if (memoryConversion >= userLimits.hard) {
|
||||
client.util.exec(`killall -9 -u ${acc.username}`);
|
||||
embed.setTitle('Resource Enforcement Notification');
|
||||
embed.setDescription('Someone has reached the (hard) resource limit for their tier on RAM. The system has automatically killed all of their processes.');
|
||||
client.util.createModerationLog(acc.userID, client.guilds.get('446067825673633794').members.get(client.user.id), 1, '[AUTO] Exceeded resource limit for RAM.');
|
||||
client.util.transport.sendMail({
|
||||
to: acc.emailAddress,
|
||||
from: 'Library of Code sp-us | Cloud Services <help@libraryofcode.org>',
|
||||
subject: 'Your account has been warned',
|
||||
html: `
|
||||
<h1>Library of Code sp-us | Cloud Services</h1>
|
||||
<p>Your account has received an official warning from a Moderator. Please get the underlying issue resolved to avoid <i>possible</i> moderative action.</p>
|
||||
<p><strong>Reason:</strong> [AUTO] Exceeded resource limit for RAM.</p>
|
||||
<p><strong>Moderator:</strong> ${client.user.username}</p>
|
||||
|
||||
<b><i>Library of Code sp-us | Support Team</i></b>
|
||||
`,
|
||||
});
|
||||
} else {
|
||||
embed.setTitle('Resource Limit Notification');
|
||||
embed.setDescription('Someone has reached the (soft) resource limit for their tier on RAM.');
|
||||
try {
|
||||
const accounts = await client.db.Account.find();
|
||||
for (const acc of accounts) {
|
||||
if (acc.root === true) continue;
|
||||
// memory in bytes
|
||||
const mem = Number(await client.util.exec(`memory ${acc.username}`)) * 1000;
|
||||
// memory in megabytes
|
||||
const memoryConversion = mem / 1024 / 1024;
|
||||
const userLimits: { soft?: number, hard?: number } = {};
|
||||
switch (acc.tier) {
|
||||
case 1:
|
||||
userLimits.soft = memoryLimits.TIER_1_SOFT;
|
||||
userLimits.hard = memoryLimits.TIER_1_HARD;
|
||||
break;
|
||||
case 2:
|
||||
userLimits.soft = memoryLimits.TIER_2_SOFT;
|
||||
userLimits.hard = memoryLimits.TIER_2_HARD;
|
||||
break;
|
||||
case 3:
|
||||
userLimits.soft = memoryLimits.TIER_3_SOFT;
|
||||
userLimits.hard = memoryLimits.TIER_3_HARD;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* if the user has exceeded their soft memory limit, which is the one described in the
|
||||
resource limit guidelines, we'll inform staff.
|
||||
*/
|
||||
if (memoryConversion >= userLimits.soft) {
|
||||
client.signale.info(`RAM Soft Limit Reached | ${acc.username} | ${memoryConversion}/${userLimits.soft} MB`);
|
||||
const embed = new RichEmbed();
|
||||
if (client.users.get(acc.userID)) embed.setThumbnail(client.users.get(acc.userID).avatarURL);
|
||||
embed.addField('User', `${acc.username} | <@${acc.userID}> | ${acc.userID}`, true);
|
||||
embed.addField('Tier', String(acc.tier), true);
|
||||
embed.addField('Memory Usage', `${String(memoryConversion)} MB`, true);
|
||||
embed.addField('Memory Limit', `${String(userLimits.soft)} MB`, true);
|
||||
embed.setFooter(client.user.username, client.user.avatarURL);
|
||||
embed.setTimestamp();
|
||||
|
||||
// if they exceed the hard limit, we'll kill all of their processes.
|
||||
if (memoryConversion >= userLimits.hard) {
|
||||
client.signale.info(`RAM Hard Limit Reached | ${acc.username} | ${memoryConversion}/${userLimits.hard} MB`);
|
||||
client.util.exec(`killall -9 -u ${acc.username}`);
|
||||
embed.setTitle('Resource Enforcement Notification');
|
||||
embed.setDescription('Someone has reached the (hard) resource limit for their tier on RAM. The system has automatically killed all of their processes.');
|
||||
client.util.createModerationLog(acc.userID, client.guilds.get('446067825673633794').members.get(client.user.id), 1, '[AUTO] Exceeded resource limit for RAM.');
|
||||
client.util.transport.sendMail({
|
||||
to: acc.emailAddress,
|
||||
from: 'Library of Code sp-us | Cloud Services <help@libraryofcode.org>',
|
||||
subject: 'Your account has been warned',
|
||||
html: `
|
||||
<h1>Library of Code sp-us | Cloud Services</h1>
|
||||
<p>Your account has received an official warning from a Moderator. Please get the underlying issue resolved to avoid <i>possible</i> moderative action.</p>
|
||||
<p><strong>Reason:</strong> [AUTO] Exceeded resource limit for RAM.</p>
|
||||
<p><strong>Moderator:</strong> ${client.user.username}</p>
|
||||
|
||||
<b><i>Library of Code sp-us | Support Team</i></b>
|
||||
`,
|
||||
});
|
||||
} else {
|
||||
embed.setTitle('Resource Limit Notification');
|
||||
embed.setDescription('Someone has reached the (soft) resource limit for their tier on RAM.');
|
||||
}
|
||||
// @ts-ignore
|
||||
client.createMessage(channelID, { embed });
|
||||
}
|
||||
// @ts-ignore
|
||||
client.createMessage(channelID, { embed });
|
||||
}
|
||||
} catch (err) {
|
||||
client.util.handleError(err);
|
||||
}
|
||||
}, 300000);
|
||||
}, 60000);
|
||||
}
|
||||
|
|
|
@ -8,7 +8,8 @@ export interface AccountInterface extends Document {
|
|||
createdBy: string,
|
||||
createdAt: Date,
|
||||
locked: boolean,
|
||||
tier: number;
|
||||
tier: number,
|
||||
supportKey: string,
|
||||
permissions: {
|
||||
staff: boolean,
|
||||
sheriff: boolean,
|
||||
|
@ -29,6 +30,7 @@ const Account: Schema = new Schema({
|
|||
createdAt: Date,
|
||||
locked: Boolean,
|
||||
tier: Number,
|
||||
supportKey: String,
|
||||
permissions: {
|
||||
staff: Boolean,
|
||||
sheriff: Boolean,
|
||||
|
|
|
@ -24,19 +24,19 @@ server {
|
|||
limit_req zone=one burst=15;
|
||||
location / {
|
||||
|
||||
proxy_set_header Host $host;
|
||||
proxy_set_header Host $host;
|
||||
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
proxy_set_header X-Real-IP $remote_addr;
|
||||
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
|
||||
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
proxy_set_header X-Forwarded-Proto $scheme;
|
||||
|
||||
proxy_pass http://localhost:[PORT];
|
||||
proxy_pass http://localhost:[PORT];
|
||||
|
||||
proxy_read_timeout 90;
|
||||
proxy_read_timeout 90;
|
||||
|
||||
proxy_redirect http://localhost:[PORT] https://[DOMAIN];
|
||||
proxy_redirect http://localhost:[PORT] https://[DOMAIN];
|
||||
|
||||
}
|
||||
}
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
"compilerOptions": {
|
||||
/* Basic Options */
|
||||
// "incremental": true, /* Enable incremental compilation */
|
||||
"target": "ES2020", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */
|
||||
"target": "ES2017", /* Specify ECMAScript target version: 'ES3' (default), 'ES5', 'ES2015', 'ES2016', 'ES2017', 'ES2018', 'ES2019' or 'ESNEXT'. */
|
||||
"module": "commonjs", /* Specify module code generation: 'none', 'commonjs', 'amd', 'system', 'umd', 'es2015', or 'ESNext'. */
|
||||
"lib": ["ES2019.Object", "ES2020.Promise"], /* Specify library files to be included in the compilation. */
|
||||
// "allowJs": true, /* Allow javascript files to be compiled. */
|
||||
|
|
Loading…
Reference in New Issue