diff --git a/astrbot/core/knowledge_base/parsers/util.py b/astrbot/core/knowledge_base/parsers/util.py index a98ed60ed2..4d3eb53854 100644 --- a/astrbot/core/knowledge_base/parsers/util.py +++ b/astrbot/core/knowledge_base/parsers/util.py @@ -2,7 +2,28 @@ async def select_parser(ext: str) -> BaseParser: - if ext in {".md", ".txt", ".markdown", ".rst", ".adoc", ".xlsx", ".docx", ".xls"}: + # Markdown variants that the MarkdownChunker whitelist in kb_helper + # already accepts; parse them as plain text without extra dependencies. + if ext in {".mdx", ".mkd"}: + from .text_parser import TextParser + + return TextParser() + # Formats supported by markitdown-no-magika (verified converters: + # HtmlConverter, CsvConverter, PlainTextConverter; note it has no + # RTF converter, so .rtf stays unsupported). + if ext in { + ".csv", + ".html", + ".htm", + ".md", + ".txt", + ".markdown", + ".rst", + ".adoc", + ".xlsx", + ".docx", + ".xls", + }: from .markitdown_parser import MarkitdownParser return MarkitdownParser() diff --git a/tests/test_kb_parser_routing.py b/tests/test_kb_parser_routing.py new file mode 100644 index 0000000000..99a21d82a6 --- /dev/null +++ b/tests/test_kb_parser_routing.py @@ -0,0 +1,45 @@ +from __future__ import annotations + +import pytest + +from astrbot.core.knowledge_base.parsers.markitdown_parser import MarkitdownParser +from astrbot.core.knowledge_base.parsers.text_parser import TextParser +from astrbot.core.knowledge_base.parsers.util import select_parser + + +@pytest.mark.parametrize("ext", [".mdx", ".mkd"]) +@pytest.mark.asyncio +async def test_markdown_variants_use_text_parser(ext: str) -> None: + # These extensions are accepted by the MarkdownChunker whitelist in + # kb_helper but previously had no parser route, so uploads always + # failed with "暂时不支持的文件格式". + parser = await select_parser(ext) + + assert isinstance(parser, TextParser) + + +@pytest.mark.parametrize("ext", [".html", ".htm", ".csv"]) +@pytest.mark.asyncio +async def test_html_csv_use_markitdown_parser(ext: str) -> None: + parser = await select_parser(ext) + + assert isinstance(parser, MarkitdownParser) + + +@pytest.mark.asyncio +async def test_markitdown_parses_html_and_csv() -> None: + html = b"
Hello world
" + result = await MarkitdownParser().parse(html, "a.html") + assert "Title" in result.text and "Hello **world**" in result.text + + csv = b"name,age\nalice,1\n" + result = await MarkitdownParser().parse(csv, "a.csv") + assert "alice" in result.text + + +@pytest.mark.asyncio +async def test_rtf_still_unsupported() -> None: + # markitdown-no-magika 0.1.2 has no RTF converter, so .rtf must keep + # raising instead of being routed to a parser that cannot handle it. + with pytest.raises(ValueError, match="暂时不支持的文件格式"): + await select_parser(".rtf")