Creating an Atom Feed in Radiant
Updated: I’ve updated the code to use Radiant 0.6’s <r:date for="updated_at"/>
to get the last updated dates right for the feed and its articles.
Out of the box, Radiant and its sample blog templates include an RSS feed. Having recently taken an interest in Atom I thought I’d try building an Atom feed. Here’s how I did it.
Atom Requirements
Creating the Atom feed itself is fairly straightforward, but there are a few things to be aware of.
Atom feeds use the application/atom+xml
Content-Type so the first step is to create an appropriate Layout. [Note: To edit the layout’s Content-Type click the More link that appears under the Name field.]
The feed and its entries each require an id
element. There are many possible schemes for ids but I’ve chosen URLs to keep things simple. Also, the feed has an updated
element to indicate when the feed was last updated. Finally, all timestamps in the feed must conform to RFC 3339.
Building the Feed
The beginning of the feed is quite simple. The root is a feed
element in the Atom namespace. There’s a title
element and separate link
elements for links to the feed itself and to the page associated with the feed (in this case, my home page). The generator
element indicates that the feed was created using Radiant.
<?xml version="1.0" encoding="UTF-8"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en-us">
<title type="text">Sean Santry</title>
<link rel="self" href="http://seansantry.com<r:url />" />
<link rel="alternate" type="text/html" href="http://seansantry.com/" />
<id>http://seansantry.com/</id>
<generator uri="http://radiantcms.org/"
version="0.5.2">Radiant CMS</generator>
Next is the author
element with my name
and the uri
for my site. An email
element is optional (for feeding spammers).
<author>
<name>Sean Santry</name>
<uri>http://seansantry.com/</uri>
</author>
I mentioned that the feed has an updated
element with a timestamp that indicates when the feed was last updated. Since this timestamp depends on when an entry was most recently added or modified Radiant’s r:date
tag won’t work. That would give the date when the Atom feed itself was last edited, which isn’t correct.
The solution is to find the most recent article using a combination of Radiant tags. The r:find
tag gets all the articles in my blog and the r:children:each
tag sorts by the published_at
date in descending order. Setting the limit
attribute to 1
gets back just the most recently updated page. Finally the r:date
tag with the RFC 3339 date format (%Y-%m-%dT%H:%M:%SZ
) populates the feed’s updated
element.
<updated><r:find url="/articles/">
<r:children:each limit="1" order="desc">
<r:date format="%Y-%m-%dT%H:%M:%SZ" for="updated_at" />
</r:children:each>
</r:find></updated>
Adding the entries themselves is simple. Once again the r:find
and r:children:each
tags get the appropriate pages. Within the entry
element are the entry’s author
, the dates on which the entry was last published and updated and the entry’s title
. The entry’s URL serves as the entry’s id
and as the entry’s permalink (in the link
element).
I like providing the full content for entries in my feeds, so the content
element has the full output from the r:content
tag. If your entries have summaries stored in a page part, you could use that instead.
<r:find url="/articles/">
<r:children:each limit="10" order="desc">
<entry>
<author><name><r:author /></name></author>
<published><r:date format="%Y-%m-%dT%H:%M:%SZ" /></published>
<updated><r:date format="%Y-%m-%dT%H:%M:%SZ" for="updated_at" /></updated>
<title><r:title /></title>
<link rel="alternate" type="text/html"
href="http://seansantry.com<r:url />" />
<id>http://seansantry.com<r:url /></id>
<content type="html"><r:escape_html>
<r:content /></r:escape_html></content>
</entry>
</r:children:each>
</r:find>
</feed>
You can see the results of this feed at http://seansantry.com/atom/. Download the source to get started. Once you've created your feed you can check it for validity using the feed validator.