使用Zend_Feed+Cron打造Feed Reader

相信对于很多人来说,通过Bloglines,Google Reader这些阅读器订阅和浏览Blog已经是网络生活的一部份。如果你打算自己打造一个好用的Feed Reader,不妨试试Zend_Feed这个好用的类库。

首先大概的原理是读取Blog的RSS或Atom Feed,得到XML文件,解析该文件得到数据。为了加快浏览速度,我们通常需要把得到数据保存到本地数据库中。

以上目的分解成技术步骤有以下三步:
1。读取RSS。 你可以使用现成的函数或者专业的RSS类库(这种类库一般还提供更多丰富的功能),也可以自己模拟HTTP来抓取;

在PHP中,使用简单的比如 file_get_contents()函数就可以方便而且高效地抓取文件,但有时候可能RSS文件是不能直接获取的,比如获取你的Bloglines帐号中订阅的RSS,那么可能你还需要提交一些参数或者通过HTTP认证之类,这时可用模拟HTTP的方法,比如下面代码使用了PEAR::Http_Request:

function getRSS ( $username , $password , $s , $n = 0 ){

$url = "http://rpc.bloglines.com/getitems?s=" . $s . "&n=" . $n ;

$req =&new HTTP_Request ( $url );
$req -> setBasicAuth ( $username , $password );
$req -> sendRequest ();

$blogContent = $req -> getResponseBody ();
return
$blogContent ;

}

填入你的Bloglines帐号和密码,利用这个函数你就可以得到RSS文件。

2。解析XML RSS文件遵循一定规范,你可以自己写个函数来解析,没什么难度,但有点繁琐。
3。将解析得到的数据入库。

好了,大概知道了要做的工作,你会发现虽然都不难,但是自己一个个实现比较麻烦,呵呵。这就是本文要介绍Zend_Feed的原因。

Zend_Feed是Zend Framework中的一个类库,我们完全可以把它单独拿出来使用。Zend_Feed高度封装,使用非常方便,例如读取一个RSS Feed:


$channel=newZend_Feed_Rss('http://rss.example.com/channelName');
echo
$channel->title();

//遍历记录
foreach($channelas$item){
echo
$item->title()."\n";
}

是不是非常简单? 读取和解析总共5行代码。

好,下面我们开始完成一个真正的Feed Reader:

FeedReader.php

<?php
set_time_limit
(0);
define('ZEND_DIR','/www/lib');
set_include_path(get_include_path().PATH_SEPARATOR.ZEND_DIR);
require_once(
'Zend.php');
Zend::loadClass('Zend_Feed');
Zend::loadClass('Zend_Filter_Input');

$link=mysql_connect('localhost','user','pwd')
ordie(
'Couldnotconnect:'.mysql_error());
//echo'Connectedsuccessfully';
mysql_select_db('phpeye')ordie('Couldnotselectdatabase');


$feedChannel=array(
'http://www.phpdeveloper.org/phpdev.rdf',
'http://www.planet-php.net/rss/'
);

foreach(
$feedChannelas$channel){
readRssFeed($channel);
}

echo
"Done!";

function
readRssFeed($feedAddress){

try{
$rss=Zend_Feed::import($feedAddress);
}catch(
Zend_Feed_Exception$e){
//Feed导入失败
//echo"Exceptioncaughtimportingfeed:{$e->getMessage()}\n";
$msg="Exceptioncaughtimportingfeed:{$e->getMessage()}\n";
$dateTime=date("Y-m-dH:i:s",time());
$errMsg=$msg.''.$dateTime."\n\n";

echo
$errMsg;
file_put_contents('FeedReader.log',$errMsg,FILE_APPEND);
exit;
}

//初始化保存channel数据的数组,$rss内部数据只能通过调用类方法才能访问
$channel=array(
'title'=>$rss->title(),
'link'=>$rss->link(),
'description'=>$rss->description(),
'items'=>array()
);

$count=0;
//循环获得channel的item并存储到相关数组中
foreach($rssas$item){


$channel['items'][]=array(
'title'=>$item->title(),
'link'=>$item->link(),
'description'=>$item->description()
);


//标题和内容都需要转义
$title=strip_tags(mysql_real_escape_string($item->title()));
$link=strip_tags($item->link());
$description=mysql_real_escape_string($item->description());

//先查询数据库看记录是否已经存在,存在则不操作,否则向数据库添加新记录
$query="select*fromfeedentrywhereentitle='$title'";
//echo"<HR>SQL:".$query."<P>\n\r";
$result=mysql_query($query)ordie('Queryfailed:'.mysql_error());
$num_rows=mysql_num_rows($result);

if(
$num_rows>0){
//echo"Therecordalreadyexists!";
//donothing...
}else{
$query="insertintofeedentry(entitle,link,endescription,addtime)values('$title','$link','$description',NOW())";
//echo"<HR>SQL:".$query."<P>\n\r";

$result=mysql_query($query)ordie('Queryfailed:'.mysql_error());

$count++;
}

}

//zend::dump($channel);
$dateTime=date("Y-m-dH:i:s",time());

if(
$count>0){
$Msg=$count."entrysreadsuccessfully!".$dateTime."\n\n";
echo
$Msg;
file_put_contents('FeedReader.log',$Msg,FILE_APPEND);
}else{
$Msg='readnothing...'.$dateTime."\n\n";
echo
$Msg;
file_put_contents('FeedReader.log',$Msg,FILE_APPEND);
}

}

?>

文件中除了RSS读取,解析和入库外,还有DEBUG和日志功能。

数据表结构如下:

CREATE TABLE `feedentry` (
`id` int(11) NOT NULL auto_increment,
`entitle` varchar(200) NOT NULL default '',
`link` varchar(200) NOT NULL default '',
`endescription` mediumtext NOT NULL,
`category` varchar(50) NOT NULL default '',
`comments` text NOT NULL,
`publishtime` datetime NOT NULL default '0000-00-00 00:00:00',
`addtime` datetime NOT NULL default '0000-00-00 00:00:00',
PRIMARY KEY (`id`)
) TYPE=MyISAM ;


呵呵
,把这个文件保存。然后利用Linux的Cron脚本让它定时在命令行下运行,下面让它每小时的40分运行一次:
crontab -e
40 * * * * /usr/local/bin/php -q /www/phpeye/FeedReader.php

一个好用的Feed Reader就打造完成了。如果你想添加RSS频道,可以自己在$feedChannel这个数组中添加元素,非常方便,当然如果你有兴趣,可以写一个WEB界面来管理,那样就更方便了。

改进:

这个Reader已经具备了核心功能,但是没有完成频道管理功能,你可以再建一个feedchannel数据表,并且在feedentry表中增加一个channelID字段,这样就可以随意增添管理Feed频道了。

效果请看:http://www.phpeye.com

本文介绍的程序属于PHPEye Blog中英翻译平台的一部份,该平台尚在开发当中。

<END>






评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值