diff options
author | Daniel Huber <30466471+daniel0611@users.noreply.github.com> | 2022-01-03 11:02:42 +0100 |
---|---|---|
committer | Erkin Alp Güney <erkinalp9035@gmail.com> | 2022-01-04 09:46:22 +0300 |
commit | e31d8e85a62114e275cb495d0378109542824033 (patch) | |
tree | 3bfb59ccc9daf68a7b165a909620c457b0bc5469 /util | |
parent | Fix schemas handler (diff) | |
download | server-e31d8e85a62114e275cb495d0378109542824033.tar.xz |
Incrementing user discriminators
Closes #328
Diffstat (limited to 'util')
-rw-r--r-- | util/src/entities/Config.ts | 2 | ||||
-rw-r--r-- | util/src/entities/User.ts | 49 |
2 files changed, 35 insertions, 16 deletions
diff --git a/util/src/entities/Config.ts b/util/src/entities/Config.ts index 9e25c737..6993cc09 100644 --- a/util/src/entities/Config.ts +++ b/util/src/entities/Config.ts @@ -149,6 +149,7 @@ export interface ConfigValue { minUpperCase: number; minSymbols: number; }; + incrementingDiscriminators: boolean; // random otherwise }; regions: { default: string; @@ -335,6 +336,7 @@ export const DefaultConfigOptions: ConfigValue = { minUpperCase: 2, minSymbols: 0, }, + incrementingDiscriminators: false, }, regions: { default: "fosscord", diff --git a/util/src/entities/User.ts b/util/src/entities/User.ts index bc852616..5f2618e0 100644 --- a/util/src/entities/User.ts +++ b/util/src/entities/User.ts @@ -64,7 +64,7 @@ export class User extends BaseClass { setDiscriminator(val: string) { const number = Number(val); if (isNaN(number)) throw new Error("invalid discriminator"); - if (number <= 0 || number > 10000) throw new Error("discriminator must be between 1 and 9999"); + if (number <= 0 || number >= 10000) throw new Error("discriminator must be between 1 and 9999"); this.discriminator = val.toString().padStart(4, "0"); } @@ -178,6 +178,35 @@ export class User extends BaseClass { ); } + private static async generateDiscriminator(username: string): Promise<string | undefined> { + if (Config.get().register.incrementingDiscriminators) { + // discriminator will be incrementally generated + + // First we need to figure out the currently highest discrimnator for the given username and then increment it + const users = await User.find({ where: { username }, select: ["discriminator"] }); + const highestDiscriminator = Math.max(0, ...users.map((u) => Number(u.discriminator))); + + const discriminator = highestDiscriminator + 1; + if (discriminator >= 10000) { + return undefined; + } + + return discriminator.toString().padStart(4, "0"); + } else { + // discriminator will be randomly generated + + // randomly generates a discriminator between 1 and 9999 and checks max five times if it already exists + // TODO: is there any better way to generate a random discriminator only once, without checking if it already exists in the database? + for (let tries = 0; tries < 5; tries++) { + const discriminator = Math.randomIntBetween(1, 9999).toString().padStart(4, "0"); + const exists = await User.findOne({ where: { discriminator, username: username }, select: ["id"] }); + if (!exists) return discriminator; + } + + return undefined; + } + } + static async register({ email, username, @@ -194,21 +223,9 @@ export class User extends BaseClass { // trim special uf8 control characters -> Backspace, Newline, ... username = trimSpecial(username); - // discriminator will be randomly generated - let discriminator = ""; - - let exists; - // randomly generates a discriminator between 1 and 9999 and checks max five times if it already exists - // if it all five times already exists, abort with USERNAME_TOO_MANY_USERS error - // else just continue - // TODO: is there any better way to generate a random discriminator only once, without checking if it already exists in the database? - for (let tries = 0; tries < 5; tries++) { - discriminator = Math.randomIntBetween(1, 9999).toString().padStart(4, "0"); - exists = await User.findOne({ where: { discriminator, username: username }, select: ["id"] }); - if (!exists) break; - } - - if (exists) { + const discriminator = await User.generateDiscriminator(username); + if (!discriminator) { + // We've failed to generate a valid and unused discriminator throw FieldErrors({ username: { code: "USERNAME_TOO_MANY_USERS", |