Skip to content

Commit ed4d057

Browse files
authored
Merge branch 'main' into feat/rework-sections
Signed-off-by: Marius Ahsmus <marius.ahsmus@gmail.com>
2 parents d732098 + 7adbc73 commit ed4d057

16 files changed

Lines changed: 690 additions & 297 deletions

File tree

next-sitemap.config.cjs

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/** @type {import('next-sitemap').IConfig} */
2+
const siteUrl = process.env.NEXT_PUBLIC_APP_URL || "https://code0.tech"
3+
4+
module.exports = {
5+
siteUrl,
6+
generateRobotsTxt: true,
7+
generateIndexSitemap: false,
8+
exclude: [
9+
"/admin/*",
10+
"/api/*",
11+
"/en/checkout",
12+
"/de/checkout",
13+
],
14+
alternateRefs: [
15+
{ href: `${siteUrl}/en`, hreflang: "en" },
16+
{ href: `${siteUrl}/de`, hreflang: "de" },
17+
],
18+
robotsTxtOptions: {
19+
additionalSitemaps: [
20+
`${siteUrl}/server-sitemap.xml`,
21+
],
22+
},
23+
additionalPaths: async () => {
24+
const locales = ["en", "de"]
25+
26+
const staticPaths = [
27+
"",
28+
"about-us",
29+
"actions",
30+
"blog",
31+
"community-edition",
32+
"contact",
33+
"enterprise-edition",
34+
"features",
35+
"jobs",
36+
"legal-notice",
37+
"privacy",
38+
"subscription",
39+
"terms",
40+
]
41+
42+
return locales.flatMap((locale) =>
43+
staticPaths.map((path) => ({
44+
loc: path ? `/${locale}/${path}` : `/${locale}`,
45+
changefreq: "weekly",
46+
priority: path ? 0.7 : 1,
47+
lastmod: new Date().toISOString()
48+
}))
49+
)
50+
}
51+
}

package-lock.json

Lines changed: 374 additions & 142 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 10 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
"scripts": {
77
"dev": "next dev",
88
"build": "next build",
9-
"postbuild": "node scripts/prepare-standalone.mjs",
9+
"postbuild": "next-sitemap --config next-sitemap.config.cjs && node scripts/prepare-standalone.mjs",
1010
"start": "next start",
1111
"standalone": "node .next/standalone/server.js",
1212
"migrate": "payload migrate",
@@ -18,9 +18,9 @@
1818
"generate": "payload generate:types"
1919
},
2020
"dependencies": {
21-
"@c15t/nextjs": "^2.0.0",
21+
"@c15t/nextjs": "^2.0.4",
2222
"@c15t/scripts": "^2.0.1",
23-
"@code0-tech/pictor": "^0.6.4",
23+
"@code0-tech/pictor": "^0.7.1",
2424
"@icons-pack/react-simple-icons": "^13.13.0",
2525
"@payloadcms/db-postgres": "3.84.1",
2626
"@payloadcms/email-nodemailer": "3.84.1",
@@ -31,9 +31,10 @@
3131
"@tabler/icons-react": "3.41.1",
3232
"clsx": "^2.1.1",
3333
"graphql": "^16.13.2",
34-
"knip": "^6.7.0",
34+
"knip": "^6.11.0",
3535
"motion": "^12.38.0",
3636
"next": "^16.2.4",
37+
"next-sitemap": "^4.2.3",
3738
"ogl": "^1.0.11",
3839
"payload": "3.84.1",
3940
"react": "^19.2.5",
@@ -48,18 +49,18 @@
4849
"@types/node": "^25.6.0",
4950
"@types/react": "^19.2.14",
5051
"@types/react-dom": "^19.2.3",
51-
"postcss": "^8.5.10",
52+
"postcss": "^8.5.14",
5253
"tailwindcss": "^4.2.4",
5354
"tsx": "^4.21.0",
5455
"typescript": "^6.0.3"
5556
},
5657
"overrides": {
57-
"nodemailer": "8.0.6",
58+
"nodemailer": "8.0.7",
5859
"lodash": "4.18.1",
5960
"file-type": "22.0.0",
60-
"undici": "8.1.0",
61-
"dompurify": "3.4.1",
62-
"yaml": "2.8.3",
61+
"undici": "8.2.0",
62+
"dompurify": "3.4.2",
63+
"yaml": "2.8.4",
6364
"@esbuild-kit/core-utils": {
6465
"esbuild": "0.28.0"
6566
}

public/robots.txt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
# *
2+
User-agent: *
3+
Allow: /
4+
5+
# Host
6+
Host: https://localhost:3000
7+
8+
# Sitemaps
9+
Sitemap: https://localhost:3000/sitemap.xml
10+
Sitemap: https://localhost:3000/server-sitemap.xml

public/sitemap.xml

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
<?xml version="1.0" encoding="UTF-8"?>
2+
<urlset xmlns="http://www.sitemaps.org/schemas/sitemap/0.9" xmlns:news="http://www.google.com/schemas/sitemap-news/0.9" xmlns:xhtml="http://www.w3.org/1999/xhtml" xmlns:mobile="http://www.google.com/schemas/sitemap-mobile/1.0" xmlns:image="http://www.google.com/schemas/sitemap-image/1.1" xmlns:video="http://www.google.com/schemas/sitemap-video/1.1">
3+
<url><loc>https://localhost:3000</loc><lastmod>2026-05-04T18:30:07.461Z</lastmod><changefreq>daily</changefreq><priority>0.7</priority><xhtml:link rel="alternate" hreflang="en" href="https://localhost:3000/en"/><xhtml:link rel="alternate" hreflang="de" href="https://localhost:3000/de"/></url>
4+
<url><loc>https://localhost:3000/robots.txt</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>daily</changefreq><priority>0.7</priority><xhtml:link rel="alternate" hreflang="en" href="https://localhost:3000/en/robots.txt"/><xhtml:link rel="alternate" hreflang="de" href="https://localhost:3000/de/robots.txt"/></url>
5+
<url><loc>https://localhost:3000/en</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>1</priority></url>
6+
<url><loc>https://localhost:3000/en/about-us</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
7+
<url><loc>https://localhost:3000/en/actions</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
8+
<url><loc>https://localhost:3000/en/blog</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
9+
<url><loc>https://localhost:3000/en/community-edition</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
10+
<url><loc>https://localhost:3000/en/contact</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
11+
<url><loc>https://localhost:3000/en/enterprise-edition</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
12+
<url><loc>https://localhost:3000/en/features</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
13+
<url><loc>https://localhost:3000/en/jobs</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
14+
<url><loc>https://localhost:3000/en/legal-notice</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
15+
<url><loc>https://localhost:3000/en/privacy</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
16+
<url><loc>https://localhost:3000/en/subscription</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
17+
<url><loc>https://localhost:3000/en/terms</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
18+
<url><loc>https://localhost:3000/de</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>1</priority></url>
19+
<url><loc>https://localhost:3000/de/about-us</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
20+
<url><loc>https://localhost:3000/de/actions</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
21+
<url><loc>https://localhost:3000/de/blog</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
22+
<url><loc>https://localhost:3000/de/community-edition</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
23+
<url><loc>https://localhost:3000/de/contact</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
24+
<url><loc>https://localhost:3000/de/enterprise-edition</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
25+
<url><loc>https://localhost:3000/de/features</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
26+
<url><loc>https://localhost:3000/de/jobs</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
27+
<url><loc>https://localhost:3000/de/legal-notice</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
28+
<url><loc>https://localhost:3000/de/privacy</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
29+
<url><loc>https://localhost:3000/de/subscription</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
30+
<url><loc>https://localhost:3000/de/terms</loc><lastmod>2026-05-04T18:30:07.462Z</lastmod><changefreq>weekly</changefreq><priority>0.7</priority></url>
31+
</urlset>

src/app/(landing)/[locale]/actions/[slug]/page.tsx

Lines changed: 2 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@ import { Aurora } from "@/components/ui/Aurora"
44
import { HapticButtonLink } from "@/components/ui/HapticButtonLink"
55
import { LandingContainer } from "@/components/ui/LandingContainer"
66
import { LinkButton } from "@/components/ui/LinkButton"
7-
import { getActionBySlug, getActionSlugs, getLandingPage, type ActionsLayoutBlock } from "@/lib/cms"
8-
import { SUPPORTED_LOCALES, isSupportedLocale } from "@/lib/i18n"
7+
import { getActionBySlug, getLandingPage, type ActionsLayoutBlock } from "@/lib/cms"
8+
import { isSupportedLocale } from "@/lib/i18n"
99
import { createMetadata } from "@/lib/siteConfig"
1010
import type { Media } from "@/payload-types"
1111
import { IconArrowLeft, IconExternalLink } from "@tabler/icons-react"
@@ -137,15 +137,3 @@ export async function generateMetadata({ params }: { params: Promise<{ locale: s
137137
})
138138
}
139139

140-
export async function generateStaticParams() {
141-
const all = await Promise.all(
142-
SUPPORTED_LOCALES.map(async (locale) => {
143-
const slugs = await getActionSlugs(locale)
144-
return slugs.map((slug) => ({ locale, slug }))
145-
})
146-
)
147-
148-
return all.flat()
149-
}
150-
151-
export const dynamicParams = false

src/app/(landing)/[locale]/blog/[slug]/page.tsx

Lines changed: 6 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,17 +1,17 @@
11
import { BlogPost } from "@/components/blog/BlogPost"
22
import { BlogSkeleton } from "@/components/blog/BlogSkeleton"
3+
import { InteractiveGridPattern } from "@/components/InteractiveGridPattern"
34
import { Aurora } from "@/components/ui/Aurora"
5+
import { HapticButtonLink } from "@/components/ui/HapticButtonLink"
46
import { LandingContainer } from "@/components/ui/LandingContainer"
5-
import { type Media } from "@/payload-types"
6-
import { SUPPORTED_LOCALES, isSupportedLocale } from "@/lib/i18n"
7-
import { getBlogPostBySlug, getBlogSlugs, getLandingPage, type CtaLayoutBlock } from "@/lib/cms"
7+
import { getBlogPostBySlug, getLandingPage, type CtaLayoutBlock } from "@/lib/cms"
8+
import { isSupportedLocale } from "@/lib/i18n"
89
import { createMetadata, resolveSiteUrl } from "@/lib/siteConfig"
10+
import { type Media } from "@/payload-types"
911
import type { Metadata } from "next"
10-
import { notFound } from "next/navigation"
1112
import Image from "next/image"
13+
import { notFound } from "next/navigation"
1214
import { Suspense } from "react"
13-
import { InteractiveGridPattern } from "@/components/InteractiveGridPattern"
14-
import { HapticButtonLink } from "@/components/ui/HapticButtonLink"
1515

1616
function getMediaUrl(value?: number | Media | null) {
1717
if (!value || typeof value === "number" || !value.url) {
@@ -119,14 +119,3 @@ export async function generateMetadata({ params }: { params: Promise<{ locale: s
119119
})
120120
}
121121

122-
export async function generateStaticParams() {
123-
const all = await Promise.all(
124-
SUPPORTED_LOCALES.map(async (locale) => {
125-
const slugs = await getBlogSlugs(locale)
126-
return slugs.map((slug) => ({ locale, slug }))
127-
})
128-
)
129-
return all.flat()
130-
}
131-
132-
export const dynamicParams = false

src/app/(landing)/[locale]/jobs/[slug]/page.tsx

Lines changed: 2 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -2,9 +2,9 @@ import { JobDetailContent } from "@/components/JobDetailContent"
22
import { Aurora } from "@/components/ui/Aurora"
33
import { LandingContainer } from "@/components/ui/LandingContainer"
44
import { createMetadata } from "@/lib/siteConfig"
5-
import { SUPPORTED_LOCALES, isSupportedLocale } from "@/lib/i18n"
5+
import { isSupportedLocale } from "@/lib/i18n"
66
import { getLandingPage, type JobsLayoutBlock } from "@/lib/cms"
7-
import { getJobBySlug, getJobSlugs } from "@/lib/cms"
7+
import { getJobBySlug } from "@/lib/cms"
88
import { convertLexicalToHTML } from "@payloadcms/richtext-lexical/html"
99
import type { Metadata } from "next"
1010
import { notFound } from "next/navigation"
@@ -51,14 +51,3 @@ export async function generateMetadata({ params }: { params: Promise<{ locale: s
5151
})
5252
}
5353

54-
export async function generateStaticParams() {
55-
const all = await Promise.all(
56-
SUPPORTED_LOCALES.map(async (locale) => {
57-
const slugs = await getJobSlugs(locale)
58-
return slugs.map((slug) => ({ locale, slug }))
59-
})
60-
)
61-
return all.flat()
62-
}
63-
64-
export const dynamicParams = false

src/app/(landing)/[locale]/layout.tsx

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,8 @@ import { Navigation } from "@/components/navigation/Navigation"
33
import { FooterSection } from "@/components/sections/FooterSection"
44
import { getFooter } from "@/lib/cms"
55
import { getNavbarItems } from "@/lib/cms"
6-
import { SUPPORTED_LOCALES, isSupportedLocale } from "@/lib/i18n"
6+
import { getSections } from "@/lib/cms"
7+
import { isSupportedLocale } from "@/lib/i18n"
78
import type { ReactNode } from "react"
89
import { notFound } from "next/navigation"
910

@@ -12,11 +13,8 @@ interface LocaleLayoutProps {
1213
params: Promise<{ locale: string }>
1314
}
1415

15-
export function generateStaticParams() {
16-
return SUPPORTED_LOCALES.map((locale) => ({ locale }))
17-
}
18-
1916
export const revalidate = 300
17+
export const dynamic = "force-dynamic"
2018

2119
export default async function LocaleLayout({ children, params }: LocaleLayoutProps) {
2220
const { locale } = await params

src/app/(landing)/[locale]/page.tsx

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2,15 +2,16 @@ import { DeploymentImage } from "@/components/DeploymentImage"
22
import { PageBlocks } from "@/components/PageBlockRenderer"
33
import { LandingContainer } from "@/components/ui/LandingContainer"
44
import { getLandingPage } from "@/lib/cms"
5-
import { isSupportedLocale, SUPPORTED_LOCALES } from "@/lib/i18n"
5+
import type { DeploymentLayoutBlock, HeroLayoutBlock } from "@/lib/cms"
6+
import type { BrandLayoutBlock } from "@/lib/cms"
7+
import type { CtaLayoutBlock } from "@/lib/cms"
8+
import type { FaqLayoutBlock } from "@/lib/cms"
9+
import type { UseCaseLayoutBlock } from "@/lib/cms"
10+
import { isSupportedLocale } from "@/lib/i18n"
611
import { getLandingPageMetadata } from "@/lib/pageMetadata"
712
import type { Metadata } from "next"
813
import { notFound } from "next/navigation"
914

10-
export function generateStaticParams() {
11-
return SUPPORTED_LOCALES.map((locale) => ({ locale }))
12-
}
13-
1415
export async function generateMetadata({ params }: { params: Promise<{ locale: string }> }): Promise<Metadata> {
1516
const { locale } = await params
1617
return getLandingPageMetadata("main", locale)

0 commit comments

Comments
 (0)