Enhance dashboard guild access with owner bypass functionality

- Introduced `resolveDashboardGuild` to handle guild resolution for both managed and owner-panel bypass scenarios.
- Updated `GuildLayout` and `WelcomePage` components to utilize the new guild resolution logic, improving access handling.
- Enhanced `DashboardShell` to display an informational banner for users accessing guilds via the owner-panel bypass.
- Added localization support for owner bypass messages in English and German.
- Updated authentication logic to allow owner-panel users to access guilds without Discord Manage Guild permission.
This commit is contained in:
smueller
2026-07-24 11:59:16 +02:00
parent e45642b6f9
commit 20593b7173
10 changed files with 133 additions and 22 deletions

View File

@@ -18,6 +18,8 @@ interface DashboardShellProps {
otherGuilds: DashboardGuild[];
user: SessionUser;
showOwnerLink?: boolean;
/** True when an Owner-panel user opened a guild they do not manage on Discord. */
ownerBypass?: boolean;
children: ReactNode;
}
@@ -27,6 +29,7 @@ export function DashboardShell({
otherGuilds,
user,
showOwnerLink = false,
ownerBypass = false,
children
}: DashboardShellProps) {
const t = useTranslations();
@@ -59,7 +62,21 @@ export function DashboardShell({
</div>
</header>
<main className="flex-1 px-4 py-6 sm:px-6 sm:py-8">
<div className="mx-auto w-full max-w-[1200px]">{children}</div>
<div className="mx-auto w-full max-w-[1200px] space-y-4">
{ownerBypass ? (
<div className="rounded-md border border-amber-500/40 bg-amber-500/10 px-4 py-3 text-sm text-amber-100">
<p className="font-medium">{t('dashboard.ownerBypass.title')}</p>
<p className="mt-1 text-amber-100/80">{t('dashboard.ownerBypass.description')}</p>
<a
href="/owner/guilds"
className="mt-2 inline-block text-sm font-medium text-amber-50 underline underline-offset-4 hover:text-white"
>
{t('dashboard.ownerBypass.backToOwner')}
</a>
</div>
) : null}
{children}
</div>
</main>
</div>
</div>

View File

@@ -1,5 +1,6 @@
'use client';
import Link from 'next/link';
import { useRouter } from 'next/navigation';
import { useMemo, useState, useTransition } from 'react';
import { toast } from 'sonner';
@@ -165,6 +166,9 @@ export function GuildsManager({
</div>
</div>
<div className="flex flex-wrap gap-2">
<Button size="sm" variant="default" asChild>
<Link href={`/dashboard/${guild.id}`}>{t('owner.guilds.openDashboard')}</Link>
</Button>
<Button
size="sm"
variant="outline"