Files
Epicure/apps/web/app/(app)/settings/ai/page.tsx
T
Arnaud b2d592afe8 feat(settings): sidebar layout with profile, security, AI, notifications, nutrition
Sticky sidebar nav. Sections: Profile (name/language), Security (email/password change),
AI & Models (BYOK keys + per-use-case model prefs), Notifications (push subscribe),
Nutrition goals. Sub-pages: API keys, Webhooks.
2026-07-01 08:10:51 +02:00

48 lines
1.7 KiB
TypeScript
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
import type { Metadata } from "next";
import { headers } from "next/headers";
import { auth } from "@/lib/auth/server";
import { db, userAiKeys, userModelPrefs, eq } from "@epicure/db";
import { ByokManager } from "@/components/settings/byok-manager";
import { ModelPrefsForm } from "@/components/settings/model-prefs-form";
export const metadata: Metadata = { title: "AI & Models Settings" };
export default async function AiSettingsPage() {
const session = await auth.api.getSession({ headers: await headers() });
if (!session) return null;
const [aiKeys, modelPrefs] = await Promise.all([
db.query.userAiKeys.findMany({
where: eq(userAiKeys.userId, session.user.id),
columns: { provider: true },
}),
db.query.userModelPrefs.findFirst({
where: eq(userModelPrefs.userId, session.user.id),
}),
]);
return (
<div className="space-y-8">
<section className="rounded-xl border p-6 space-y-4">
<div>
<h2 className="font-semibold text-lg">Your API Keys (BYOK)</h2>
<p className="text-sm text-muted-foreground mt-1">
Use your own API keys instead of the app&apos;s shared quota. Keys are encrypted at rest.
</p>
</div>
<ByokManager initialKeys={aiKeys.map((k) => k.provider)} />
</section>
<section className="rounded-xl border p-6 space-y-4">
<div>
<h2 className="font-semibold text-lg">Model Preferences</h2>
<p className="text-sm text-muted-foreground mt-1">
Choose which model to use for each task. Defaults to your first configured provider.
</p>
</div>
<ModelPrefsForm initialPrefs={modelPrefs ?? null} />
</section>
</div>
);
}