Create dynamic RSS feed in Yii
Posted Apr 20, 2014 · Updated May 3, 2014
Edit controllers/SiteController.php
and add the following lines:
public function actionRss() {
$posts=Post::model()->findAll(array(
'order'=>'create_time DESC',
'condition'=>'status='.Post::STATUS_PUBLISHED,
'limit'=>20,
));
header('Content-Type: application/xml');
$this->renderPartial('rss', array('posts'=>$posts));
}
Create views/site/rss.php
with the following content:
<?php
$markdown = new CMarkdown;
$doc = new DOMDocument('1.0', 'UTF-8');
$rss = $doc->createElement('rss');
$rss->setAttribute('version', '2.0');
$rss->setAttribute('xmlns:atom', 'http://www.w3.org/2005/Atom');
$rss->setAttribute('xmlns:dc', 'http://purl.org/dc/elements/1.1/');
$doc->appendChild($rss);
$channel = $doc->createElement('channel');
$channel->appendChild($doc->createElement('title', CHtml::encode(Yii::app()->name)));
$channel->appendChild($doc->createElement('link', $this->createAbsoluteUrl('/')));
$channel->appendChild($doc->createElement('description', CHtml::encode(Yii::app()->name).'\'s RSS feed.'));
$atomSelfLink = $doc->createElement('atom:link');
$atomSelfLink->setAttribute('href', $this->createAbsoluteUrl('site/rss'));
$atomSelfLink->setAttribute('rel', 'self');
$atomSelfLink->setAttribute('type', 'application/rss+xml');
$channel->appendChild($atomSelfLink);
$channel->appendChild($doc->createElement('copyright', '©'.date('Y').', '.CHtml::encode(Yii::app()->name)));
$channel->appendChild($doc->createElement('pubDate', date(DATE_RSS)));
$channel->appendChild($doc->createElement('lastBuildDate', date(DATE_RSS, $posts[0]->update_time)));
$rssImage = $doc->createElement('image');
$rssImage->appendChild($doc->createElement('title', CHtml::encode(Yii::app()->name)));
$rssImage->appendChild($doc->createElement('url', $this->createAbsoluteUrl('/static/logo.png')));
$rssImage->appendChild($doc->createElement('link', $this->createAbsoluteUrl('/')));
$rssImage->appendChild($doc->createElement('description', CHtml::encode(Yii::app()->name).'\'s website.'));
$channel->appendChild($rssImage);
$rss->appendChild($channel);
foreach($posts as $post) {
$item = $doc->createElement('item');
$item->appendChild($doc->createElement('title', $post->title));
$item->appendChild($doc->createElement('link', $this->createAbsoluteUrl('post/view', array('id'=>$post->id, 'title'=>$post->title))));
$description = $doc->createElement('description');
$description->appendChild($doc->createCDATASection($markdown->transform($post->content)));
$item->appendChild($description);
$item->appendChild($doc->createElement('dc:creator', ucfirst($post->author->username)));
$item->appendChild($doc->createElement('category', CHtml::encode($post->tags)));
$guid = $doc->createElement('guid', $post->id);
$guid->setAttribute('isPermaLink', 'false');
$item->appendChild($guid);
$item->appendChild($doc->createElement('pubDate', date(DATE_RSS, $post->create_time)));
$channel->appendChild($item);
}
echo $doc->saveXML();
To make it easy for people to subscribe to your new RSS feed you can add this to the head section of views/layouts/main.php
of your theme:
<?php Yii::app()->clientScript->registerLinkTag('alternate', 'application/rss+xml', $this->createAbsoluteUrl('site/rss')); ?>
Leave a Comment