diff --git a/backend/package-lock.json b/backend/package-lock.json index f19dd93..3a5a2e2 100644 --- a/backend/package-lock.json +++ b/backend/package-lock.json @@ -19,6 +19,7 @@ "@nestjs/swagger": "^7.3.1", "@nestjs/throttler": "^5.2.0", "@prisma/client": "^5.16.1", + "@types/jmespath": "^0.15.2", "archiver": "^7.0.1", "argon2": "^0.40.3", "body-parser": "^1.20.2", @@ -28,6 +29,7 @@ "class-validator": "^0.14.1", "content-disposition": "^0.5.4", "cookie-parser": "^1.4.6", + "jmespath": "^0.16.0", "mime-types": "^2.1.35", "moment": "^2.30.1", "nanoid": "^3.3.7", @@ -1994,6 +1996,12 @@ "@types/range-parser": "*" } }, + "node_modules/@types/jmespath": { + "version": "0.15.2", + "resolved": "https://registry.npmjs.org/@types/jmespath/-/jmespath-0.15.2.tgz", + "integrity": "sha512-pegh49FtNsC389Flyo9y8AfkVIZn9MMPE9yJrO9svhq6Fks2MwymULWjZqySuxmctd3ZH4/n7Mr98D+1Qo5vGA==", + "license": "MIT" + }, "node_modules/@types/json-schema": { "version": "7.0.12", "resolved": "https://registry.npmjs.org/@types/json-schema/-/json-schema-7.0.12.tgz", @@ -5523,6 +5531,15 @@ "url": "https://github.com/chalk/supports-color?sponsor=1" } }, + "node_modules/jmespath": { + "version": "0.16.0", + "resolved": "https://registry.npmjs.org/jmespath/-/jmespath-0.16.0.tgz", + "integrity": "sha512-9FzQjJ7MATs1tSpnco1K6ayiYE3figslrXA72G2HQ/n76RzvYlofyi5QM+iX4YRs/pu3yzxlVQSST23+dMDknw==", + "license": "Apache-2.0", + "engines": { + "node": ">= 0.6.0" + } + }, "node_modules/joi": { "version": "17.11.0", "resolved": "https://registry.npmjs.org/joi/-/joi-17.11.0.tgz", diff --git a/backend/package.json b/backend/package.json index 73e0abe..8c82ac1 100644 --- a/backend/package.json +++ b/backend/package.json @@ -24,6 +24,7 @@ "@nestjs/swagger": "^7.3.1", "@nestjs/throttler": "^5.2.0", "@prisma/client": "^5.16.1", + "@types/jmespath": "^0.15.2", "archiver": "^7.0.1", "argon2": "^0.40.3", "body-parser": "^1.20.2", @@ -33,6 +34,7 @@ "class-validator": "^0.14.1", "content-disposition": "^0.5.4", "cookie-parser": "^1.4.6", + "jmespath": "^0.16.0", "mime-types": "^2.1.35", "moment": "^2.30.1", "nanoid": "^3.3.7", diff --git a/backend/prisma/seed/config.seed.ts b/backend/prisma/seed/config.seed.ts index 3b4dad5..6ddc573 100644 --- a/backend/prisma/seed/config.seed.ts +++ b/backend/prisma/seed/config.seed.ts @@ -230,6 +230,18 @@ const configVariables: ConfigVariables = { type: "string", defaultValue: "", }, + "oidc-rolePath": { + type: "string", + defaultValue: "", + }, + "oidc-roleGeneralAccess": { + type: "string", + defaultValue: "", + }, + "oidc-roleAdminAccess": { + type: "string", + defaultValue: "", + }, "oidc-clientId": { type: "string", defaultValue: "", diff --git a/backend/src/auth/auth.service.ts b/backend/src/auth/auth.service.ts index 25186fd..587dffc 100644 --- a/backend/src/auth/auth.service.ts +++ b/backend/src/auth/auth.service.ts @@ -27,7 +27,7 @@ export class AuthService { ) {} private readonly logger = new Logger(AuthService.name); - async signUp(dto: AuthRegisterDTO, ip: string) { + async signUp(dto: AuthRegisterDTO, ip: string, isAdmin?: boolean) { const isFirstUser = (await this.prisma.user.count()) == 0; const hash = dto.password ? await argon.hash(dto.password) : null; @@ -37,7 +37,7 @@ export class AuthService { email: dto.email, username: dto.username, password: hash, - isAdmin: isFirstUser, + isAdmin: isAdmin ?? isFirstUser, }, }); @@ -80,7 +80,7 @@ export class AuthService { throw new UnauthorizedException("Wrong email or password"); } - this.logger.log(`Successful login for user ${dto.email} from IP ${ip}`); + this.logger.log(`Successful login for user ${user.email} from IP ${ip}`); return this.generateToken(user); } diff --git a/backend/src/oauth/dto/oauthSignIn.dto.ts b/backend/src/oauth/dto/oauthSignIn.dto.ts index 75a64ad..3efe889 100644 --- a/backend/src/oauth/dto/oauthSignIn.dto.ts +++ b/backend/src/oauth/dto/oauthSignIn.dto.ts @@ -3,4 +3,5 @@ export interface OAuthSignInDto { providerId: string; providerUsername: string; email: string; + isAdmin?: boolean; } diff --git a/backend/src/oauth/oauth.service.ts b/backend/src/oauth/oauth.service.ts index 0da039b..5d73df9 100644 --- a/backend/src/oauth/oauth.service.ts +++ b/backend/src/oauth/oauth.service.ts @@ -46,13 +46,16 @@ export class OAuthService { provider: user.provider, providerUserId: user.providerId, }, - include: { - user: true, - }, }); if (oauthUser) { + await this.updateIsAdmin(user); + const updatedUser = await this.prisma.user.findFirst({ + where: { + email: user.email, + }, + }); this.logger.log(`Successful login for user ${user.email} from IP ${ip}`); - return this.auth.generateToken(oauthUser.user, true); + return this.auth.generateToken(updatedUser, true); } return this.signUp(user, ip); @@ -150,6 +153,7 @@ export class OAuthService { userId: existingUser.id, }, }); + await this.updateIsAdmin(user); return this.auth.generateToken(existingUser, true); } @@ -160,6 +164,7 @@ export class OAuthService { password: null, }, ip, + user.isAdmin, ); await this.prisma.oAuthUser.create({ @@ -173,4 +178,16 @@ export class OAuthService { return result; } + + private async updateIsAdmin(user: OAuthSignInDto) { + if ("isAdmin" in user) + await this.prisma.user.update({ + where: { + email: user.email, + }, + data: { + isAdmin: user.isAdmin, + }, + }); + } } diff --git a/backend/src/oauth/provider/discord.provider.ts b/backend/src/oauth/provider/discord.provider.ts index acb4d97..717cd8e 100644 --- a/backend/src/oauth/provider/discord.provider.ts +++ b/backend/src/oauth/provider/discord.provider.ts @@ -101,10 +101,10 @@ export class DiscordProvider implements OAuthProvider { }); const guilds = (await res.json()) as DiscordPartialGuild[]; if (!guilds.some((guild) => guild.id === guildId)) { - throw new ErrorPageException("discord_guild_permission_denied"); + throw new ErrorPageException("user_not_allowed"); } } catch { - throw new ErrorPageException("discord_guild_permission_denied"); + throw new ErrorPageException("user_not_allowed"); } } } diff --git a/backend/src/oauth/provider/genericOidc.provider.ts b/backend/src/oauth/provider/genericOidc.provider.ts index 6ac1dc1..10f957a 100644 --- a/backend/src/oauth/provider/genericOidc.provider.ts +++ b/backend/src/oauth/provider/genericOidc.provider.ts @@ -2,6 +2,7 @@ import { Logger } from "@nestjs/common"; import { ConfigService } from "../../config/config.service"; import { JwtService } from "@nestjs/jwt"; import { Cache } from "cache-manager"; +import * as jmespath from "jmespath"; import { nanoid } from "nanoid"; import { OAuthCallbackDto } from "../dto/oauthCallback.dto"; import { OAuthProvider, OAuthToken } from "./oauthProvider.interface"; @@ -108,6 +109,11 @@ export abstract class GenericOidcProvider implements OAuthProvider { token: OAuthToken, query: OAuthCallbackDto, claim?: string, + roleConfig?: { + path?: string; + generalAccess?: string; + adminAccess?: string; + }, ): Promise { const idTokenData = this.decodeIdToken(token.idToken); // maybe it's not necessary to verify the id token since it's directly obtained from the provider @@ -127,6 +133,39 @@ export abstract class GenericOidcProvider implements OAuthProvider { : idTokenData.preferred_username || idTokenData.name || idTokenData.nickname; + + let isAdmin: boolean; + + if (roleConfig?.path) { + // A path to read roles from the token is configured + let roles: string[] | null; + try { + roles = jmespath.search(idTokenData, roleConfig.path); + } catch (e) { + roles = null; + } + if (Array.isArray(roles)) { + // Roles are found in the token + if (roleConfig.generalAccess && !roles.includes(roleConfig.generalAccess)) { + // Role for general access is configured and the user does not have it + this.logger.error(`User roles ${roles} do not include ${roleConfig.generalAccess}`); + throw new ErrorPageException("user_not_allowed"); + } + if (roleConfig.adminAccess) { + // Role for admin access is configured + isAdmin = roles.includes(roleConfig.adminAccess); + } + } else { + this.logger.error( + `Roles not found at path ${roleConfig.path} in ID Token ${JSON.stringify( + idTokenData, + undefined, + 2, + )}`, + ); + throw new ErrorPageException("user_not_allowed"); + } + } if (!username) { this.logger.error( @@ -146,6 +185,7 @@ export abstract class GenericOidcProvider implements OAuthProvider { email: idTokenData.email, providerId: idTokenData.sub, providerUsername: username, + ...(isAdmin !== undefined && { isAdmin }), }; } diff --git a/backend/src/oauth/provider/oidc.provider.ts b/backend/src/oauth/provider/oidc.provider.ts index 984290d..9265254 100644 --- a/backend/src/oauth/provider/oidc.provider.ts +++ b/backend/src/oauth/provider/oidc.provider.ts @@ -34,6 +34,13 @@ export class OidcProvider extends GenericOidcProvider { _?: string, ): Promise { const claim = this.config.get("oauth.oidc-usernameClaim") || undefined; - return super.getUserInfo(token, query, claim); + const rolePath = this.config.get("oauth.oidc-rolePath") || undefined; + const roleGeneralAccess = this.config.get("oauth.oidc-roleGeneralAccess") || undefined; + const roleAdminAccess = this.config.get("oauth.oidc-roleAdminAccess") || undefined; + return super.getUserInfo(token, query, claim, { + path: rolePath, + generalAccess: roleGeneralAccess, + adminAccess: roleAdminAccess, + }); } } diff --git a/frontend/src/i18n/translations/ar-EG.ts b/frontend/src/i18n/translations/ar-EG.ts index 3323912..f717705 100644 --- a/frontend/src/i18n/translations/ar-EG.ts +++ b/frontend/src/i18n/translations/ar-EG.ts @@ -485,7 +485,7 @@ export default { "error.msg.not_linked": "لم يتم ربط حساب {0} هذا بأي حساب حتى الآن.", "error.msg.unverified_account": "لم يتم التحقق من حساب {0} هذا، يرجى المحاولة مرة أخرى بعد التحقق.", - "error.msg.discord_guild_permission_denied": "غير مسموح لك بتسجيل الدخول.", + "error.msg.user_not_allowed": "غير مسموح لك بتسجيل الدخول.", "error.msg.cannot_get_user_info": "فشلت عملية جلب معلومات المستخدم الخاصة بك من حساب {0} هذا.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/da-DK.ts b/frontend/src/i18n/translations/da-DK.ts index c107737..47b2d89 100644 --- a/frontend/src/i18n/translations/da-DK.ts +++ b/frontend/src/i18n/translations/da-DK.ts @@ -494,7 +494,7 @@ export default { "error.msg.not_linked": "This {0} account haven't linked to any account yet.", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "Du har ikke tilladelse til at logge ind.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/de-DE.ts b/frontend/src/i18n/translations/de-DE.ts index 2bb97be..9bc1fbb 100644 --- a/frontend/src/i18n/translations/de-DE.ts +++ b/frontend/src/i18n/translations/de-DE.ts @@ -73,7 +73,7 @@ export default { "account.card.password.title": "Passwort", "account.card.password.old": "Altes Passwort", "account.card.password.new": "Neues Passwort", - "account.card.password.noPasswordSet": "Du hast kein Passwort erstellt. Wenn Du Dich mit E-Mail und Passwort anmelden möchtest, musst Du ein Passwort festlegen.", + "account.card.password.noPasswordSet": "Du hast kein Passwort erstellt. Wenn du dich mit E-Mail und Passwort anmelden möchtest, musst du ein Passwort festlegen.", "account.notify.password.success": "Passwort erfolgreich geändert", "account.card.oauth.title": "Anmeldung über soziale Netzwerke", "account.card.oauth.github": "GitHub", @@ -85,7 +85,7 @@ export default { "account.card.oauth.unlink": "Verknüpfung aufheben", "account.card.oauth.unlinked": "Verknüpfung aufgehoben", "account.modal.unlink.title": "Kontoverknüpfung aufheben", - "account.modal.unlink.description": "Das Entfernen der Verknüpfung mit Deinem sozialen Konten kann dazu führen, dass Du Dein Konto verlierst, wenn Du Dich nicht an Deinen Benutzernamen und Dein Passwort erinnerst.", + "account.modal.unlink.description": "Das Entfernen der Verknüpfung mit deinem sozialen Konten kann dazu führen, dass du dein Konto verlierst, wenn du dich nicht an deinen Benutzernamen und dein Passwort erinnerst.", "account.notify.oauth.unlinked.success": "Verknüpfung erfolgreich aufgehoben", "account.card.security.title": "Sicherheit", "account.card.security.totp.enable.description": "Gib dein aktuelles Passwort ein, um TOTP zu aktivieren", @@ -301,7 +301,7 @@ export default { "admin.config.general.logo.description": "Ändere dein Logo durch Hochladen eines Bildes. Das Bild muss im PNG-Format vorliegen und sollte mit Seitenverhältnis 1:1 sein.", "admin.config.general.logo.placeholder": "Bild auswählen", "admin.config.email.enable-share-email-recipients": "Erlaube das Teilen der Freigabe via Email", - "admin.config.email.enable-share-email-recipients.description": "Gibt an, ob Emails an Freigabe-Empfänger ermöglicht werden sollen. Aktiviere dies nur, wenn Du SMTP aktivierst hast.", + "admin.config.email.enable-share-email-recipients.description": "Gibt an, ob Emails an Freigabe-Empfänger ermöglicht werden sollen. Aktiviere dies nur, wenn du SMTP aktivierst hast.", "admin.config.email.share-recipients-subject": "Betreff für Freigabe-Empfänger", "admin.config.email.share-recipients-subject.description": "Betreff der E-Mail, die an die Freigabe-Empfänger gesendet wird.", "admin.config.email.share-recipients-message": "Nachricht für Freigabe-Empfänger", @@ -333,7 +333,7 @@ export default { "admin.config.share.auto-open-share-modal": "Auto open create share modal", "admin.config.share.auto-open-share-modal.description": "The share creation modal automatically appears when a user selects files, eliminating the need to manually click the button.", "admin.config.smtp.enabled": "Aktiviert", - "admin.config.smtp.enabled.description": "Gibt an, ob SMTP aktiviert ist. Aktiviere dies nur, wenn Du den Host, den Port, die Email, den Benutzernamen und das Passwort deines SMTP-Servers eingegeben hast.", + "admin.config.smtp.enabled.description": "Gibt an, ob SMTP aktiviert ist. Aktiviere dies nur, wenn du den Host, den Port, die Email, den Benutzernamen und das Passwort deines SMTP-Servers eingegeben hast.", "admin.config.smtp.host": "Host", "admin.config.smtp.host.description": "Host des SMTP-Servers", "admin.config.smtp.port": "Port", @@ -387,6 +387,19 @@ export default { "admin.config.oauth.oidc-discovery-uri.description": "Discovery-URL der OpenID OAuth App", "admin.config.oauth.oidc-username-claim": "OpenID Connect Benutzername anfordern", "admin.config.oauth.oidc-username-claim.description": "Benutzername im OpenID Token. Leer lassen, wenn du nicht weißt, was diese Konfiguration bedeutet.", + "admin.config.oauth.oidc-role-path": "Path to roles in OpenID Connect token", + "admin.config.oauth.oidc-role-path.description": + "Muss ein valider JMES-Pfad sein, der zu einem Array an Rollen führt. " + + "Die Zugangsverwaltung über Rollen in OpenID Connect ist nur empfohlen, wenn kein anderer Identitätsprovider konfiguriert und die Anmeldung per Password deaktiviert ist. " + + "Leer lassen, wenn du nicht weißt, was diese Konfiguration bedeutet.", + "admin.config.oauth.oidc-role-general-access": "OpenID Connect role for general access", + "admin.config.oauth.oidc-role-general-access.description": + "Rolle für generellen Zugriff. Muss Teil der Rollen eines Benutzers sein, damit dieser sich anmelden kann. " + + "Leer lassen, wenn du nicht weißt, was diese Konfiguration bedeutet.", + "admin.config.oauth.oidc-role-admin-access": "OpenID Connect role for admin access", + "admin.config.oauth.oidc-role-admin-access.description": + "Rolle für administrativen Zugriff. Muss Teil der Rollen eines Benutzers sein, damit dieser auf das Administrator-Panel zugreifen kann. " + + "Leer lassen, wenn du nicht weißt, was diese Konfiguration bedeutet.", "admin.config.oauth.oidc-client-id": "OpenID Connect Client-ID", "admin.config.oauth.oidc-client-id.description": "Client-ID der OpenID Connect OAuth-App", "admin.config.oauth.oidc-client-secret": "OpenID Connect Client-Secret", @@ -407,7 +420,7 @@ export default { "error.msg.already_linked": "Das Konto {0} ist bereits mit einem anderen Konto verknüpft.", "error.msg.not_linked": "Das Konto {0} wurde noch nicht mit einem Konto verknüpft.", "error.msg.unverified_account": "Dieses Konto {0} wurde noch nicht verifiziert, bitte versuche es nach der Verifikation erneut.", - "error.msg.discord_guild_permission_denied": "Du bist nicht berechtigt, Dich anzumelden.", + "error.msg.user_not_allowed": "Du bist nicht berechtigt, dich anzumelden.", "error.msg.cannot_get_user_info": "Deine Benutzerinformationen können nicht von diesem Konto {0} abgerufen werden.", "error.param.provider_github": "GitHub", "error.param.provider_google": "Google", diff --git a/frontend/src/i18n/translations/el-GR.ts b/frontend/src/i18n/translations/el-GR.ts index aeb357e..e65e9ca 100644 --- a/frontend/src/i18n/translations/el-GR.ts +++ b/frontend/src/i18n/translations/el-GR.ts @@ -518,7 +518,7 @@ export default { "Αυτός ο λογαριασμός {0} δεν έχει συνδεθεί με κανένα λογαριασμό ακόμα.", "error.msg.unverified_account": "Αυτός ο λογαριασμός {0} δεν έχει επαληθευτεί, παρακαλώ προσπαθήστε ξανά μετά την επαλήθευση.", - "error.msg.discord_guild_permission_denied": "Δεν σας επιτρέπεται η σύνδεση.", + "error.msg.user_not_allowed": "Δεν σας επιτρέπεται η σύνδεση.", "error.msg.cannot_get_user_info": "Δεν είναι δυνατή η λήψη των πληροφοριών χρήστη από αυτόν τον λογαριασμό {0}.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/en-US.ts b/frontend/src/i18n/translations/en-US.ts index 2f0d58f..f8d09b6 100644 --- a/frontend/src/i18n/translations/en-US.ts +++ b/frontend/src/i18n/translations/en-US.ts @@ -539,6 +539,19 @@ export default { "admin.config.oauth.oidc-username-claim": "OpenID Connect username claim", "admin.config.oauth.oidc-username-claim.description": "Username claim in OpenID Connect ID token. Leave it blank if you don't know what this config is.", + "admin.config.oauth.oidc-role-path": "Path to roles in OpenID Connect token", + "admin.config.oauth.oidc-role-path.description": + "Must be a valid JMES path referencing an array of roles. " + + "Managing access rights using OpenID Connect roles is only recommended if no other identity provider is configured and password login is disabled. " + + "Leave it blank if you don't know what this config is.", + "admin.config.oauth.oidc-role-general-access": "OpenID Connect role for general access", + "admin.config.oauth.oidc-role-general-access.description": + "Role required for general access. Must be present in a user’s roles for them to log in. " + + "Leave it blank if you don't know what this config is.", + "admin.config.oauth.oidc-role-admin-access": "OpenID Connect role for admin access", + "admin.config.oauth.oidc-role-admin-access.description": + "Role required for administrative access. Must be present in a user’s roles for them to access the admin panel. " + + "Leave it blank if you don't know what this config is.", "admin.config.oauth.oidc-client-id": "OpenID Connect Client ID", "admin.config.oauth.oidc-client-id.description": "Client ID of the OpenID Connect OAuth app", @@ -567,7 +580,7 @@ export default { "error.msg.not_linked": "This {0} account haven't linked to any account yet.", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/es-ES.ts b/frontend/src/i18n/translations/es-ES.ts index 916de95..e2a5a29 100644 --- a/frontend/src/i18n/translations/es-ES.ts +++ b/frontend/src/i18n/translations/es-ES.ts @@ -509,7 +509,7 @@ export default { "Esta cuenta {0} aún no ha sido vinculada a ninguna cuenta.", "error.msg.unverified_account": "Esta cuenta {0} no está verificada, por favor inténtalo de nuevo después de la verificación.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "No tienes permitido iniciar sesion.", "error.msg.cannot_get_user_info": "No se puede obtener la información de usuario de la cuenta {0}.", diff --git a/frontend/src/i18n/translations/fi-FI.ts b/frontend/src/i18n/translations/fi-FI.ts index affaba4..3032c19 100644 --- a/frontend/src/i18n/translations/fi-FI.ts +++ b/frontend/src/i18n/translations/fi-FI.ts @@ -497,7 +497,7 @@ export default { "error.msg.not_linked": "This {0} account haven't linked to any account yet.", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/fr-FR.ts b/frontend/src/i18n/translations/fr-FR.ts index 7e831bb..22a1bbd 100644 --- a/frontend/src/i18n/translations/fr-FR.ts +++ b/frontend/src/i18n/translations/fr-FR.ts @@ -504,7 +504,7 @@ export default { "error.msg.not_linked": "Le compte {0} n’est pas encore associé à compte.", "error.msg.unverified_account": "Le compte {0} n'est pas vérifié, veuillez réessayer après vérification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "Vous n’êtes pas autorisé à vous authentifier.", "error.msg.cannot_get_user_info": "Impossible d’obtenir vos informations utilisateur à partir du compte {0}.", diff --git a/frontend/src/i18n/translations/hu-HU.ts b/frontend/src/i18n/translations/hu-HU.ts index 2e6c847..1524086 100644 --- a/frontend/src/i18n/translations/hu-HU.ts +++ b/frontend/src/i18n/translations/hu-HU.ts @@ -503,7 +503,7 @@ export default { "Ez a(z){0} fiók még nem kapcsolódott egyetlen fiókhoz sem.", "error.msg.unverified_account": "Ezt a(z) {0} fiókot még nem igazolták vissza, kérem próbálja újra a megerősítés után.", - "error.msg.discord_guild_permission_denied": "Nem jelentkezhet be.", + "error.msg.user_not_allowed": "Nem jelentkezhet be.", "error.msg.cannot_get_user_info": "Nem nyerhető ki felhasználói információ ebből a(z) {0} fiókból.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/it-IT.ts b/frontend/src/i18n/translations/it-IT.ts index d79d291..8e4a63d 100644 --- a/frontend/src/i18n/translations/it-IT.ts +++ b/frontend/src/i18n/translations/it-IT.ts @@ -512,7 +512,7 @@ export default { "Questo account {0} non è ancora collegato ad alcun account.", "error.msg.unverified_account": "Questo account {0} non è verificato, per favore riprova dopo la verifica.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "Non sei autorizzato ad accedere.", "error.msg.cannot_get_user_info": "Non è possibile ottenere le informazioni utente da questo account {0}.", diff --git a/frontend/src/i18n/translations/ja-JP.ts b/frontend/src/i18n/translations/ja-JP.ts index d29f410..182aef6 100644 --- a/frontend/src/i18n/translations/ja-JP.ts +++ b/frontend/src/i18n/translations/ja-JP.ts @@ -495,7 +495,7 @@ export default { "この{0} アカウントはどのアカウントにもリンクされていません。", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/ko-KR.ts b/frontend/src/i18n/translations/ko-KR.ts index a8ad567..c3a51b1 100644 --- a/frontend/src/i18n/translations/ko-KR.ts +++ b/frontend/src/i18n/translations/ko-KR.ts @@ -484,7 +484,7 @@ export default { "이 {0} 계정은 아직 어떤 계정에도 연결되지 않았습니다.", "error.msg.unverified_account": "이 {0} 계정은 확인되지 않았습니다. 확인 후 다시 시도하십시오.", - "error.msg.discord_guild_permission_denied": "로그인할 수 없습니다.", + "error.msg.user_not_allowed": "로그인할 수 없습니다.", "error.msg.cannot_get_user_info": "이 {0} 계정에서 사용자 정보를 가져올 수 없습니다", "error.param.provider_github": "깃허브", diff --git a/frontend/src/i18n/translations/nl-BE.ts b/frontend/src/i18n/translations/nl-BE.ts index 4295da2..0de615a 100644 --- a/frontend/src/i18n/translations/nl-BE.ts +++ b/frontend/src/i18n/translations/nl-BE.ts @@ -504,7 +504,7 @@ export default { "Dit {0} account is nog aan geen enkel account gekoppeld.", "error.msg.unverified_account": "Dit {0} account is nog niet geverifieerd, probeer het opnieuw na de verificatie.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "U heeft geen toestemming om in te loggen.", "error.msg.cannot_get_user_info": "Kan uw gebruikersgegevens van dit {0} account niet ophalen.", diff --git a/frontend/src/i18n/translations/pl-PL.ts b/frontend/src/i18n/translations/pl-PL.ts index fb28af0..cc851c8 100644 --- a/frontend/src/i18n/translations/pl-PL.ts +++ b/frontend/src/i18n/translations/pl-PL.ts @@ -508,7 +508,7 @@ export default { "To konto {0} nie zostało jeszcze połączone z żadnym kontem.", "error.msg.unverified_account": "To konto {0} nie zostało zweryfikowane, spróbuj ponownie po weryfikacji.", - "error.msg.discord_guild_permission_denied": "Nie możesz się zalogować.", + "error.msg.user_not_allowed": "Nie możesz się zalogować.", "error.msg.cannot_get_user_info": "Nie można uzyskać informacji o użytkowniku z tego konta {0}.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/pt-BR.ts b/frontend/src/i18n/translations/pt-BR.ts index beedb9d..c714e87 100644 --- a/frontend/src/i18n/translations/pt-BR.ts +++ b/frontend/src/i18n/translations/pt-BR.ts @@ -516,7 +516,7 @@ export default { "Esta conta {0} ainda não foi vinculada a nenhuma conta.", "error.msg.unverified_account": "Esta conta {0} não foi verificada, tente novamente após a verificação.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "Você não tem permissão para acessar.", "error.msg.cannot_get_user_info": "Não é possível obter suas informações de usuário desta conta {0}.", diff --git a/frontend/src/i18n/translations/ru-RU.ts b/frontend/src/i18n/translations/ru-RU.ts index c16ffc5..3181be6 100644 --- a/frontend/src/i18n/translations/ru-RU.ts +++ b/frontend/src/i18n/translations/ru-RU.ts @@ -500,7 +500,7 @@ export default { "Эта учетная запись {0} ещё не привязана ни к одному аккаунту.", "error.msg.unverified_account": "Эта учетная запись {0} не подтверждена, повторите попытку после подтверждения.", - "error.msg.discord_guild_permission_denied": "У вас нет разрешения на вход.", + "error.msg.user_not_allowed": "У вас нет разрешения на вход.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/sl-SI.ts b/frontend/src/i18n/translations/sl-SI.ts index 705b1d4..fabae4e 100644 --- a/frontend/src/i18n/translations/sl-SI.ts +++ b/frontend/src/i18n/translations/sl-SI.ts @@ -498,7 +498,7 @@ export default { "error.msg.not_linked": "Račun {0} še ni povezan z nobenim računom.", "error.msg.unverified_account": "Račun {0} je nepreverjen, prosimo poskusite ponovno po preverjanju.", - "error.msg.discord_guild_permission_denied": "Nimate dovoljenja za prijavo.", + "error.msg.user_not_allowed": "Nimate dovoljenja za prijavo.", "error.msg.cannot_get_user_info": "Ne moremo najti uporabniških informacij za račun {0}.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/sr-SP.ts b/frontend/src/i18n/translations/sr-SP.ts index a90e9be..02e4ae5 100644 --- a/frontend/src/i18n/translations/sr-SP.ts +++ b/frontend/src/i18n/translations/sr-SP.ts @@ -495,7 +495,7 @@ export default { "Овај {0} налог још увек није повезан ни са једним налогом.", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/sv-SE.ts b/frontend/src/i18n/translations/sv-SE.ts index fbb5e2b..19c6314 100644 --- a/frontend/src/i18n/translations/sv-SE.ts +++ b/frontend/src/i18n/translations/sv-SE.ts @@ -497,7 +497,7 @@ export default { "Detta {0} konto har ännu inte länkat till något konto.", "error.msg.unverified_account": "Detta {0} -konto är overifierat, försök igen efter verifiering.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "Du är inte tillåten att logga in.", "error.msg.cannot_get_user_info": "Kan inte hämta din användarinformation från detta {0} konto.", diff --git a/frontend/src/i18n/translations/th-TH.ts b/frontend/src/i18n/translations/th-TH.ts index 433e668..be0ccde 100644 --- a/frontend/src/i18n/translations/th-TH.ts +++ b/frontend/src/i18n/translations/th-TH.ts @@ -489,7 +489,7 @@ export default { "error.msg.not_linked": "This {0} account haven't linked to any account yet.", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.", diff --git a/frontend/src/i18n/translations/tr-TR.ts b/frontend/src/i18n/translations/tr-TR.ts index 0e1122a..54cad5e 100644 --- a/frontend/src/i18n/translations/tr-TR.ts +++ b/frontend/src/i18n/translations/tr-TR.ts @@ -493,7 +493,7 @@ export default { "error.msg.not_linked": "Bu {0} hesabı henüz bir hesaba bağlı değil.", "error.msg.unverified_account": "Bu {0} hesabı doğrulanmamış, lütfen doğruladıktan sonra yeniden dene.", - "error.msg.discord_guild_permission_denied": "Giriş yapmana izin verilmiyor.", + "error.msg.user_not_allowed": "Giriş yapmana izin verilmiyor.", "error.msg.cannot_get_user_info": "Bu {0} hesabından kullanıcı bilgilerinizi alamıyorum.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/uk-UA.ts b/frontend/src/i18n/translations/uk-UA.ts index 5a55b3e..d101633 100644 --- a/frontend/src/i18n/translations/uk-UA.ts +++ b/frontend/src/i18n/translations/uk-UA.ts @@ -506,7 +506,7 @@ export default { "Цей обліковий запис {0} ще не прив'язаний до жодного акаунту.", "error.msg.unverified_account": "Цей обліковий запис {0} не підтверджено, повторіть спробу після підтвердження.", - "error.msg.discord_guild_permission_denied": "У вас немає дозволу на вхід.", + "error.msg.user_not_allowed": "У вас немає дозволу на вхід.", "error.msg.cannot_get_user_info": "Не вдається отримати інфу про користувача з цього {0} облікового запису.", "error.param.provider_github": "GitHub", diff --git a/frontend/src/i18n/translations/zh-CN.ts b/frontend/src/i18n/translations/zh-CN.ts index 9caf18d..f3c09f6 100644 --- a/frontend/src/i18n/translations/zh-CN.ts +++ b/frontend/src/i18n/translations/zh-CN.ts @@ -458,7 +458,7 @@ export default { "error.msg.already_linked": "{0} 这个账户已经关联到另一个账号。", "error.msg.not_linked": "{0} 这个账户尚未关联到任何账号。", "error.msg.unverified_account": "{0} 这个账户尚未验证,请在验证后重试。", - "error.msg.discord_guild_permission_denied": "您无权登录。", + "error.msg.user_not_allowed": "您无权登录。", "error.msg.cannot_get_user_info": "无法从 {0} 这个账户获取您的用户信息。", "error.param.provider_github": "GitHub", "error.param.provider_google": "谷歌", diff --git a/frontend/src/i18n/translations/zh-TW.ts b/frontend/src/i18n/translations/zh-TW.ts index 728a8c4..dfe6d3f 100644 --- a/frontend/src/i18n/translations/zh-TW.ts +++ b/frontend/src/i18n/translations/zh-TW.ts @@ -461,7 +461,7 @@ export default { "error.msg.not_linked": "此 {0} 帳號尚未關聯到任何帳號。", "error.msg.unverified_account": "This {0} account is unverified, please try again after verification.", - "error.msg.discord_guild_permission_denied": + "error.msg.user_not_allowed": "You are not allowed to sign in.", "error.msg.cannot_get_user_info": "Can not get your user info from this {0} account.",