import html
import re


def split_for_telegram(message: str, max_size: int = 4000) -> list[str]:
    if len(message) <= max_size:
        return [message]

    chunks: list[str] = []
    pending_content = message
    while pending_content:
        if len(pending_content) <= max_size:
            chunks.append(pending_content)
            break
        candidate_chunk = pending_content[:max_size]
        split_position = candidate_chunk.rfind("\n")
        if split_position < 0:
            split_position = candidate_chunk.rfind(" ")
        if split_position < 0:
            split_position = max_size
        chunks.append(pending_content[:split_position])
        pending_content = pending_content[split_position:].lstrip()
    return chunks


def markdown_to_telegram_html(markdown_text: str) -> str:
    if not markdown_text:
        return ""

    code_blocks: list[str] = []
    inline_codes: list[str] = []

    def capture_code_block(match: re.Match[str]) -> str:
        code_blocks.append(match.group(1))
        return f"\x00CB{len(code_blocks) - 1}\x00"

    def capture_inline_code(match: re.Match[str]) -> str:
        inline_codes.append(match.group(1))
        return f"\x00IC{len(inline_codes) - 1}\x00"

    telegram_text = re.sub(r"```[\w]*\n?([\s\S]*?)```", capture_code_block, markdown_text)
    telegram_text = re.sub(r"`([^`]+)`", capture_inline_code, telegram_text)
    telegram_text = re.sub(r"^#{1,6}\s+(.+)$", r"\1", telegram_text, flags=re.MULTILINE)
    telegram_text = re.sub(r"^>\s*(.*)$", r"\1", telegram_text, flags=re.MULTILINE)
    telegram_text = html.escape(telegram_text)
    telegram_text = re.sub(r"\[([^\]]+)\]\(([^)]+)\)", r'<a href="\2">\1</a>', telegram_text)
    telegram_text = re.sub(r"\*\*(.+?)\*\*", r"<b>\1</b>", telegram_text)
    telegram_text = re.sub(r"__(.+?)__", r"<b>\1</b>", telegram_text)
    telegram_text = re.sub(
        r"(?<![A-Za-z0-9])_([^_]+)_(?![A-Za-z0-9])",
        r"<i>\1</i>",
        telegram_text,
    )
    telegram_text = re.sub(r"~~(.+?)~~", r"<s>\1</s>", telegram_text)
    telegram_text = re.sub(r"^[-*]\s+", "• ", telegram_text, flags=re.MULTILINE)

    for index, code_content in enumerate(inline_codes):
        telegram_text = telegram_text.replace(
            f"\x00IC{index}\x00", f"<code>{html.escape(code_content)}</code>"
        )

    for index, code_content in enumerate(code_blocks):
        telegram_text = telegram_text.replace(
            f"\x00CB{index}\x00", f"<pre><code>{html.escape(code_content)}</code></pre>"
        )

    return telegram_text


def normalize_newlines(text: str) -> str:
    normalized = text.replace("\\r\\n", "\n").replace("\\r", "\n")
    return re.sub(r"\r\n?", "\n", normalized)
