Files
Anime-Movies-Upcomming-Real…/embed_builder.py
2026-04-22 10:04:59 +02:00

111 lines
3.6 KiB
Python

#!/usr/bin/env python3
from __future__ import annotations
import html
import re
import discord
def is_missing(value: str | None) -> bool:
text = (value or "").strip().lower()
return text in {"", "n/a", "none", "null"}
def fit_embed_value(text: str, max_len: int = 1000) -> str:
value = (text or "").strip()
if is_missing(value):
value = "Unbekannt"
if len(value) <= max_len:
return value
return value[: max_len - 3] + "..."
def fit_embed_description(text: str, max_len: int = 3800) -> str:
value = (text or "").strip()
if len(value) <= max_len:
return value
return value[: max_len - 3] + "..."
def format_tag_badges(tags_text: str) -> str:
if is_missing(tags_text):
return "Unbekannt"
parts = [part.strip() for part in tags_text.split(",") if part.strip()]
if not parts:
return "Unbekannt"
return " ".join(f"`{part}`" for part in parts)
def format_single_badge(text: str) -> str:
if is_missing(text):
return "Unbekannt"
return f"`{fit_embed_value(text, max_len=200)}`"
def compact_text(text: str) -> str:
raw = text or ""
raw = re.sub(r"<\s*br\s*/?\s*>", " ", raw, flags=re.IGNORECASE)
raw = re.sub(r"</\s*p\s*>", " ", raw, flags=re.IGNORECASE)
raw = re.sub(r"<[^>]+>", "", raw)
raw = html.unescape(raw)
return " ".join(raw.replace("\n", " ").split())
def add_line(lines: list[str], label: str, value: str) -> None:
if is_missing(value):
return
lines.append(f"**{label}:** {fit_embed_value(value)}")
def make_links_view(anilist_url: str) -> discord.ui.View | None:
if is_missing(anilist_url):
return None
view = discord.ui.View(timeout=None)
view.add_item(discord.ui.Button(label="Zum Anime", style=discord.ButtonStyle.link, url=anilist_url))
return view
def build_movie_embed(item: dict, index: int) -> discord.Embed:
title = fit_embed_value(
str(item.get("title_schedule_english") or item.get("title_english_anilist") or item.get("title", "")),
max_len=200,
)
anilist_url = str(item.get("anilist_url", "")).strip()
embed = discord.Embed(
title=title,
url=anilist_url if not is_missing(anilist_url) else None,
color=discord.Color.from_rgb(30, 144, 255),
)
tags_badges = format_tag_badges(str(item.get("tags", "")))
genres_badges = format_tag_badges(str(item.get("genres", "")))
romaji_badge = format_single_badge(str(item.get("title_romaji", "")))
native_badge = format_single_badge(str(item.get("title_native", "")))
description_text = compact_text(str(item.get("description", "")))
lines: list[str] = []
add_line(lines, "Anime Typ", str(item.get("format", "")))
add_line(lines, "Genres", genres_badges)
add_line(lines, "Tags", tags_badges)
add_line(lines, "Release", str(item.get("release", "")))
add_line(lines, "Studios", str(item.get("studio", "")))
add_line(lines, "Romaji", romaji_badge)
add_line(lines, "Nativ", native_badge)
add_line(lines, "Beschreibung", description_text)
embed.description = fit_embed_description("\n".join(lines) if lines else "Keine Details verfuegbar")
cover = (item.get("cover_image") or "").strip()
if cover:
embed.set_image(url=cover)
embed.set_footer(
text=(
"Daten: AniList, AnimeSchedule, TMDB | "
"This product uses the TMDB API but is not endorsed or certified by TMDB. "
f"| Eintrag #{index}"
)
)
return embed