feat: SEO altyapısı + admin editör/favicon/menü düzeltmeleri

Admin & site:
- @tailwindcss/typography ekle → editör ve yayın içeriği prose stilleriyle düzgün render
- Favicon: logo.png'den kare app/icon.png + apple-icon.png, varsayılan favicon.ico kaldırıldı
- SEO keyword: seo_settings.default_keywords + seo_pages.keywords + buildMetadata birleştirme
- Menü düzeni admin'den yönetilebilir (site_settings.nav_items, /admin/menu, header & mobile-menu refactor)

SEO:
- app/sitemap.ts (statik + blog/hizmet/çözüm/proje/sektör dinamik)
- app/robots.ts (sitemap ref + /admin,/api disallow)
- app/llms.txt/route.ts (AI/LLM rehberi)
- BlogPosting/Service/FAQ/Article JSON-LD wire (json-ld bileşenleri bağlandı)
- buildMetadata: blog/proje OG görseli + type article + keywords birleştirme düzeltmesi
- blog tags → keyword
This commit is contained in:
egecankomur
2026-06-04 07:15:18 +03:00
parent a321ac5c9b
commit d49c9aa225
26 changed files with 780 additions and 151 deletions
+96
View File
@@ -0,0 +1,96 @@
import { siteConfig } from "@/lib/site-config";
import {
getSeoSettings,
getSiteSettings,
listIndustries,
listProjects,
listPublishedPosts,
listServices,
listSolutions,
} from "@/lib/data";
// AI/LLM'lerin (ChatGPT, Perplexity, Claude, Google AI Overviews vb.) siteyi
// hızlı ve doğru anlaması için /llms.txt rehberi.
// Spec: https://llmstxt.org
export const revalidate = 3600;
const BASE = siteConfig.url;
function section(title: string, lines: string[]): string {
if (lines.length === 0) return "";
return `## ${title}\n\n${lines.join("\n")}\n`;
}
export async function GET() {
const [seo, site, services, solutions, posts, industries] = await Promise.all([
getSeoSettings(),
getSiteSettings(),
listServices(),
listSolutions(),
listPublishedPosts({ limit: 30 }),
listIndustries(),
]);
const name = seo?.site_name || siteConfig.name;
const summary =
seo?.site_description || site?.footer_tagline || siteConfig.tagline;
const phone = site?.contact_phone || siteConfig.contact.phone;
const email = site?.contact_email || siteConfig.contact.email;
const address = site?.contact_address || siteConfig.contact.address;
const link = (title: string, path: string, desc?: string) =>
`- [${title}](${BASE}${path})${desc ? `: ${desc}` : ""}`;
const body = [
`# ${name}`,
"",
`> ${summary}`,
"",
`${name}, Kocaeli/İzmit merkezli; yazılım geliştirme, web tasarım, e-ticaret, mobil uygulama, CRM ve dijital pazarlama hizmetleri sunar. İletişim: ${phone} · ${email} · ${address}`,
"",
section("Ana Sayfalar", [
link("Anasayfa", "/"),
link("Hizmetler", "/hizmetler", "Tüm hizmetlerin listesi"),
link("Çözümler", "/cozumler", "Paket çözümler"),
link("Projeler", "/projeler", "Portföy ve vaka çalışmaları"),
link("Blog", "/blog", "Rehber içerikler ve yazılar"),
link("Hakkımızda", "/hakkimizda"),
link("İletişim", "/iletisim"),
]),
section(
"Hizmetler",
services.map((s) =>
link(s.title, `/hizmetler/${s.slug}`, s.description ?? undefined),
),
),
section(
"Çözümler",
solutions.map((s) =>
link(s.title, `/cozumler/${s.slug}`, s.description ?? undefined),
),
),
section(
"Sektörler",
industries.map((i) =>
link(i.title, `/sektor/${i.slug}`, i.subtitle ?? undefined),
),
),
section(
"Blog Yazıları",
posts.map((p) =>
link(p.title, `/blog/${p.slug}`, p.excerpt ?? undefined),
),
),
section("Kaynaklar", [link("Site haritası", "/sitemap.xml")]),
]
.filter(Boolean)
.join("\n");
return new Response(body, {
headers: {
"Content-Type": "text/plain; charset=utf-8",
"Cache-Control": "public, max-age=0, s-maxage=3600, stale-while-revalidate=86400",
},
});
}