microsoft/markitdown · error · ValueError
No channel found in RSS feed
Error message
No channel found in RSS feed
What it means
After _feed_type() classified the document as RSS (an <rss> element exists), _parse_rss_type() requires at least one <channel> child element. An <rss> root with no <channel> raises ValueError('No channel found in RSS feed'). Per the RSS 2.0 spec a channel is mandatory, so this fires on truncated or malformed feeds that still have the <rss> wrapper.
Source
Thrown at packages/markitdown/src/markitdown/converters/_rss_converter.py:141
if entry_summary:
md_text += self._parse_content(entry_summary)
if entry_content:
md_text += self._parse_content(entry_content)
return DocumentConverterResult(
markdown=md_text,
title=title,
)
def _parse_rss_type(self, doc: Document) -> DocumentConverterResult:
"""Parse the type of an RSS feed.
Returns None if the feed type is not recognized or something goes wrong.
"""
root = doc.getElementsByTagName("rss")[0]
channel_list = root.getElementsByTagName("channel")
if not channel_list:
raise ValueError("No channel found in RSS feed")
channel = channel_list[0]
channel_title = self._get_data_by_tag_name(channel, "title")
channel_description = self._get_data_by_tag_name(channel, "description")
items = channel.getElementsByTagName("item")
if channel_title:
md_text = f"# {channel_title}\n"
if channel_description:
md_text += f"{channel_description}\n"
for item in items:
title = self._get_data_by_tag_name(item, "title")
description = self._get_data_by_tag_name(item, "description")
pubDate = self._get_data_by_tag_name(item, "pubDate")
content = self._get_data_by_tag_name(item, "content:encoded")
if title:
md_text += f"\n## {title}\n"
if pubDate:
md_text += f"Published on: {pubDate}\n"View on GitHub (pinned to fd239d5d2b)
Solutions
- Check the feed with a validator (e.g. w3.org feed validator) and confirm the <channel> element exists inside <rss>
- Re-fetch the feed if it may have been truncated (verify Content-Length / try curl and inspect)
- If you control the producer, emit a valid RSS 2.0 document with a channel containing title/link/description
- Wrap conversion in a ValueError catch to skip malformed feeds in batch jobs
Example fix
# before
result = MarkItDown().convert('feed.rss') # ValueError: No channel found in RSS feed
# after: pre-check structure
import defusedxml.minidom as minidom
doc = minidom.parse('feed.rss')
if not doc.getElementsByTagName('rss')[0].getElementsByTagName('channel'):
raise SkipFile('malformed rss: no channel')
result = MarkItDown().convert('feed.rss') Defensive patterns
Strategy: validation
Validate before calling
from defusedxml import minidom
def rss_has_channel(raw: bytes) -> bool:
try:
doc = minidom.parseString(raw)
rss = doc.getElementsByTagName("rss")
return bool(rss) and bool(rss[0].getElementsByTagName("channel"))
except Exception:
return False Try / catch
try:
result = MarkItDown().convert("feed.rss")
except ValueError as e:
if "No channel found" in str(e):
logger.warning("malformed/truncated RSS feed; skipping") # skip in batch jobs Prevention
- Validate feeds (w3.org feed validator) before ingestion
- Fetch feeds completely (check Content-Length / verify with curl) before converting
- In batch pipelines, catch ValueError per feed and continue instead of aborting the run
When it happens
Trigger: Converting XML whose root is <rss> (e.g. <rss version='2.0'></rss> or <rss> containing only non-channel elements) with zero <channel> descendants; feeds truncated mid-transfer so the channel opening tag was lost; empty template files with just the rss skeleton.
Common situations: Scraping a partially downloaded feed over a flaky connection; feeds behind error pages that still emit an <rss> root; hand-built test fixtures missing the channel block.
Related errors
- Unknown feed type
- Unsupported file URI: {uri}. Netloc must be empty or localho
- Unsupported URI scheme: {uri.split(':')[0]}. Supported schem
- Not a file URL: {file_uri}
- Malformed data URI, missing ',' separator
AI-assisted analysis of microsoft/markitdown@fd239d5d2b (2026-08-14).
Data as JSON: /api/errors/aa907bc4c27eb168.
Report an issue: GitHub.