RSS, Atom and web feeds

Feed structure and required elements, item versus entry fields, the date and identifier rules that decide whether a reader shows your post once or twice, and how to validate a feed.

The two feed vocabularies

<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom">
  <channel>
    <title>Example Engineering</title>
    <link>https://example.com/blog</link>
    <description>Notes on building software.</description>
    <language>en</language>
    <atom:link href="https://example.com/feed.xml" rel="self" type="application/rss+xml"/>

    <item>
      <title>Parsing XML without surprises</title>
      <link>https://example.com/blog/parsing-xml</link>
      <guid isPermaLink="false">urn:example:post:1024</guid>
      <pubDate>Fri, 18 Sep 2026 10:00:00 +0000</pubDate>
      <description>A short summary for feed readers.</description>
    </item>
  </channel>
</rss>
<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
  <title>Example Engineering</title>
  <link href="https://example.com/blog"/>
  <link rel="self" href="https://example.com/atom.xml"/>
  <updated>2026-09-18T10:00:00Z</updated>
  <id>urn:uuid:60a76c80-d399-11d9-b93C-0003939e0af6</id>

  <entry>
    <title>Parsing XML without surprises</title>
    <link href="https://example.com/blog/parsing-xml"/>
    <id>urn:example:post:1024</id>
    <updated>2026-09-18T10:00:00Z</updated>
    <summary>A short summary for feed readers.</summary>
  </entry>
</feed>

The rules that decide whether readers behave

ConcernRSS 2.0AtomRule
IdentifierguididMust be unique and permanent; never reuse for a different post
Date formatRFC 822, for example Fri, 18 Sep 2026 10:00:00 +0000RFC 3339, for example 2026-09-18T10:00:00ZThe two formats are not interchangeable
Feed timestampNot requiredupdated requiredAtom requires it; readers use it to poll
Contentdescription or content:encodedcontent or summaryEscaping matters: HTML in a feed must be escaped or in CDATA
Self linkOptional extensionlink rel="self"Needed for correct fetching and caching
Languagelanguagexml:langOptional, but improves display
PaginationExtensionlink rel="next"Large archives need it
<!-- HTML inside a feed: escape it, or wrap it in CDATA -->
<description>A short summary with &lt;strong&gt;bold&lt;/strong&gt; text.</description>

<description><![CDATA[A short summary with <strong>bold</strong> text.]]></description>

<!-- CDATA cannot contain the sequence that closes it, so splitting is required -->
<description><![CDATA[Use ]]]]><![CDATA[> to close a CDATA section.]]></description>

Prefer escaping to CDATA. Escaped content survives XSLT, concatenation and naive string handling, whereas an embedded CDATA terminator inside a code sample is a classic source of broken feeds.

Publishing and validating

  1. Serve the feed with the correct content type: application/rss+xml or application/atom+xml.
  2. Send a Last-Modified or ETag and honour conditional requests, so aggregators do not refetch everything.
  3. Validate against the schema — the RSS validator or the Atom RELAX NG schema — before publishing.
  4. Keep the item order stable, newest first, and never reorder existing entries.
  5. Set a cache lifetime that matches your publishing cadence.
  6. Test with at least two real readers, because lenient parsing hides mistakes that a strict one exposes.
# validate structure and formatting
xmllint --noout feed.xml
xmllint --format feed.xml | head -30

# check the date format precisely
xmllint --xpath 'string(//item/pubDate)' feed.xml

# confirm the served content type
curl -sI https://example.com/feed.xml | grep -i content-type
⚠️
The single most common feed bug is a guid that changes on every request — for example one derived from a timestamp or a session. Every reader then treats the same article as new, and subscribers see the entire archive again.

FAQ

Is the guid the URL?
It may be, using isPermaLink="true" when the identifier is genuinely a permalink. Use a stable URN instead if the URL may change, and set isPermaLink="false".
Should a feed carry full content or a summary?
Full content is friendlier to readers; a summary drives traffic to the site. Either is valid, but be consistent so readers do not flip between modes.

Attributes vs child elements: modelling decisions SVG, XHTML and XML in the browser

Last refreshed 2026-09-18.