Unicode i slugs: «Grønt er skjønt» → grønt-er-skjønt

Bokstaver og tall i alle skriftsystemer beholdes, alt annet blir
bindestrek. NFC-normalisering gir samme slug uansett om ø/å kommer
prekomponert eller som base + kombinerende tegn (macOS). URL-er i
feed.xml percent-encodes siden RSS-lesere krever ASCII.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01JcEy43fNYpwg6K6oTKakWR
This commit is contained in:
Ole-Morten Duesund 2026-08-26 14:02:07 +02:00
commit 1218c5d650
4 changed files with 26 additions and 20 deletions

View file

@ -1,7 +1,10 @@
"""Lager URL-vennlige slugs fra titler.
Norske tegn translittereres eksplisitt (æae, øoe, åaa) fordi generisk
unicode-normalisering ville mistet dem helt ("blåbær" "blbr").
Unicode-bokstaver beholdes ("Grønt er skjønt" "grønt-er-skjønt"); moderne
nettlesere og servere håndterer UTF-8 i stier, og det gir penere og mer
lesbare adresser enn translitterering. Teksten NFC-normaliseres slik at
f.eks. «ø» skrevet som base + kombinerende tegn (vanlig fra macOS) gir samme
slug som det prekomponerte tegnet.
"""
from __future__ import annotations
@ -9,15 +12,13 @@ from __future__ import annotations
import re
import unicodedata
_NORDIC = str.maketrans(
{"æ": "ae", "ø": "oe", "å": "aa", "ä": "ae", "ö": "oe", "ü": "ue", "ß": "ss"}
)
# Alt som ikke er bokstav eller tall (i alle skriftsystemer) blir skilletegn.
_SEP = re.compile(r"[^\w]+|_+", re.UNICODE)
def slugify(text: str) -> str:
text = text.lower().translate(_NORDIC)
text = unicodedata.normalize("NFKD", text).encode("ascii", "ignore").decode()
text = re.sub(r"[^a-z0-9]+", "-", text).strip("-")
text = unicodedata.normalize("NFC", text).casefold()
text = _SEP.sub("-", text).strip("-")
return text or "post"