Files
Portfolio/src/app/[locale]/imprint/page.tsx
T
damjan_savicandClaude Opus 4.5 b1ec7b4d61 Migrate from Vite to Next.js 15 with SSR
- Replace Vite + React Router with Next.js 15 App Router
- Implement i18n with next-intl (URL-based: /de, /en, /sr)
- Add SSR/SSG for all pages (48 static pages generated)
- Setup Supabase SSR client for auth
- Migrate all pages: Home, About, Portfolio, Blog, Contact, Login, Dashboard, Imprint, Privacy, Terms
- Add Docker support with standalone output
- Replace i18next with next-intl JSON translations
- Use next/image for optimized images

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-17 01:00:33 +01:00

277 lines
10 KiB
TypeScript

import { setRequestLocale } from 'next-intl/server';
import Link from 'next/link';
import type { Metadata } from 'next';
type Props = {
params: Promise<{ locale: string }>;
};
export async function generateMetadata({ params }: Props): Promise<Metadata> {
const { locale } = await params;
const titles: Record<string, string> = {
de: 'Impressum',
en: 'Imprint',
sr: 'Impresum',
};
const descriptions: Record<string, string> = {
de: 'Impressum fuer die Portfolio-Website von Damjan Savic',
en: 'Legal notice for Damjan Savic portfolio website',
sr: 'Pravno obavestenje za portfolio veb sajt Damjana Savica',
};
return {
title: titles[locale] || titles.de,
description: descriptions[locale] || descriptions.de,
};
}
export default async function ImprintPage({ params }: Props) {
const { locale } = await params;
setRequestLocale(locale);
const content: Record<string, {
title: string;
contact: { title: string; content: string[] };
liability: { title: string; sections: { title: string; content: string }[] };
copyright: { title: string; content: string };
images: { title: string; content: string[] };
privacy: { title: string; content: string; link: string };
technical: { title: string; design: string; tech: string };
copyrightNotice: string;
}> = {
de: {
title: 'Impressum',
contact: {
title: 'Kontakt',
content: [
'Damjan Savic',
'Fullstack Developer & Digital Solutions Consultant',
'E-Mail: info@damjan-savic.com',
'Website: https://damjan-savic.com',
],
},
liability: {
title: 'Haftungsausschluss',
sections: [
{
title: 'Haftung fuer Inhalte',
content: 'Die Inhalte meiner Seiten wurden mit groesster Sorgfalt erstellt. Fuer die Richtigkeit, Vollstaendigkeit und Aktualitaet der Inhalte kann ich jedoch keine Gewaehr uebernehmen.',
},
{
title: 'Haftung fuer Links',
content: 'Meine Website enthaelt Links zu externen Websites Dritter, auf deren Inhalte ich keinen Einfluss habe. Deshalb kann ich fuer diese fremden Inhalte auch keine Gewaehr uebernehmen. Fuer die Inhalte der verlinkten Seiten ist stets der jeweilige Anbieter oder Betreiber der Seiten verantwortlich.',
},
],
},
copyright: {
title: 'Urheberrecht',
content: 'Die durch den Seitenbetreiber erstellten Inhalte und Werke auf diesen Seiten unterliegen dem deutschen Urheberrecht. Die Vervielfaeltigung, Bearbeitung, Verbreitung und jede Art der Verwertung ausserhalb der Grenzen des Urheberrechtes beduerfen der schriftlichen Zustimmung des jeweiligen Autors bzw. Erstellers.',
},
images: {
title: 'Bildnachweise',
content: [
'Eigene Aufnahmen und Erstellungen',
'Icons: Heroicons, Tabler Icons (MIT Lizenz)',
'Weitere Bildquellen sind direkt bei den jeweiligen Bildern angegeben',
],
},
privacy: {
title: 'Datenschutz',
content: 'Die Nutzung unserer Webseite ist in der Regel ohne Angabe personenbezogener Daten moeglich. Weitere Informationen zum Datenschutz finden Sie in unserer',
link: 'Datenschutzerklaerung',
},
technical: {
title: 'Technische Umsetzung',
design: 'Design & Entwicklung: Damjan Savic',
tech: 'Technologien: Next.js, TypeScript, Tailwind CSS',
},
copyrightNotice: 'Alle Rechte vorbehalten.',
},
en: {
title: 'Legal Notice',
contact: {
title: 'Contact',
content: [
'Damjan Savic',
'Fullstack Developer & Digital Solutions Consultant',
'Email: info@damjan-savic.com',
'Website: https://damjan-savic.com',
],
},
liability: {
title: 'Disclaimer',
sections: [
{
title: 'Liability for Content',
content: 'The contents of my pages were created with the utmost care. However, I cannot guarantee the accuracy, completeness and timeliness of the content.',
},
{
title: 'Liability for Links',
content: 'My website contains links to external websites of third parties, over whose content I have no influence. Therefore, I cannot assume any liability for this external content. The respective provider or operator of the pages is always responsible for the content of the linked pages.',
},
],
},
copyright: {
title: 'Copyright',
content: 'The content and works created by the site operator on these pages are subject to German copyright law. Reproduction, editing, distribution and any kind of exploitation outside the limits of copyright require the written consent of the respective author or creator.',
},
images: {
title: 'Image Credits',
content: [
'Own photographs and creations',
'Icons: Heroicons, Tabler Icons (MIT License)',
'Other image sources are indicated directly at the respective images',
],
},
privacy: {
title: 'Privacy',
content: 'The use of our website is generally possible without providing personal data. For more information on data protection, please see our',
link: 'Privacy Policy',
},
technical: {
title: 'Technical Implementation',
design: 'Design & Development: Damjan Savic',
tech: 'Technologies: Next.js, TypeScript, Tailwind CSS',
},
copyrightNotice: 'All rights reserved.',
},
sr: {
title: 'Pravno obavestenje',
contact: {
title: 'Kontakt',
content: [
'Damjan Savic',
'Fullstack Developer & Digital Solutions Consultant',
'Email: info@damjan-savic.com',
'Website: https://damjan-savic.com',
],
},
liability: {
title: 'Odricanje od odgovornosti',
sections: [
{
title: 'Odgovornost za sadrzaj',
content: 'Sadrzaj mojih stranica je kreiran sa najvecom paznjom. Medjutim, ne mogu garantovati tacnost, potpunost i aktuelnost sadrzaja.',
},
{
title: 'Odgovornost za linkove',
content: 'Moja web stranica sadrzi linkove ka eksternim web stranicama trecih lica, na ciji sadrzaj nemam uticaja. Stoga ne mogu preuzeti nikakvu odgovornost za ovaj eksterni sadrzaj.',
},
],
},
copyright: {
title: 'Autorska prava',
content: 'Sadrzaj i dela koja je kreirao vlasnik sajta na ovim stranicama podlezu nemackom zakonu o autorskim pravima.',
},
images: {
title: 'Krediti za slike',
content: [
'Sopstvene fotografije i kreacije',
'Ikone: Heroicons, Tabler Icons (MIT Licenca)',
'Drugi izvori slika su naznaceni direktno kod odgovarajucih slika',
],
},
privacy: {
title: 'Privatnost',
content: 'Koriscenje nase web stranice je generalno moguce bez navodjenja licnih podataka. Za vise informacija o zastiti podataka, pogledajte nasu',
link: 'Politiku privatnosti',
},
technical: {
title: 'Tehnicka implementacija',
design: 'Dizajn i razvoj: Damjan Savic',
tech: 'Tehnologije: Next.js, TypeScript, Tailwind CSS',
},
copyrightNotice: 'Sva prava zadrzana.',
},
};
const c = content[locale] || content.de;
return (
<main className="min-h-screen py-16 sm:py-20 lg:py-24">
<div className="max-w-4xl mx-auto px-4 sm:px-6 lg:px-8">
{/* Breadcrumb */}
<nav className="mb-8">
<Link
href={`/${locale}`}
className="text-zinc-400 hover:text-white transition-colors"
>
Home
</Link>
<span className="mx-2 text-zinc-600">/</span>
<span className="text-white">{c.title}</span>
</nav>
<h1 className="text-4xl font-bold text-white mb-8">{c.title}</h1>
<div className="prose prose-invert max-w-none space-y-8">
{/* Contact */}
<section className="bg-zinc-900/50 p-6 rounded-xl ring-1 ring-zinc-800">
<h2 className="text-2xl font-semibold text-white mb-4">{c.contact.title}</h2>
<div className="text-zinc-300 space-y-1">
{c.contact.content.map((line, index) => (
<p key={index}>{line}</p>
))}
</div>
</section>
{/* Liability */}
<section>
<h2 className="text-2xl font-semibold text-white mb-4">{c.liability.title}</h2>
{c.liability.sections.map((section, index) => (
<div key={index} className="mb-4">
<h3 className="text-xl font-medium text-white mb-2">{section.title}</h3>
<p className="text-zinc-300">{section.content}</p>
</div>
))}
</section>
{/* Copyright */}
<section>
<h2 className="text-2xl font-semibold text-white mb-4">{c.copyright.title}</h2>
<p className="text-zinc-300">{c.copyright.content}</p>
</section>
{/* Images */}
<section>
<h2 className="text-2xl font-semibold text-white mb-4">{c.images.title}</h2>
<ul className="list-disc list-inside text-zinc-300 space-y-1">
{c.images.content.map((item, index) => (
<li key={index}>{item}</li>
))}
</ul>
</section>
{/* Privacy */}
<section>
<h2 className="text-2xl font-semibold text-white mb-4">{c.privacy.title}</h2>
<p className="text-zinc-300">
{c.privacy.content}{' '}
<Link href={`/${locale}/privacy`} className="text-orange-500 hover:text-orange-400 underline">
{c.privacy.link}
</Link>
.
</p>
</section>
{/* Technical */}
<section className="bg-zinc-900/50 p-6 rounded-xl ring-1 ring-zinc-800">
<h2 className="text-2xl font-semibold text-white mb-4">{c.technical.title}</h2>
<p className="text-zinc-300">{c.technical.design}</p>
<p className="text-zinc-300">{c.technical.tech}</p>
</section>
{/* Copyright Notice */}
<section>
<p className="text-zinc-400">
&copy; {new Date().getFullYear()} Damjan Savic. {c.copyrightNotice}
</p>
</section>
</div>
</div>
</main>
);
}