Table of Contents
Version: 3.0.1
Requires: PHP 5.2
Tested On: PHP 5.3
Commit Hash: 5c795d1f4f
Released: Apr 22nd, 15:19
Requires: PHP 5.2
Tested On: PHP 5.3
Commit Hash: 5c795d1f4f
Released: Apr 22nd, 15:19
Feeds
Version: 3.0.1 (logs)
Package: Plugin: RSS and XML Datasource Reader
Category: CakePHP
Views: 5,012
Permalink -
Tinylink
A CakePHP Component that will take a list of feeds and aggregate them into a single array based on their timestamp.
Class Features:
Class Features:
- Supports RSS 2.0, RSS 1.0 (RDF) and Atom feed types
- Can support as many feeds as you wish
- Separates feeds into groups so you can add accordingly and not conflict
- Uses the HttpSocket and XML libraries to parse the feeds
- Built in cache support (with a little configuration)
- Has a max return limit to cut down the returned arrays size
Top
1 - Installation
Place the plugin into a folder called Feeds/ within your application plugins directory and add the datasource to config/database.php.
Once your datasource has been defined, you can now use it within your models. To do so, set the $useDbConfig property in your model to "feeds" and $useTable to false. When you do this, the models find() method will interact with the datasource to parse XML and RSS feeds.
Caching Results
This configuration should be automatically called when the datasource is used, but you can overwrite it. You would call this like any other Cache::config(), just make sure that they key is "feeds".
public $feeds = array('datasource' => 'Feeds.FeedSource');
Once your datasource has been defined, you can now use it within your models. To do so, set the $useDbConfig property in your model to "feeds" and $useTable to false. When you do this, the models find() method will interact with the datasource to parse XML and RSS feeds.
class Example extends Model { public $useTable = false; public $useDbConfig = 'feeds'; }
Caching Results
This configuration should be automatically called when the datasource is used, but you can overwrite it. You would call this like any other Cache::config(), just make sure that they key is "feeds".
Cache::config('feeds', array( 'engine' => 'File', 'serialize' => true, 'prefix' => '' ));
Top
2 - Configuration
You can pass an array of options as the 2nd argument of your models find(); exactly like regular model usage. The array accepts the following parameters:
When defining the order, the order value will be an array of element to sort direction (similar to Cake's default implementation). The element name must be one of the following: title, guid, date, link, image, author, description. The sort direction should be either ASC or DESC.
Here's a more robust example:
- fields - A mapping of element names to extract data from (more in chapter 4)
- order - The order in which to sort the response (default date ASC)
- limit - How many results to return (default 20)
- feed.root - Custom name for the XML documents root (more in chapter 5)
- feed.cache - True/false to cache the response
- feed.expires - A strtotime() format for the cache duration
When defining the order, the order value will be an array of element to sort direction (similar to Cake's default implementation). The element name must be one of the following: title, guid, date, link, image, author, description. The sort direction should be either ASC or DESC.
'order' => array('title' => 'ASC')
Here's a more robust example:
$this->find('all', array( 'conditions' => $urls, 'order' => array('title' => 'ASC'), 'limit' => 5, 'feed' => array( 'root' => 'articles', 'cache' => true, 'expires' => '+5 minutes' ) ));
Top
3 - Fetching Feeds
You may use the models find() method to fetch your data. You can pass an array of URLs to parse as the conditions. Additionally, the plugin comes packaged with a model called Aggregator that you may use for this task.
Then fetch the feeds by passing the conditions.
If you do not wish to use the Aggregator, you could create your own model with its own method.
public $uses = array('Feeds.Aggregator');
Then fetch the feeds by passing the conditions.
$this->Aggregator->find('all', array( 'conditions' => array( 'Starcraft 2 Armory' => 'http://feeds.feedburner.com/starcraft', 'Miles Johnson' => 'http://feeds.feedburner.com/milesj' ) ));
If you do not wish to use the Aggregator, you could create your own model with its own method.
public function getStarcraftFeeds() { return $this->find('all', array( 'conditions' => array( 'Starcraft 2 Armory' => 'http://feeds.feedburner.com/starcraft' ) )); }
Top
4 - Extracting Data
By default, the datasource will grab the following elements: title, guid, link, date, image, author, description. The datasource will use a mapping of keys to determine which element to grab the data from, for example.
The array above will search within the keys author, writer, editor and user to determine where to get the authors name. Once a value is found, it will exit early on.
If you need to grab additional data, you can use the fields option within find(). The following code was used on Twitter's API.
$elements = array( 'title', 'guid' => array('guid', 'id'), 'date' => array('date', 'pubDate', 'published', 'updated'), 'link' => array('link', 'origLink'), 'image' => array('image', 'thumbnail'), 'author' => array('author', 'writer', 'editor', 'user'), 'description' => array('description', 'desc', 'summary', 'content', 'text') );
The array above will search within the keys author, writer, editor and user to determine where to get the authors name. Once a value is found, it will exit early on.
If you need to grab additional data, you can use the fields option within find(). The following code was used on Twitter's API.
$this->find('all', array( 'fields' => array( 'link' => array('id_str'), 'description' => array('text'), 'date' => array('created_at'), // Checks user.screen_name for the author value 'author' => array( 'keys' => array('user'), 'attributes' => array('screen_name') ), // Checks user.profile_image_url for the image value 'image' => array( 'keys' => array('user'), 'attributes' => array('profile_image_url') ) ) ));
Top
Read the whole documentation? Download the script now and try it yourself! Return to the Top
5 - Custom Document Root
By default, the class will logically grab the list of items from an RSS, RDF and Atom feed. If you are parsing custom XML, or JSON (yes it works), you can define your own root element to grab the items from.
$this->find('all', array( 'feed' => array( 'root' => 'items', // Cache this feed for 1 hour 'cache' => 'cacheKey', 'expires' => '+1 hour' ) ));