Merge remote-tracking branch 'origin/main' into dev/credits
This commit is contained in:
commit
98421afab8
@ -1,11 +1,21 @@
|
||||
import { DashboardHeader } from '@/components/dashboard/dashboard-header';
|
||||
import { getSession } from '@/lib/server';
|
||||
import { getTranslations } from 'next-intl/server';
|
||||
import { notFound } from 'next/navigation';
|
||||
|
||||
interface UsersLayoutProps {
|
||||
children: React.ReactNode;
|
||||
}
|
||||
|
||||
export default async function UsersLayout({ children }: UsersLayoutProps) {
|
||||
// if is demo website, allow user to access admin and user pages, but data is fake
|
||||
const isDemo = process.env.NEXT_PUBLIC_DEMO_WEBSITE === 'true';
|
||||
// Check if user is admin
|
||||
const session = await getSession();
|
||||
if (!session || (session.user.role !== 'admin' && !isDemo)) {
|
||||
notFound();
|
||||
}
|
||||
|
||||
const t = await getTranslations('Dashboard.admin');
|
||||
|
||||
const breadcrumbs = [
|
||||
|
@ -23,18 +23,22 @@ export default async function BillingLayout({ children }: BillingLayoutProps) {
|
||||
<>
|
||||
<DashboardHeader breadcrumbs={breadcrumbs} />
|
||||
|
||||
<div className="px-4 lg:px-6 py-16">
|
||||
<div className="max-w-6xl mx-auto space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('billing.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('billing.description')}
|
||||
</p>
|
||||
</div>
|
||||
<div className="flex flex-1 flex-col">
|
||||
<div className="@container/main flex flex-1 flex-col gap-2">
|
||||
<div className="flex flex-col gap-4 py-4 md:gap-6 md:py-6">
|
||||
<div className="px-4 lg:px-6 space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('billing.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('billing.description')}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{children}
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
|
@ -25,18 +25,22 @@ export default async function NotificationsLayout({
|
||||
<>
|
||||
<DashboardHeader breadcrumbs={breadcrumbs} />
|
||||
|
||||
<div className="px-4 lg:px-6 py-16">
|
||||
<div className="max-w-6xl mx-auto space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('notification.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('notification.description')}
|
||||
</p>
|
||||
</div>
|
||||
<div className="flex flex-1 flex-col">
|
||||
<div className="@container/main flex flex-1 flex-col gap-2">
|
||||
<div className="flex flex-col gap-4 py-4 md:gap-6 md:py-6">
|
||||
<div className="px-4 lg:px-6 space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('notification.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('notification.description')}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{children}
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
|
@ -2,7 +2,7 @@ import { NewsletterFormCard } from '@/components/settings/notification/newslette
|
||||
|
||||
export default function NotificationPage() {
|
||||
return (
|
||||
<div className="grid gap-8 md:grid-cols-2">
|
||||
<div className="grid gap-8 @lg/main:grid-cols-2">
|
||||
<NewsletterFormCard />
|
||||
</div>
|
||||
);
|
||||
|
@ -23,18 +23,22 @@ export default async function ProfileLayout({ children }: ProfileLayoutProps) {
|
||||
<>
|
||||
<DashboardHeader breadcrumbs={breadcrumbs} />
|
||||
|
||||
<div className="px-4 lg:px-6 py-16">
|
||||
<div className="max-w-6xl mx-auto space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('profile.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('profile.description')}
|
||||
</p>
|
||||
</div>
|
||||
<div className="flex flex-1 flex-col">
|
||||
<div className="@container/main flex flex-1 flex-col gap-2">
|
||||
<div className="flex flex-col gap-4 py-4 md:gap-6 md:py-6">
|
||||
<div className="px-4 lg:px-6 space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('profile.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('profile.description')}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{children}
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
|
@ -3,7 +3,7 @@ import { UpdateNameCard } from '@/components/settings/profile/update-name-card';
|
||||
|
||||
export default function ProfilePage() {
|
||||
return (
|
||||
<div className="grid gap-8 md:grid-cols-2">
|
||||
<div className="flex flex-col gap-8">
|
||||
<UpdateAvatarCard />
|
||||
<UpdateNameCard />
|
||||
</div>
|
||||
|
@ -25,18 +25,22 @@ export default async function SecurityLayout({
|
||||
<>
|
||||
<DashboardHeader breadcrumbs={breadcrumbs} />
|
||||
|
||||
<div className="px-4 lg:px-6 py-16">
|
||||
<div className="max-w-6xl mx-auto space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('security.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('security.description')}
|
||||
</p>
|
||||
</div>
|
||||
<div className="flex flex-1 flex-col">
|
||||
<div className="@container/main flex flex-1 flex-col gap-2">
|
||||
<div className="flex flex-col gap-4 py-4 md:gap-6 md:py-6">
|
||||
<div className="px-4 lg:px-6 space-y-10">
|
||||
<div>
|
||||
<h1 className="text-3xl font-bold tracking-tight">
|
||||
{t('security.title')}
|
||||
</h1>
|
||||
<p className="text-muted-foreground mt-2">
|
||||
{t('security.description')}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
{children}
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
|
@ -3,7 +3,7 @@ import { PasswordCardWrapper } from '@/components/settings/security/password-car
|
||||
|
||||
export default function SecurityPage() {
|
||||
return (
|
||||
<div className="grid gap-8 grid-cols-1">
|
||||
<div className="flex flex-col gap-8">
|
||||
<PasswordCardWrapper />
|
||||
<DeleteAccountCard />
|
||||
</div>
|
||||
|
@ -29,6 +29,9 @@ export function DashboardHeader({
|
||||
breadcrumbs,
|
||||
actions,
|
||||
}: DashboardHeaderProps) {
|
||||
// if is demo website, allow user to access admin and user pages, but data is fake
|
||||
const isDemo = process.env.NEXT_PUBLIC_DEMO_WEBSITE === 'true';
|
||||
|
||||
return (
|
||||
<header className="flex h-(--header-height) shrink-0 items-center gap-2 border-b transition-[width,height] ease-linear group-has-data-[collapsible=icon]/sidebar-wrapper:h-(--header-height)">
|
||||
<div className="flex w-full items-center gap-1 px-4 lg:gap-2 lg:px-6">
|
||||
@ -69,7 +72,7 @@ export function DashboardHeader({
|
||||
<div className="ml-auto flex items-center gap-3 px-4">
|
||||
{actions}
|
||||
|
||||
<ThemeSelector />
|
||||
{isDemo && <ThemeSelector />}
|
||||
<ModeSwitcher />
|
||||
<LocaleSwitcher />
|
||||
</div>
|
||||
|
Loading…
Reference in New Issue
Block a user