const UMLAUT_REPLACEMENTS: Record<string, string> = {
    Ae: "Ae",
    Oe: "Oe",
    Ue: "Ue",
    ae: "ae",
    oe: "oe",
    ue: "ue",
    ss: "ss",
    Ä: "Ae",
    Ö: "Oe",
    Ü: "Ue",
    ä: "ae",
    ö: "oe",
    ü: "ue",
    ß: "ss"
}

function replaceGermanCharacters(value: string) {
    return value.replace(/[ÄÖÜäöüß]/g, (char) => UMLAUT_REPLACEMENTS[char] || char)
}

function sanitizeFileNamePart(value: string) {
    return value
        .normalize("NFKD")
        .replace(/[\u0300-\u036f]/g, "")
        .replace(/[^A-Za-z0-9._-]+/g, "-")
        .replace(/-+/g, "-")
        .replace(/[._-]{2,}/g, (match) => match[0])
        .replace(/^[._-]+|[._-]+$/g, "")
}

export function sanitizeFilename(filename?: string | null, fallback = "file") {
    const rawName = (filename || "").trim()

    if (!rawName) {
        return fallback
    }

    const normalized = replaceGermanCharacters(rawName)
        .replace(/[\u0000-\u001f\u007f]/g, "")
        .replace(/[\\/]/g, "-")

    const lastDotIndex = normalized.lastIndexOf(".")
    const hasExtension = lastDotIndex > 0 && lastDotIndex < normalized.length - 1

    const basename = hasExtension ? normalized.slice(0, lastDotIndex) : normalized
    const extension = hasExtension ? normalized.slice(lastDotIndex + 1) : ""

    const safeBasename = sanitizeFileNamePart(basename) || fallback
    const safeExtension = extension ? sanitizeFileNamePart(extension).toLowerCase() : ""

    return safeExtension ? `${safeBasename}.${safeExtension}` : safeBasename
}
