feat(ui): complete phase 4 Poyraz UI foundation
This commit is contained in:
@@ -22,7 +22,7 @@ type AnalyticsClientProps = {
|
||||
data: AnalyticsData;
|
||||
};
|
||||
|
||||
const COLORS = ["hsl(var(--primary))", "hsl(var(--destructive))", "#eab308", "#3b82f6", "#8b5cf6"];
|
||||
const COLORS = ["var(--poyraz-primary)", "var(--poyraz-destructive)", "#eab308", "#3b82f6", "#8b5cf6"];
|
||||
|
||||
export function AnalyticsClient({ data }: AnalyticsClientProps) {
|
||||
const router = useRouter();
|
||||
@@ -98,8 +98,8 @@ export function AnalyticsClient({ data }: AnalyticsClientProps) {
|
||||
<Tooltip
|
||||
formatter={(value) => `₺${Number(value ?? 0)}`}
|
||||
contentStyle={{
|
||||
backgroundColor: 'hsl(var(--background))',
|
||||
borderColor: 'hsl(var(--border))',
|
||||
backgroundColor: 'var(--poyraz-background)',
|
||||
borderColor: 'var(--poyraz-border)',
|
||||
borderRadius: '0.375rem',
|
||||
}}
|
||||
/>
|
||||
@@ -119,9 +119,9 @@ export function AnalyticsClient({ data }: AnalyticsClientProps) {
|
||||
<div className="h-[300px] w-full">
|
||||
<ResponsiveContainer width="100%" height="100%">
|
||||
<BarChart data={taskStatusData}>
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="hsl(var(--border))" />
|
||||
<XAxis dataKey="name" axisLine={false} tickLine={false} tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }} dy={10} />
|
||||
<YAxis axisLine={false} tickLine={false} tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }} dx={-10} />
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="var(--poyraz-border)" />
|
||||
<XAxis dataKey="name" axisLine={false} tickLine={false} tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }} dy={10} />
|
||||
<YAxis axisLine={false} tickLine={false} tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }} dx={-10} />
|
||||
<Tooltip
|
||||
cursor={{ fill: 'transparent' }}
|
||||
content={({ active, payload, label }) => {
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function AnalyticsLoading() {
|
||||
return (
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function ClientsLoading() {
|
||||
return (
|
||||
|
||||
@@ -111,18 +111,18 @@ export function DashboardClient({ data }: DashboardClientProps) {
|
||||
{incomeTrendData.length > 0 ? (
|
||||
<ResponsiveContainer width="100%" height="100%">
|
||||
<BarChart data={incomeTrendData}>
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="hsl(var(--border))" />
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="var(--poyraz-border)" />
|
||||
<XAxis
|
||||
dataKey="name"
|
||||
axisLine={false}
|
||||
tickLine={false}
|
||||
tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }}
|
||||
tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }}
|
||||
dy={10}
|
||||
/>
|
||||
<YAxis
|
||||
axisLine={false}
|
||||
tickLine={false}
|
||||
tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }}
|
||||
tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }}
|
||||
dx={-10}
|
||||
/>
|
||||
<Tooltip
|
||||
@@ -181,26 +181,26 @@ export function DashboardClient({ data }: DashboardClientProps) {
|
||||
{moodTrendData.length > 0 ? (
|
||||
<ResponsiveContainer width="100%" height="100%">
|
||||
<LineChart data={moodTrendData}>
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="hsl(var(--border))" />
|
||||
<CartesianGrid strokeDasharray="3 3" vertical={false} stroke="var(--poyraz-border)" />
|
||||
<XAxis
|
||||
dataKey="date"
|
||||
axisLine={false}
|
||||
tickLine={false}
|
||||
tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }}
|
||||
tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }}
|
||||
dy={10}
|
||||
/>
|
||||
<YAxis
|
||||
domain={[0, 5]}
|
||||
axisLine={false}
|
||||
tickLine={false}
|
||||
tick={{ fontSize: 12, fill: 'hsl(var(--muted-foreground))' }}
|
||||
tick={{ fontSize: 12, fill: 'var(--poyraz-muted-foreground)' }}
|
||||
width={30}
|
||||
dx={-10}
|
||||
/>
|
||||
<Tooltip
|
||||
contentStyle={{
|
||||
backgroundColor: 'hsl(var(--background))',
|
||||
borderColor: 'hsl(var(--border))',
|
||||
backgroundColor: 'var(--poyraz-background)',
|
||||
borderColor: 'var(--poyraz-border)',
|
||||
borderRadius: '0.375rem',
|
||||
boxShadow: '0 4px 6px -1px rgb(0 0 0 / 0.1), 0 2px 4px -2px rgb(0 0 0 / 0.1)'
|
||||
}}
|
||||
@@ -208,9 +208,9 @@ export function DashboardClient({ data }: DashboardClientProps) {
|
||||
<Line
|
||||
type="monotone"
|
||||
dataKey="mood"
|
||||
stroke="hsl(var(--primary))"
|
||||
stroke="var(--poyraz-primary)"
|
||||
strokeWidth={3}
|
||||
dot={{ r: 4, fill: "hsl(var(--primary))", strokeWidth: 2, stroke: "hsl(var(--background))" }}
|
||||
dot={{ r: 4, fill: "var(--poyraz-primary)", strokeWidth: 2, stroke: "var(--poyraz-background)" }}
|
||||
activeDot={{ r: 6, strokeWidth: 0 }}
|
||||
/>
|
||||
<Line
|
||||
@@ -218,7 +218,7 @@ export function DashboardClient({ data }: DashboardClientProps) {
|
||||
dataKey="energy"
|
||||
stroke="#eab308"
|
||||
strokeWidth={3}
|
||||
dot={{ r: 4, fill: "#eab308", strokeWidth: 2, stroke: "hsl(var(--background))" }}
|
||||
dot={{ r: 4, fill: "#eab308", strokeWidth: 2, stroke: "var(--poyraz-background)" }}
|
||||
activeDot={{ r: 6, strokeWidth: 0 }}
|
||||
/>
|
||||
</LineChart>
|
||||
|
||||
@@ -138,12 +138,12 @@ export function JournalClient({ logs }: JournalClientProps) {
|
||||
<div className="h-80">
|
||||
<ResponsiveContainer width="100%" height="100%">
|
||||
<LineChart data={chartData} margin={{ left: -16, right: 16, top: 12, bottom: 0 }}>
|
||||
<CartesianGrid strokeDasharray="3 3" stroke="hsl(var(--border))" />
|
||||
<CartesianGrid strokeDasharray="3 3" stroke="var(--poyraz-border)" />
|
||||
<XAxis dataKey="date" tickLine={false} axisLine={false} fontSize={12} />
|
||||
<YAxis domain={[1, 5]} tickCount={5} tickLine={false} axisLine={false} fontSize={12} />
|
||||
<Tooltip
|
||||
contentStyle={{
|
||||
border: "1px solid hsl(var(--border))",
|
||||
border: "1px solid var(--poyraz-border)",
|
||||
borderRadius: 4,
|
||||
boxShadow: "0 10px 30px rgba(15, 23, 42, 0.08)",
|
||||
}}
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import { DashboardShell } from "@/components/layout/dashboard-shell";
|
||||
import { requireFreelancer } from "@/server/auth/session";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
export default async function DashboardLayout({
|
||||
children,
|
||||
@@ -7,6 +8,7 @@ export default async function DashboardLayout({
|
||||
children: React.ReactNode;
|
||||
}>) {
|
||||
const { user, profile } = await requireFreelancer();
|
||||
const branding = getPublicBranding();
|
||||
const displayName = profile.displayName || user.name || user.email.split("@")[0] || "Neta Kullanıcısı";
|
||||
|
||||
const shortName =
|
||||
@@ -20,6 +22,12 @@ export default async function DashboardLayout({
|
||||
|
||||
return (
|
||||
<DashboardShell
|
||||
branding={{
|
||||
applicationName: branding.applicationName,
|
||||
organizationName: branding.organizationName,
|
||||
lightLogoUrl: branding.lightLogoUrl,
|
||||
darkLogoUrl: branding.darkLogoUrl,
|
||||
}}
|
||||
user={{
|
||||
email: user.email,
|
||||
displayName,
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function DashboardLoading() {
|
||||
return (
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function ProjectDetailLoading() {
|
||||
return (
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function ProjectsLoading() {
|
||||
return (
|
||||
|
||||
@@ -1,5 +1,4 @@
|
||||
import { Skeleton } from "@/components/ui/skeleton";
|
||||
import { Card, CardContent } from "poyraz-ui/atoms";
|
||||
import { Card, CardContent, Skeleton } from "poyraz-ui/atoms";
|
||||
|
||||
export default function TasksLoading() {
|
||||
return (
|
||||
|
||||
+8
-120
@@ -1,85 +1,13 @@
|
||||
@import "tailwindcss";
|
||||
@import "poyraz-ui/preset.css";
|
||||
|
||||
@source "../app/**/*.{js,ts,jsx,tsx,mdx}";
|
||||
@source "../components/**/*.{js,ts,jsx,tsx,mdx}";
|
||||
@source "../config/**/*.{js,ts,jsx,tsx,mdx}";
|
||||
|
||||
@theme inline {
|
||||
--font-sans: var(--font-geist-sans);
|
||||
--color-background: var(--background);
|
||||
--color-background-dark: var(--background-dark);
|
||||
--color-foreground: var(--foreground);
|
||||
--color-surface: var(--surface);
|
||||
--color-surface-raised: var(--surface-raised);
|
||||
--color-card: var(--card);
|
||||
--color-card-foreground: var(--card-foreground);
|
||||
--color-popover: var(--popover);
|
||||
--color-popover-foreground: var(--popover-foreground);
|
||||
--color-primary: var(--primary);
|
||||
--color-primary-foreground: var(--primary-foreground);
|
||||
--color-primary-hover: var(--primary-hover);
|
||||
--color-primary-pressed: var(--primary-pressed);
|
||||
--color-secondary: var(--secondary);
|
||||
--color-secondary-foreground: var(--secondary-foreground);
|
||||
--color-muted: var(--muted);
|
||||
--color-muted-foreground: var(--muted-foreground);
|
||||
--color-accent: var(--accent);
|
||||
--color-accent-hover: var(--accent-hover);
|
||||
--color-accent-foreground: var(--accent-foreground);
|
||||
--color-destructive: var(--destructive);
|
||||
--color-destructive-hover: var(--destructive-hover);
|
||||
--color-destructive-pressed: var(--destructive-pressed);
|
||||
--color-destructive-foreground: var(--destructive-foreground);
|
||||
--color-success: var(--success);
|
||||
--color-info: var(--info);
|
||||
--color-border: var(--border);
|
||||
--color-border-strong: var(--border-strong);
|
||||
--color-input: var(--input);
|
||||
--color-input-bg: var(--input-bg);
|
||||
--color-ring: var(--ring);
|
||||
--radius-sm: 4px;
|
||||
--radius-md: 6px;
|
||||
--radius-lg: 8px;
|
||||
--radius-xl: 8px;
|
||||
}
|
||||
|
||||
@layer base {
|
||||
:root {
|
||||
--background: #f7f8fb;
|
||||
--background-dark: #f8fafc;
|
||||
--foreground: #101828;
|
||||
--surface: #ffffff;
|
||||
--surface-raised: #ffffff;
|
||||
--card: #ffffff;
|
||||
--card-foreground: #101828;
|
||||
--popover: #ffffff;
|
||||
--popover-foreground: #101828;
|
||||
--primary: #c81e1e;
|
||||
--primary-foreground: #ffffff;
|
||||
--primary-hover: #a91b1b;
|
||||
--primary-pressed: #861515;
|
||||
--secondary: #eef2f7;
|
||||
--secondary-foreground: #182230;
|
||||
--muted: #eef2f7;
|
||||
--muted-foreground: #667085;
|
||||
--accent: #e6edf5;
|
||||
--accent-hover: #d8e2ee;
|
||||
--accent-foreground: #101828;
|
||||
--destructive: #d92d20;
|
||||
--destructive-hover: #b42318;
|
||||
--destructive-pressed: #912018;
|
||||
--destructive-foreground: #ffffff;
|
||||
--success: #168a4a;
|
||||
--info: #2563eb;
|
||||
--border: #d9e0ea;
|
||||
--border-strong: #b9c4d2;
|
||||
--input: #b9c4d2;
|
||||
--input-bg: #ffffff;
|
||||
--overlay: rgba(15, 23, 42, 0.48);
|
||||
--ring: #c81e1e;
|
||||
--radius: 0.375rem;
|
||||
--motion-duration-fast: 120ms;
|
||||
--motion-duration-base: 180ms;
|
||||
--poyraz-font-primary: var(--font-geist-sans), ui-sans-serif, system-ui, sans-serif;
|
||||
}
|
||||
|
||||
* {
|
||||
@@ -90,48 +18,8 @@
|
||||
color-scheme: light;
|
||||
}
|
||||
|
||||
:root[data-color-mode="dark"] {
|
||||
:root.dark {
|
||||
color-scheme: dark;
|
||||
--background: #0b1018;
|
||||
--background-dark: #0b1018;
|
||||
--foreground: #f2f4f7;
|
||||
--surface: #121926;
|
||||
--surface-raised: #182230;
|
||||
--card: #121926;
|
||||
--card-foreground: #f2f4f7;
|
||||
--popover: #182230;
|
||||
--popover-foreground: #f2f4f7;
|
||||
--secondary: #253044;
|
||||
--secondary-foreground: #f2f4f7;
|
||||
--muted: #253044;
|
||||
--muted-foreground: #98a2b3;
|
||||
--border: #344054;
|
||||
--border-strong: #475467;
|
||||
--input: #475467;
|
||||
--input-bg: #121926;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
:root[data-color-mode="system"] {
|
||||
color-scheme: dark;
|
||||
--background: #0b1018;
|
||||
--background-dark: #0b1018;
|
||||
--foreground: #f2f4f7;
|
||||
--surface: #121926;
|
||||
--surface-raised: #182230;
|
||||
--card: #121926;
|
||||
--card-foreground: #f2f4f7;
|
||||
--popover: #182230;
|
||||
--popover-foreground: #f2f4f7;
|
||||
--secondary: #253044;
|
||||
--secondary-foreground: #f2f4f7;
|
||||
--muted: #253044;
|
||||
--muted-foreground: #98a2b3;
|
||||
--border: #344054;
|
||||
--border-strong: #475467;
|
||||
--input: #475467;
|
||||
--input-bg: #121926;
|
||||
}
|
||||
}
|
||||
|
||||
body {
|
||||
@@ -144,8 +32,8 @@
|
||||
input:-webkit-autofill:hover,
|
||||
input:-webkit-autofill:focus,
|
||||
input:-webkit-autofill:active {
|
||||
-webkit-box-shadow: 0 0 0 30px var(--input-bg) inset !important;
|
||||
-webkit-text-fill-color: var(--foreground) !important;
|
||||
-webkit-box-shadow: 0 0 0 30px var(--poyraz-surface) inset !important;
|
||||
-webkit-text-fill-color: var(--poyraz-foreground) !important;
|
||||
transition: background-color 5000s ease-in-out 0s;
|
||||
}
|
||||
}
|
||||
@@ -153,7 +41,7 @@
|
||||
@layer utilities {
|
||||
* {
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: color-mix(in srgb, var(--primary) 45%, transparent) transparent;
|
||||
scrollbar-color: color-mix(in srgb, var(--poyraz-primary) 45%, transparent) transparent;
|
||||
}
|
||||
|
||||
*::-webkit-scrollbar,
|
||||
@@ -169,7 +57,7 @@
|
||||
|
||||
*::-webkit-scrollbar-thumb,
|
||||
.tiny-scrollbar::-webkit-scrollbar-thumb {
|
||||
background: color-mix(in srgb, var(--primary) 36%, transparent);
|
||||
background: color-mix(in srgb, var(--poyraz-primary) 36%, transparent);
|
||||
border: 2px solid transparent;
|
||||
border-radius: 999px;
|
||||
background-clip: padding-box;
|
||||
@@ -177,7 +65,7 @@
|
||||
|
||||
*::-webkit-scrollbar-thumb:hover,
|
||||
.tiny-scrollbar::-webkit-scrollbar-thumb:hover {
|
||||
background: color-mix(in srgb, var(--primary) 58%, transparent);
|
||||
background: color-mix(in srgb, var(--poyraz-primary) 58%, transparent);
|
||||
background-clip: padding-box;
|
||||
}
|
||||
|
||||
|
||||
@@ -5,9 +5,10 @@ import { acceptInvitation } from "./actions";
|
||||
import { AuthPageShell } from "@/components/auth/auth-page-shell";
|
||||
import { SubmitButton } from "@/components/auth/submit-button";
|
||||
import { ErrorToaster } from "@/components/error-toaster";
|
||||
import { Input } from "@/components/ui/input";
|
||||
import { Label } from "@/components/ui/field";
|
||||
import { Input, Label } from "poyraz-ui/atoms";
|
||||
import { Alert, AlertDescription } from "poyraz-ui/molecules";
|
||||
import { getPortalInvitationPreview } from "@/server/auth/invitations";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
export const dynamic = "force-dynamic";
|
||||
|
||||
@@ -20,6 +21,7 @@ export default async function InvitationPage({
|
||||
}) {
|
||||
const { token } = await params;
|
||||
const invitation = getPortalInvitationPreview(token);
|
||||
const branding = getPublicBranding();
|
||||
|
||||
if (!invitation) {
|
||||
notFound();
|
||||
@@ -40,6 +42,11 @@ export default async function InvitationPage({
|
||||
<>
|
||||
{query.error && query.message ? <ErrorToaster message={query.message} /> : null}
|
||||
<AuthPageShell
|
||||
branding={{
|
||||
applicationName: branding.applicationName,
|
||||
lightLogoUrl: branding.lightLogoUrl,
|
||||
darkLogoUrl: branding.darkLogoUrl,
|
||||
}}
|
||||
title="Müşteri portalına katıl"
|
||||
description="Davet edilen hesabın için adını ve şifreni belirle."
|
||||
form={
|
||||
@@ -75,7 +82,9 @@ export default async function InvitationPage({
|
||||
</SubmitButton>
|
||||
</form>
|
||||
) : (
|
||||
<p className="text-sm text-muted-foreground">{unavailableMessage}</p>
|
||||
<Alert variant="warning" appearance="soft">
|
||||
<AlertDescription>{unavailableMessage}</AlertDescription>
|
||||
</Alert>
|
||||
)
|
||||
}
|
||||
secondaryAction={null}
|
||||
|
||||
+12
-2
@@ -4,10 +4,17 @@ import "./globals.css";
|
||||
import { Geist } from "next/font/google";
|
||||
import { cn } from "@/lib/utils";
|
||||
import { OfflineIndicator } from "@/components/ui/offline-indicator";
|
||||
import { Toaster } from "@/components/ui/toast";
|
||||
import { Toaster } from "poyraz-ui/molecules";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
const geist = Geist({ subsets: ["latin"], variable: "--font-geist-sans" });
|
||||
const colorModeScript = `(() => {
|
||||
const root = document.documentElement;
|
||||
const media = window.matchMedia("(prefers-color-scheme: dark)");
|
||||
const apply = () => root.classList.toggle("dark", root.dataset.colorMode === "dark" || (root.dataset.colorMode === "system" && media.matches));
|
||||
apply();
|
||||
if (root.dataset.colorMode === "system") media.addEventListener("change", apply);
|
||||
})();`;
|
||||
|
||||
export function generateMetadata(): Metadata {
|
||||
const branding = getPublicBranding();
|
||||
@@ -42,10 +49,13 @@ export default function RootLayout({
|
||||
style={branding.cssVariables as CSSProperties}
|
||||
suppressHydrationWarning
|
||||
>
|
||||
<head>
|
||||
<script dangerouslySetInnerHTML={{ __html: colorModeScript }} />
|
||||
</head>
|
||||
<body>
|
||||
{children}
|
||||
<OfflineIndicator />
|
||||
<Toaster />
|
||||
<Toaster closeButton richColors position="top-right" />
|
||||
</body>
|
||||
</html>
|
||||
);
|
||||
|
||||
+12
-5
@@ -3,9 +3,10 @@ import { AuthPageShell } from "@/components/auth/auth-page-shell";
|
||||
import { ErrorToaster } from "@/components/error-toaster";
|
||||
import { LockKeyhole, LogIn, Mail } from "lucide-react";
|
||||
import Link from "next/link";
|
||||
import { Input } from "@/components/ui/input";
|
||||
import { Label } from "@/components/ui/field";
|
||||
import { Input, Label } from "poyraz-ui/atoms";
|
||||
import { Alert, AlertDescription } from "poyraz-ui/molecules";
|
||||
import { SubmitButton } from "@/components/auth/submit-button";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
export default async function LoginPage({
|
||||
searchParams,
|
||||
@@ -15,19 +16,25 @@ export default async function LoginPage({
|
||||
const resolvedParams = await searchParams;
|
||||
const error = resolvedParams?.error;
|
||||
const message = resolvedParams?.message;
|
||||
const branding = getPublicBranding();
|
||||
|
||||
return (
|
||||
<>
|
||||
{error && message && <ErrorToaster message={String(message)} />}
|
||||
<AuthPageShell
|
||||
branding={{
|
||||
applicationName: branding.applicationName,
|
||||
lightLogoUrl: branding.lightLogoUrl,
|
||||
darkLogoUrl: branding.darkLogoUrl,
|
||||
}}
|
||||
title="Giriş yap"
|
||||
description="Neta çalışma alanına erişmek için hesabına giriş yap."
|
||||
form={
|
||||
<form className="space-y-6">
|
||||
{!error && message ? (
|
||||
<p className="rounded-md border border-success/30 bg-success/5 p-3 text-sm text-foreground">
|
||||
{String(message)}
|
||||
</p>
|
||||
<Alert variant="success" appearance="soft">
|
||||
<AlertDescription>{String(message)}</AlertDescription>
|
||||
</Alert>
|
||||
) : null}
|
||||
<div className="space-y-4">
|
||||
<div className="space-y-2">
|
||||
|
||||
@@ -1,5 +1,6 @@
|
||||
import { PortalShell } from "@/components/layout/portal-shell";
|
||||
import { requireClientUser } from "@/server/auth/session";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
export default async function PortalLayout({
|
||||
children,
|
||||
@@ -7,6 +8,7 @@ export default async function PortalLayout({
|
||||
children: React.ReactNode;
|
||||
}>) {
|
||||
const { user, profile } = await requireClientUser();
|
||||
const branding = getPublicBranding();
|
||||
const displayName = profile.displayName || user.name || user.email.split("@")[0] || "Müşteri";
|
||||
|
||||
const shortName =
|
||||
@@ -20,6 +22,12 @@ export default async function PortalLayout({
|
||||
|
||||
return (
|
||||
<PortalShell
|
||||
branding={{
|
||||
applicationName: branding.applicationName,
|
||||
organizationName: branding.organizationName,
|
||||
lightLogoUrl: branding.lightLogoUrl,
|
||||
darkLogoUrl: branding.darkLogoUrl,
|
||||
}}
|
||||
user={{
|
||||
email: user.email,
|
||||
displayName,
|
||||
|
||||
@@ -5,9 +5,9 @@ import { getFirstFreelancerSetupState } from "@/server/auth/setup";
|
||||
import { LockKeyhole, Mail, UserPlus } from "lucide-react";
|
||||
import Link from "next/link";
|
||||
import { redirect } from "next/navigation";
|
||||
import { Input } from "@/components/ui/input";
|
||||
import { Label } from "@/components/ui/field";
|
||||
import { Input, Label } from "poyraz-ui/atoms";
|
||||
import { SubmitButton } from "@/components/auth/submit-button";
|
||||
import { getPublicBranding } from "@/server/branding/runtime";
|
||||
|
||||
export const dynamic = "force-dynamic";
|
||||
|
||||
@@ -33,11 +33,17 @@ export default async function RegisterPage({
|
||||
const resolvedParams = await searchParams;
|
||||
const error = resolvedParams?.error;
|
||||
const message = resolvedParams?.message;
|
||||
const branding = getPublicBranding();
|
||||
|
||||
return (
|
||||
<>
|
||||
{error && message && <ErrorToaster message={String(message)} />}
|
||||
<AuthPageShell
|
||||
branding={{
|
||||
applicationName: branding.applicationName,
|
||||
lightLogoUrl: branding.lightLogoUrl,
|
||||
darkLogoUrl: branding.darkLogoUrl,
|
||||
}}
|
||||
title="İlk admin hesabını oluştur"
|
||||
description="Bu Neta çalışma alanının ilk yönetici hesabını oluştur."
|
||||
form={
|
||||
|
||||
Reference in New Issue
Block a user