feat(katalog): YÖK İstatistik öğrenci/öğretim üyesi verisi ve Türkiye sıralaması sayfası

- src/lib/yok-istatistik.ts (scripts/yok-istatistik-uret.py ile üretilir):
  üniversite başına örgün öğrenci ve öğretim üyesi, öğrenci/üye oranı ve
  Türkiye medyanı; katalog detayına `istatistik` alanı
- /universite-siralamasi: URAP Türkiye sıralaması sayfası (URAP logosu ve
  zorunlu urapcenter.org atfıyla), sitemap'e eklendi
This commit is contained in:
bilalgursen
2026-09-24 00:01:41 +03:00
parent 22accb1241
commit 5df0af0d38
8 changed files with 652 additions and 0 deletions

View File

@@ -0,0 +1,123 @@
import Link from "next/link";
import { getAllUniversiteler } from "../katalog-queries";
import { trBaslikDuzeni } from "@/lib/slug";
import { UNITUR_ETIKET } from "@/lib/unitur";
import { UniLogo } from "@/components/uni-logo";
import { PagePixelDivider } from "@/components/pixel-decor";
import { UrapLogo } from "./urap-logo";
import {
URAP_DONEM,
URAP_KAYNAK_URL,
URAP_SIRA,
URAP_TOPLAM,
} from "@/lib/urap-siralama";
const sayi = (n: number) => n.toLocaleString("tr-TR");
const puanYaz = (n: number) =>
n.toLocaleString("tr-TR", {
minimumFractionDigits: 2,
maximumFractionDigits: 2,
});
/**
* URAP atfı: izin "urapcenter.org adresine aktif bağlantı" şartına bağlı —
* gerçek <a href>, yeni sekme, rel="noopener", nofollow YOK. Sayfanın başında
* ve sonunda tekrar edilir, liste uzun olduğundan sıra sayısıyla aynı ekranda
* kalsın.
*/
function UrapAtfi() {
return (
<a
href={URAP_KAYNAK_URL}
target="_blank"
rel="noopener"
className="font-medium text-primary hover:underline"
>
urapcenter.org
</a>
);
}
export function TurkiyeSiralamasi() {
const ozetler = new Map(getAllUniversiteler().map((u) => [u.slug, u]));
const satirlar = Object.entries(URAP_SIRA)
.map(([slug, u]) => ({ slug, ...u, ozet: ozetler.get(slug) }))
.sort((a, b) => a.sira - b.sira);
const enYuksek = satirlar[0]?.puan ?? 1;
return (
<>
<div className="mt-4 flex flex-col-reverse gap-4 sm:flex-row sm:items-start sm:justify-between sm:gap-8">
<p className="max-w-3xl text-sm leading-7 text-slate-600">
Türkiye&apos;deki {sayi(URAP_TOPLAM)} üniversitenin URAP (University
Ranking by Academic Performance) {URAP_DONEM} genel sıralaması. URAP,
üniversiteleri yayın, atıf, proje ve doktora gibi{" "}
<strong>akademik yayın ve araştırma performansı</strong>{" "}
göstergeleriyle puanlar; eğitim kalitesini ya da mezunların iş bulma
oranını ölçmez. Bölüm seçerken tek başına ölçüt değil, taban
sıralamayla birlikte bakılacak bir bilgi. Kaynak: <UrapAtfi />.
</p>
<UrapLogo className="h-10 sm:h-12" />
</div>
<PagePixelDivider seed={71} className="mt-8" />
<ol className="mt-8 divide-y divide-slate-100 overflow-hidden rounded-xl border border-slate-200 bg-white">
{satirlar.map((u) => {
const ad = u.ozet?.ad ?? trBaslikDuzeni(u.slug.replace(/-/g, " "));
const tur = u.ozet?.unitur ? UNITUR_ETIKET[u.ozet.unitur]?.cip : null;
const alt = [u.ozet?.il ? trBaslikDuzeni(u.ozet.il) : null, tur]
.filter(Boolean)
.join(" · ");
return (
<li key={u.slug}>
<Link
href={`/universite/${u.slug}`}
className="group flex items-center gap-3 px-3 py-3 hover:bg-slate-50 sm:gap-4 sm:px-5"
>
<span className="w-9 shrink-0 text-right font-heading text-lg font-bold tabular-nums text-slate-900 sm:w-11 sm:text-xl">
{u.sira}
</span>
<UniLogo slug={u.slug} ad={ad} boy="sm" />
<span className="min-w-0 flex-1">
<span className="block truncate text-sm font-medium text-slate-800 group-hover:text-primary group-hover:underline">
{ad}
</span>
{alt ? (
<span className="block text-xs text-slate-400">{alt}</span>
) : null}
</span>
<span className="hidden w-40 shrink-0 items-center gap-3 sm:flex">
<span
className="h-1.5 flex-1 overflow-hidden rounded-full bg-slate-100"
aria-hidden
>
<span
className="block h-full rounded-full bg-primary/60"
style={{ width: `${(u.puan / enYuksek) * 100}%` }}
/>
</span>
<span className="w-14 text-right text-xs tabular-nums text-slate-500">
{puanYaz(u.puan)}
</span>
</span>
</Link>
</li>
);
})}
</ol>
<div className="mt-4 flex flex-col gap-3 sm:flex-row sm:items-center sm:gap-6">
<UrapLogo className="h-8" />
<p className="text-xs leading-5 text-slate-500">
Sağdaki sayı URAP toplam puanıdır. Listede olmayan üniversite
sıralamaya girmemiştir — KKTC/yurt dışı kurumlar ve araştırma çıktısı
henüz oluşmamış yeni üniversiteler listede yer almaz; bu,
&quot;kötü&quot; demek değildir. URAP Türkiye Sıralaması {URAP_DONEM},
URAP Araştırma Laboratuvarı&apos;nın izniyle yayımlanmıştır. Kaynak:{" "}
<UrapAtfi />.
</p>
</div>
</>
);
}

View File

@@ -0,0 +1,28 @@
import Image from "next/image";
import { URAP_KAYNAK_URL } from "@/lib/urap-siralama";
/**
* URAP logosu, urapcenter.org'a aktif bağlantı olarak. Atıf şartı gereği
* gerçek <a href>, yeni sekme, rel="noopener", nofollow YOK. Logo resmî
* PNG'den (urapcenter.org/img/urap-logo/logo.png) vektörleştirildi —
* `public/urap-logo.svg`, oran 819×261.
*/
export function UrapLogo({ className = "h-8" }: { className?: string }) {
return (
<a
href={URAP_KAYNAK_URL}
target="_blank"
rel="noopener"
className="relative z-10 inline-block shrink-0 opacity-90 transition-opacity hover:opacity-100"
>
<Image
src="/urap-logo.svg"
alt="URAP — University Ranking by Academic Performance"
width={819}
height={261}
unoptimized
className={`w-auto ${className}`}
/>
</a>
);
}