考虑更换学习日记的名称和域名

  毕竟,学习只是一种手段,不是目的。使用学习作为网站的名称和域名,给人一种一直学习的迂腐形象。

  但是,对于如何继承学习日记已经取得的一些在搜索引擎中的排名(如:google pr(http://www.learndiary.com/disDiaryContentAction.do?searchDiaryID=1537&goalID=1537&naviStr=a10a25),学习日记关键词(http://www.learndiary.com/disDiaryContentAction.do?searchDiaryID=1706&goalID=1706&naviStr=a10a25)和有利因素,这还需要认真考虑。

PR更新总结;如何提高网站的PR值(转帖2篇)

PR更新总结(转自:http://www.blogcn.com/user45/search100/blog/22065579.html)

从佛罗里达更新到现在也有四个月左右了。据我以我网站的观察,PR更新了两次,而这两次的PR更新规则也与hilltop算法的原则非常吻合。大家可以由于联想到什么或者会得到相应的结论了吧。下面是我对这次PR更新的一些观察,希望能对大家有一点启示。

(1)PR更新前收集数据的时间:

  对于这个时间的把握不可能很准确,只是一个大概的推测,不过还是有现实根据的。从对我个人及公司的几个网站的观察,我得到了这次显示PR更新前收集数据的截止时间,大概是在二月份中旬左右.根据(你们也可以以此来对你的网站进行推测一下):在我的多个网站中,还有多个二级页面PR为0。而这些PR为0的页面绝大多数都是在二月中旬后才上传或者建立的;这对证明PR更新前收集数据的截止时间有一定的帮助。既然,PR更新前收集数据的截止时间已经大概知道。那么,我们可以推测下次PR更新前收集数据的截止时间应该是在二月份中旬后,PR刷新时间可以是在五月份中旬(因为googleguys曾经暗示过新算法的调整后,PR的更新大概会是一个季度一次)。

(2)影响PR值的因素(当然只是其中的一部分):

  A:外入链接数及外入链接的质量(链入网站的PR及链出数等),这可是众所周知的了。

  B:包含链接数、收录一个网站的页面数(个人认为是关键的因素)

(3)PR更新给我们带来的思考:

  由于PR值主要是同链入数与收录页面数及包含数决定,那么我们就要针对这两个因素对网站进行相应的调整。

  A:在进行链接的时候我们要非常谨慎,绝不能在低质量的自助链接中(或大多数人称为链接农场)放链接,这不但对于提高PR没帮助,还很有可能你会因此而受到惩罚。

  B:在面对自助链接时,你首先应该看一下该网站的质量,次之就是这些外出链接的质量是数量,是否存在着一个域名有多个外重复链接。如果是的话,那就证明这种自助链接是没有经过任何申核的,极其危险!有很多自助链接类似于目录,这种才是首选,因为站主会对提交的网站经过申核,这对你是一个保证。

  C:交换链接一些策略:

  1、看被链接网站是否已经被各大搜索引擎收录及其被搜索引擎的更新频率如何(在搜索结果中可以看到最后一次被除数更新的时间,如果超过三天没有更新,就不会显示);如果链入的网站被各大搜索引擎收录而且还经常更新的话,那么你的网站也会占了不少的光。因为搜索引擎也会对链接的站点进行相应的更新,那么你就不需要交钱去给搜索引擎公司来帮你更新了(如“百度”)

  2、是否被大的分类目录收录(如:dmoz,yahoo等);这样的网站PR低只是暂时的事情,过了一个月会更长的一点时间,人家的PR就会飞起来,到时你再跟人家交换,人家未必答应了,所有要有长远的眼光来对待当前的事物)

  3、是否被收录了网站内大多数的页面;如果一个网站质量好、结构合理,那么就是说这样的网站很受搜索引擎青睐。网页收录数目与PR值是成正比的。当然,有的网站被除数收录了2000多个页面,而有的只收录了80多个。后者就一定很差劲。我们看收录多少是只比例而不是数目。如果前者有几十万页才收录了2000多页,这也不算是一个非常好的网站,而后者只有100个就收录了80多个。显然后者的质量要比前者高得多了。这样的网站也不失为一个理想的交换对象。

  4、是否与很多同类网站交换了链接或者与很多网站交换了链接(不包含自助链接);这也是PR上升的一个潜在的因素,所以在交换时可以查一下对方的链接数目有多少。特别是质量高的链接多不多。

  5、网站质量如何;这关系到网站是否能长期存在的问题,如果网站质量很差,但是PR很高。这样的网站也不是理想的交换对象。网站质量差的网站的PR终有一天会降下来的,这就为你网站PR的不稳定添加了一个很大的因素。

  6、网站排名如何(指热门的关键字);这样的网站不但会对你的网站带来一定的流量,而且也是一个很好的合作伙伴。因为只有质量较高的网站才能长期地放在前几位(一般一个月就已经算是好的网站了)。

  7、是否是同类的网站;因为排名算法中,同类的网站对你网站排名投票的分值会越高。从而使到你的网站有可能得到较好的排名。

  8、试图向大的分类目录提交,这样的做法不但得到高质量的反向链接,而且还不用付出任何的代价。

  D:链接网站相关度显得特别重要,一般的话在交换链接时要考虑不但是对方网站的质量,还有就是相关度。如果不是相关的网站,对你网站排名及PR影响都不会很大。所以,建议在交换链接时要选择相关性较高的作为首页链接的首先,而不是相关网站就算PR再高也只能作次级页面的链接。

  E:外出链接数的把握:

  一般一个页面保持在12个以下。这主要是对你的链接伙伴的一个承诺。高质量的网站不会对那些在一个页面就有几十个外出链接的网站感兴趣的,也为你的网站能否与高PR网站链接提供了一个前提。

  F:优化网站的内部结构:

  使搜索引擎能收录你网站更多的页面。如:理清网站结构,分类清楚,一目了然;建立导航条,直接与各子类别相链接;建立完整的网站地图,在你增加页面时,别忘记了更新网站地图页;重要的页面要在网站内的多个页面都作一个对它的链接,这也是为什么首页的PR一般较其它页面高的一个因素。(我会在下一篇文章中对此进行详细的论述)

  另外还是一个疑问就是模板页面的问题,对一个业内网站的观察。它的首页为5但绝大多数的次级页面或其他页面都是为0。这希望大家能跟我讨论一下,探个究竟。email: wuzexin2000@yahoo.com.cn

  总结:在应对这个影响网站排名的主要因素--链接,我们要谨慎对待,不能掉以轻心。重要的是对两个主要方面的把握,即外也链接与内部链接。

search100 发表于 >2005-6-24 15:11:17 [评论] [引用] [推荐] [档案] [推给好友] [主页] [问题日志]

本站用户发表的作品,BLOGCN有权在站内免费转载或引用。未经同意,其他站点不得以任何形式侵犯本站著作权,包括但不限于:擅自复制、链接、非法使用或转载,及任何方式建立镜像站点。

 

×××××××××××××××××××××××××××××××××××××××××××××××××××

SEO:如何提高网站的PR值(转自:http://soft.yesky.com/tools/348/2060848.shtml)

 无论是对普通网络冲浪者还是网站管理员来说,Google都是目前世界范围内最受欢迎的搜索引擎。它每天处理的搜索请求高达1.5亿次,几乎占全球所有搜索量的1/3。网络冲浪者对Google情有独钟,是由于Google所提供的快速搜索速度及高命中率搜索结果。这些都是基于Google的复杂文本匹配运算法则及其搜索程序所使用的Pagerank为系统(网页级别技术)。下面我们将向大家介绍Google的Pagerank为系统。

  Google之所以受网站管理员和Internet媒体服务公司的欢迎,是由于它并非只使用关键词或代理搜索技术,而是将自身建立在高级的网页级别技术基础之上。别的搜索引擎提供给搜索者的是多种渠道得来的一个粗略的搜索结果,而Google提供给它的搜索者的则是它自己产生的高度精确的搜索结果。这就是为什么网站管理员会千方百计去提高自己网站在Google的排名。

  Google大受青睐的另一个原因就是它的网站索引速度。向Google提交你的网站直到Google收录,一般只需两个星期。如果你的网站已经被Google收录,那么通常Google会每月一次遍历和更新(重新索引)你的网站信息。不过对于那些PR值(Pagerank)较高的网站,Google索引周期会相应的短一些。

  Google的索引/重新索引周期比大多数搜索引擎要短。这就允许网站管理员可以对网站的页面属性进行编辑修改,如网页标题、头几行文字内容、大字标题、关键词分布,当然了还有外部链接的数量。然后他们很快就可以发现对网页所做的这些更改是否成功。

  正因为Google如此受欢迎,你有必要知道Google的搜索引擎是如何工作的。如果不知道它是怎样决定你的排名,那些只是稍微熟悉Google排名运算法则的站点都会比你的排名位置要靠前。现在让我们来看一下Google的排名运算法则。

  Google的排名运算法则主要使用了两个部分,第一个部分是它的文字内容匹配系统。Google使用该系统来发现与搜索者键入的搜索词相关的网页;第二部分也是排名运算法则中最最重要的部分,就是Google的专利网页级别技术(Pagerank")。

  我先来介绍一下如何使网站具有相关性,即文本内容匹配部分的运算法则:

  在搜索网站的关键词时,Google会对其标题标签(meta title)中出现的关键词给予较高的权值。所以你应当确保在你网站的标题标签中包含了最重要的关键词,即应围绕你最重要的关键词来决定网页标题的内容。不过网页的标题不可过长,一般最好在35到40个字符之间。

  众所周知,Google并不使用元标签(Meta Tags)如关键词或描述标签。这是由于在这些元标签中所使用的文字并不能为实际的访问者所看到。而且Google认为,这些元标签会被某些网站管理员用于欺诈性地放置一些与其网站毫不相干的热门关键词,并以此提高其网站对该不相干关键词的排名,从而以不正当的手段获得更多的访问者。

  这种不支持Meta Tags的特性,意味着Google将从一个网页的头几行文字内容来生成对一个网站的描述。也就是说,你最好把你的关键词或关键短语放到网页的上方,这样如果Google找到它们,就会相应提高你网站的相关性。一旦Google找不到这样相关的内容,那么你要花费很大的力气来让你页面的其它部分具有相关性。

  在决定一个网站的相关性时,Google也会考虑网页中正文内容的关键词密度(Keyword Density),所以你要确保在你的整个网页中贯穿出现了若干次关键词和关键短语。但是要记住"过犹不及",6-10%的关键词密度为最佳。

  增加页面相关性的其它策略还包括:在标题内容中放入关键词,并尽可能对内容中出现的关键词进行加粗。Google现在也索引图片的ALT属性文字并计入相关性计算。所以在你的ALT属性中应包含关键词,来增加网站的相关性得分。

  增加页面相关性的最后一个技巧就是使你网站上的外部文字链接包含你的关键词。在外部文字链接中包含关键词可有效提高你的网站相关性得分(Google在其PageRank技术的描述中,亦提及在计算网页级别时会对该网站的外部链接进行分析并计入相关性)。

  在文字链接中应该包含多少关键词?这是个见仁见智的问题。不过我注意到有很多网站在他们的交换链接区域,已经提供了相应的文字链接内容。例如:"欢迎进行友情链接,并请使用如下代码建立至本网站的链接。"

  上面我们介绍了Google如何计算网站的相关性,及如何增加网站相关性的一些有关知识。不过Google究竟使用什么方法来衡量一个网站的好坏呢?答案就是-Google的Pagerank为系统。

  PageRank取自Google的创始人Larry Page,它是Google排名运算法则(排名公式)的一部分,用来标识网页的等级/重要性。级别从1到10级,10级为满分。PR值越高说明该网页越受欢迎(越重要)。例如:一个PR值为1的网站表明这个网站不太具有流行度,而PR值为7到10则表明这个网站非常受欢迎(或者说极其重要)。

  在计算网站排名时,PageRank会将网站的外部链接数考虑进去。我们可以这样说:一个网站的外部链接数越多其PR值就越高;外部链接站点的级别越高(假如Macromedia的网站链到你的网站上),网站的PR值就越高。例如:如果ABC.COM网站上有一个XYZ.COM网站的链接,那为ABC.COM网站必须提供一些较好的网站内容,从而Google会把来自XYZ.COM的链接作为它对ABC.COM网站投的一票。你可以下载和安装Google的工具条来检查你的网站级别(PR值)。

  那么是不是说,一个网站的外部链接数越高(获得的投票越多), 这个网站就越重要,因而在用与其相关的关键词进行搜索时,它就会取得更高的排名呢?--大错特错。

  Google对一个网站上的外部链接数的重视程度并不意味着你因此可以不求策略地与任何网站建立连接。这是因为Google并不是简单地由计算网站的外部链接数来决定其等级。要是那样的话,所有网站管理员就只剩一件事情可做了-疯狂交换链接,尽可能获得最多的外部链接。Google是这样描述的:"Google不只是看一个网站的投票数量,或者这个网站的外部链接数量。同时,它也会对那些投票的网站进行分析。如果这些网站的PR值比较高(具有相当重要性),则其投票的网站可从中受益(亦具有重要性)。

  那么,是不是说对一个网站而言,它所拥有的较高网站质量和较高PR分值的外部链接数量越多就越好呢?-也不尽然。

  说它错是因为-Google的Pagerank系统不单考虑一个网站的外部链接质量,也会考虑其数量.比方说,对一个有一定PR值的网站X来说,如果你的网站Y是它的唯一一个外部链接,那么Google就相信网站X将你的网站Y视做它最好的一个外部链接,从而会给你的网站Y更多的分值。可是,如果网站X上已经有49个外部链接,那么Google就相信网站X只是将你的网站视做它第50个好的网站。因而你的外部链接站点上的外部链接数越多,你所能够得到的PR分值反而会越低,它们呈反比关系。

  说它对是因为一般情况下,一个PR分值大于等于6的外部链接站点,可显著提升你的PR分值。但如果这个外部链接站点已经有100个其它的外部链接时,那你能够得到的PR分值就几乎为零了。同样,如果一个外部链接站点的PR值仅为2,但你却是它的唯一一个外部链接,那么你所获得的PR值要远远大于那个PR值为6,外部链接数为100的网站。

  这个问题现在看来好象越来越复杂了。不要紧,看看下面这个公式你就会完全理解了,只是需要一点数学知识。

  首先让我们来解释一下什么是阻尼因子(damping factor)。阻尼因素就是当你投票或链接到另外一个站点时所获得的实际PR分值。阻尼因子一般是0.85。当然比起你网站的实际PR值,它就显得微不足道了。现在让我们来看看这个PR分值的计算公式:

  PR(A) = (1-d) + d(PR(t1)/C(t1) + ... + PR(tn)/C(tn))

  其中PR(A)表示的是从一个外部链接站点t1上,依据Pagerank为系统给你的网站所增加的PR分值;PR(t1)表示该外部链接网站本身的PR分值;C(t1)则表示该外部链接站点所拥有的外部链接数量。大家要谨记:一个网站的投票权值只有该网站PR分值的0.85,而且这个0.85的权值平均分配给其链接的每个外部网站。

  设想一个名为akamarketing.com的网站,被链接至PR值为4,外部链接数为9的网站XYZ.COM,则计算公式如下:

  PR(AKA) = (1-0.85) + 0.85*(4/10)

  PR(AKA) = 0.15 + 0.85*(0.4)

  PR(AKA) = 0.15 + 0.34

  PR(AKA) = 0.49

  也就是说,如果我的网站获得一个PR值为4,外部链接数为9的网站的链接,最后我的网站将获得0.49的PR分值。

  再让我们看看如果我的网站获得的是一个PR分值为8,外部链接数为16的网站的链接,那么我将获得的PR分值将是:

  PR(AKA) = (1-0.85) + 0.85*(8/16)

  PR(AKA) = 0.15 + 0.85(0.5)

  PR(AKA) = 0.15 + 0.425

  PR(AKA) = 0.575

  上述两个例子表明,外部链接站点的PR值固然重要,该站点的外部链接数也是一个需要考虑的重要因素。

  好了,大家无须记住上面的公式,只要记住:在建设你自己网站的外部链接时,应尽可能找那些PR值高且外部链接数又少的网站。这样一来你网站上这样的外部链接站点越多,你的PR值就会越高,从而使得你的排名得到显著提升。

  不过,为使你的PR值得到提高,你最应该做的一件事情就是-向DMOZ提交你的网站,即ODP(开放目录项目)收录。

  众所周知,Google的Pagerank系统对那些门户网络目录如DMOZ,Yahoo和Looksmart尤为器重。特别是对DMOZ。一个网站上的DMOZ链接对Google的Pagerank来说,就好象一块金子一样有价值。这时候收录该网站的那个DMOZ目录页的PR分值,也变得无足轻重了。我就看到过有一些站点,就因为被ODP所收录,从而身价倍增,其PR分值在Google上立即得到提升。这就是因为Google使用了它自己的ODP版本作为它的网站目录。

  ODP的链接对Pagerank非常重要。如果你的网站被ODP收录,则可有效提升你的页面等级。不信吗?

  确实如此。在Google上随便找个词搜索,你会发现,Google所提供的搜索结果的头10个站点中,就有7到8个也同时在Google的目录中出现。这个事实足以说明,如果一个网站没有被ODP收录的话,那它也别指望能从Google上得到太多的访问量。

  向ODP提交你的站点并被它收录,其实并不是一件难事,只是要多花点时间而已。只要确保你的网站提供了良好的内容,然后在ODP合适的目录下点击"增加站点",按照提示一步步来就OK了。至少要保证你的索引页(INDEX PAGE)被收录进去。我说"至少"是因为尽管ODP声称他们只收录你的索引页,而事实上在ODP上却不乏被收录了5到10页的网站。所以,如果你的网站内容涉及完全不同的几块内容,你可以把每个内容的网页分别向ODP提交-不过请记住"欲速则不达"。等到Google对其目录更新后,你就能看到你的PR值会有什么变化了。

  如果你的网站被Yahoo和Looksmart所收录,那么你的PR值会得到显著提升。关于"Yahoo提交技巧",如果有时间可以阅读下面这篇文章"Yahoo网站提交技巧"。

  如果你的网站是非商业性质的或几乎完全是非商业性质的内容,那么你可以通过www.Zeal.com使你的网站被著名的网络目录Looksmart所收录。我个人非常喜爱ZEAL.COM,就象Google也从DMOZ获得搜索结果一样,Looksmart也是从Zeal网络目录获得非商业搜索列表。

  让我们继续-我是在一个星期二向Zeal提交的AKA Marketing.com,到了星期四早上它就出现在Zeal上了。到了星期一我检查了一下我的日志文件,发现来自Looksmart的大量提名,原来它已经被Looksmart收录了。后来我又查看了一下我的日志,发现MSN已经根据Looksmart的数据库而更新了它自己的数据库,而且由此而提升的好的排名也给我带来了不少的访问者。想想看吧,6天之内我的网站就出现在Zeal,Looksmart和MSN上了。所以如果你有非商业网站,可千万别忘了去Zeal.com提交你的网站哦!

  在向Zeal.com提交你的网站前,你得先通过它的一个会员小测试。别担心,这个测试是很简单的。如果你是一个网站管理员,而你的网站又已经收录在三大知名网络目录DMOZ,Yahoo和Looksmart中,我猜想你的网站的PR值一定比较高,而且搜索排名也不会差。

  综述:

  1. 在网站的标题标签(TITLE tag)中包含主要关键词和关键短语。

  2. 提高网站外部链接的质量和数量。

  3. 使网站被三大知名网络目录DMOZ,Yahoo和Looksmart收录。

 

百度的广告品位有待提高啊

  百度现在应该说是中文搜索的老大了。但是比起google来,它的广告品位就显得有点低下了。据我的经验,在所看到的百度广告投放中,“增大增粗...”之类的广告占有相当的比例;但在google投放的广告中,这样的广告感觉好像还似乎没有(也许是我没看见)。

完成"issue 12"的学习日记rrs支持

  作了一点完善。rss的全部代码已经提交完毕,并且用在了现在的系统中。

  但是,我发现,至今为止,基本没有什么人用rss来订阅学习日记的的内容。我也不知道为什么?可能最主要的原因是学习日记的内容太少了,太浅了,订阅的价值不大;其次是rss订阅还不为一些朋友了解和习惯使用吧。

为什么学习日记没有实现rss0.91的支持

  在使用rome生成的程序中,我发现了rss0.91的一些限制:例如:language是channel的必需元素,copyRight的长度不能超过100个字符(?),description的长度不能超过?个字符

  我生成的内容不符合这些限制,所以就不支持rss0.91了(包括RSS 0.91 Netscape 和 RSS 0.91 Userland)。

  我只是从程序的出错信息中得知这些限制的,还没有具体去学习这些规范。

学习日记新增RSS订阅功能简介(NEW);什么是RSS?(转帖)

                     学习日记新增RSS订阅功能简介(NEW)

××××××××××××××××××××××××××××××××××××××××××××××××××××××××

(详见:http://www.learndiary.com/dispatchPageAction.do?act=rss)

学习日记网站 RSS 订阅使用说明:

本站RSS订阅使用rome动态生成,除了下面链接中的默认订阅,您可以修改url中参数取得您定制的RSS订阅(包括定制:RSS版本,条目数,用户等),(注意:参数大小写敏感):

参数"type": 为您订阅的类型,即为下面7种和"所有目标 "页面的2种;

参数"feedType": 为订阅的rss类型,包括:RSS 0.90, RSS 0.92, RSS 0.93, RSS 0.94, RSS 1.0, RSS 2.0, Atom 0.3, Atom 1.0 ,参数为: RSS类型 + "_" + RSS版本号, 如:atom_0.3(必须全部小写,RSS 0.91学习日记未实现支持);

参数"entriesNum": 为您RSS订阅的条目数,默认为39条;

参数"userName": 为您的用户名;

参数"channelID": 为您在"所有目标 "页面订阅某个目标下面的条目的目标ID号。

========================================================

  根据我的理解,RSS就是在一个RSS阅读器里订阅所有你感兴趣的、利用了RSS发布的网上的信息,这样,在你打开RSS阅读器或者RSS阅读器在系统中运行固定的时间间隔(例如1个小时)后,RSS阅读器自动连接到这些提供了RSS发布的网站上并自动更新相关的信息。

  这样,你就可以用一个RSS阅读器获得你感兴趣的所有最新信息,而不用登录到它们的一个个的网站上去浏览。

  我现在在用的一款RSS阅读器是新浪网发布的,你也可以一试:http://rss.sina.com.cn。大家如果有其它的好的RSS阅读器也希望在这里跟帖说一下。

  下面是一篇来自网上的转帖,供还没有使用过RSS阅读器朋友参考。

                        什么是RSS?(转帖)

××××××××××××××××××××××××××××××××××××××××××××××××××××××××

(转自:http://wm23.com/resource/R01/Internet_1005.htm)

什么是RSS?RSS及其发展历程

(网络营销教学网站 www.wm23.com 2005-01-03)

  RSS是2004年最热门的互联网词汇之一,不过,相对于博客(BLOG)来说,RSS的知名度相应会低很多,而且至今还没有一个非常贴切的中文词汇,也许以后无需中文名,大家都习惯于直接叫RSS了。RSS之所以同BLOG一样会被认为是热门词汇的一个原因,个人推测,应该是许多分析人士认识到RSS将要对互联网内容的浏览方法所产生的巨大影响。

  什么是RSS呢?RSS(Really Simple Syndication)是一种描述和同步网站内容的格式,是目前使用最广泛的XML应用。RSS搭建了信息迅速传播的一个技术平台,使得每个人都成为潜在的信息提供者。发布一个RSS文件后,这个RSS Feed中包含的信息就能直接被其他站点调用,而且由于这些数据都是标准的XML格式,所以也能在其他的终端和服务中使用。

  如果从RSS阅读者的角度来看,完全不必考虑它到底是什么意思,只要简单地理解为一种方便的信息获取工具就可以了。RSS获取信息的模式与加入邮件列表(如电子杂志和新闻邮件)获取信息有一定的相似之处,也就是可以不必登录各个提供信息的网站而通过客户端浏览方式(称为“RSS阅读器”)或者在线RSS阅读方式这些内容。例如,通过一个RSS阅读器,可以同时浏览新浪新闻,也可以浏览搜狐或者百度的新闻(如果你采用了RSS订阅的话)。

  在许多新闻信息服务类网站,会看到这样的按钮   ,有的网站使用一个图标,有的同时使用两个,这就是典型的提供RSS订阅的标志,这个图标一般链接到订阅RSS信息源的URL。当然,即使不用这样的图标也是可以的,只要提供订阅RSS信息源的URL即可,如网上营销新观察提供的RSS订阅URL是:http://www.marketingman.net/rss.xml

  使用RSS获取信息的前提是,先安装一个RSS阅读器,然后将提供RSS服务的网站加入到RSS阅读器的频道即可。大部分RSS阅读器本身也预设了部分RSS频道,如新浪新闻、百度新闻等。

  RSS基础知识:如何利用RSS阅读器订阅RSS新闻内容?如何免费下载RSS阅读器?(http://www.marketingman.net/wmtheo/zh272.htm)

  常用的RSS阅读器:周博通RSS阅读器(http://www.potu.com/) 看天下网络资讯浏览器(http://www.kantianxia.com/)

  网上营销新观察专题文章:RSS营销研究(http://www.marketingman.net/topics/020_RSS-marketing.htm)

  【RSS实用知识】:关于RSS订阅与RSS阅读的常见问题解答(网上营销新观察 冯英健) (http://www.marketingman.net/wmtheo/zh272.htm)

  为了进一步了解RSS及其发展历程的有关背景知识,下面摘录了2003年10月平文胜为时代营销撰写的有关RSS技术层面的介绍文章。仅供参考。网上此类介绍文章也不少,有兴趣的请到网上检索更多信息。例如维基百科对于RSS的定义、RSS规范、RSS专用阅读器和RSS在线阅读器、中文RSS搜索引擎等等(http://zh.wikipedia.org/wiki/RSS)

  RSS及其发展历程简介 (时代营销 平文胜 2003-10-10)

  RSS是一种描述和同步网站内容的格式,是目前使用最广泛的XML应用。RSS应用在国外已经非常普遍,从个人博客(Blog)栏目、企业站点到世界级的门户都提供基于RSS的服务,如IBM公司站点的中文新闻RSS http://www.ibm.com/news/cn/zh/index.rss ,YAHOO站点的http://news.yahoo.com/rss ,微软MSDN站点的http://msdn.microsoft.com/aboutmsdn/rss.asp 等等。

  1、 RSS的历史

  那么RSS究竟代表什么呢?比较普遍的有两种说法,一种是“Rich Site Summary”或“RDF Site Summary”,另一种是“Really Simple Syndication”,之所以有这些分歧,需要从RSS发展的历史说起。

  最初的0.90版本RSS是由Netscape公司设计的,目的是用来建立一个整合了各主要新闻站点内容的门户,但是0.90版本的RSS规范过于复杂,而一个简化的RSS 0.91版本也随着Netscape公司对该项目的放弃而于2000年暂停。

  不久,一家专门从事博客写作软件开发的公司UserLand接手了RSS 0.91版本的发展,并把它作为其博客写作软件的基础功能之一继续开发,逐步推出了0.92、0.93和0.94版本。随着网络博客的流行,RSS作为一种基本的功能也被越来越多的网站和博客软件支持。

  在UserLand公司接手并不断开发RSS的同时,很多的专业人士认识到需要通过一个第三方、非商业的组织,把RSS发展成为一个通用的规范,并进一步标准化。于是2001年一个联合小组在0.90版本RSS的开发原则下,以W3C新一代的语义网技术RDF(Resource Description Framework)为基础,对RSS进行了重新定义,发布RSS1.0,并将RSS定义为“RDF Site Summary”。但是这项工作没有与UserLand公司进行有效的沟通,UserLand公司也不承认RSS 1.0的有效性,并坚持按照自己的设想进一步开发出RSS的后续版本,到2002年9月发布了最新版本RSS 2.0,UserLand公司将RSS定义为“Really Simple Syndication”。

  目前RSS已经分化为RSS 0.9x/2.0和RSS 1.0两个阵营,由于分歧的存在和RSS 0.9x/2.0的广泛应用现状,RSS 1.0还没有成为标准化组织的真正标准。

  2、 RSS目前的版本和推荐

  到目前为止,RSS共有七种版本,推荐使用的是RSS 1.0和RSS 2.0,对于一些基本的站点同步,也可以选用RSS 0.91。

  3、 RSS的语法介绍

  一个RSS文件就是一段规范的XML数据,该文件一般以rss,xml或者rdf作为后缀。下面我们选择http://msdn.microsoft.com/visualc/rss.xml中的一部分作为例子简单说(略)

  4、 RSS的联合(Syndication)和聚合(Aggregation)

  发布一个RSS文件(一般称为RSS Feed)后,这个RSS Feed中包含的信息就能直接被其他站点调用,而且由于这些数据都是标准的XML格式,所以也能在其他的终端和服务中使用,如PDA、手机、邮件列表等。而且一个网站联盟(比如专门讨论旅游的网站系列)也能通过互相调用彼此的RSS Feed,自动的显示网站联盟中其他站点上的最新信息,这就叫着RSS的联合。这种联合就导致一个站点的内容更新越及时、RSS Feed被调用的越多,该站点的知名度就会越高,从而形成一种良性循环。

  而所谓RSS聚合,就是通过软件工具的方法从网络上搜集各种RSS Feed并在一个界面中提供给读者进行阅读。这些软件可以是在线的WEB工具,如http://my.netscape.com ,http://my.userland.com , http://www.xmltree.com ,http://www.moreover.com ,http://www.oreillynet.com/meerkat 等,也可以是下载到客户端安装的工具

  5、 RSS的未来发展

  随着越来越多的站点对RSS的支持,RSS已经成为目前最成功的XML应用。RSS搭建了信息迅速传播的一个技术平台,使得每个人都成为潜在的信息提供者。相信很快我们就会看到大量基于RSS的专业门户、聚合站点和更精确的搜索引擎。

参考文献:

1、 RSS 0.9 Specification http://www.purplepages.ie/RSS/netscape/rss0.90.html

2、 RSS 1.0 Specification http://web.resource.org/rss/1.0/spec

3、 RSS 2.0 Specification http://blogs.law.harvard.edu/tech/rss

rss支持第一次代码提交

  程序类基本完成,页面还没有做。使用rome可以较好的实现所有rss版本和atom的feed。个人认为还是应用得比较成功的。今天早上已经把全部代码和argoUML0.18.1的粗略设计提交到了cvs库。

  主要类的实现概略:(希望得到你的意见或建议,也供想使用rome的朋友参考。)

  1、

//$ Id: RSSAction.java,v 1.0 2006/02/26 20:49:06 dashing_meng Exp $

//Copyright (c) 2004-2005 Http://www.learndiary.com. All Rights Reserved.

//Permission to use, copy, modify, and distribute this software and its

//documentation without fee, and without a written agreement is hereby

//granted, provided that the above copyright notice and this paragraph

//appear in all copies.  This software program and documentation are

//copyrighted by http://www.learndiary.com. The software program and

//documentation are supplied "AS IS", without any accompanying services

//from The LearnDiary. The LearnDiary does not warrant that the operation

//of the program will be uninterrupted or error-free. The end-user

//understands that the program was developed for research purposes and is

//advised not to rely exclusively on the program for any reason.

//IN NO EVENT SHALL HTTP://WWW.LEARNDIARY.COM BE LIABLE TO ANY PARTY FOR

//DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES,

//INCLUDING LOST PROFITS, ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS

//DOCUMENTATION, EVEN IF HTTP://WWW.LEARNDIARY.COM HAS BEEN ADVISED OF THE

//POSSIBILITY OF SUCH DAMAGE. HTTP://WWW.LEARNDIARY.COM SPECIFICALLY

//DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED

//WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE

//SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND

//HTTP://WWW.LEARNDIARY.COM HAS NO OBLIGATIONS TO PROVIDE MAINTENANCE,

//SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.

package com.learndiary.website.action.rss;

import java.io.IOException;

import javax.servlet.http.HttpServletRequest;

import org.apache.struts.action.ActionForward;

import org.apache.commons.logging.Log;

import org.apache.commons.logging.LogFactory;

import org.apache.struts.action.ActionMapping;

import javax.servlet.http.HttpServletResponse;

import org.apache.struts.action.Action;

import org.apache.struts.action.ActionForm;

import com.learndiary.website.util.rss.*;

import com.sun.syndication.io.FeedException;

/**

 * action for generating rss feed.

 * @author http://www.learndiary.com,LearnDiary Develop Group

 */

public class RSSAction extends Action {

  /* {src_lang=Java}*/

  private Log __log = LogFactory.getFactory().getInstance(this.getClass());

  ;

  /* {transient=false, volatile=false}*/

  /**

   *  pseudo code:

   *  {

   *    //the rss feed type,includes:

   *    //latestDiariesOfMyProcessGoal, latestAdvicesOfMyDiaries,

   *    //latestGoals, mostJoinedGoals, latestDiaries, latestAdvices,

   *    //latestDiariesOfGoal, latestAdvicesOfGoal,etc..

   *    String type=request.getParameter("type");

   *   

   *    //feed type,includes:

   *    //RSS 0.90, RSS 0.91 Netscape, RSS 0.91 Userland,

   *    //RSS 0.92, RSS 0.93, RSS 0.94, RSS 1.0,

   *    // RSS 2.0, Atom 0.3, Atom 1.0

   *    String rssVersion = request.getParameter("feedType");

   * 

   *    //entries number:

   *    //user can specify how many entries he would like to see,

   *    //the default entries number is 39.

   *    int entriesNum=Integer.parseInt(request.getParemeter("entriesNum"));

   * 

   *    //user's name:

   *    //for getting specified user's entries.

   *    String userName=request.getParameter("userName");

   * 

   *    //channel article's ID:

   *    //it is only for subscribing a goal's sub-entries,goalID.

   *    int  channelID=Integer.parseInt(request.getParemeter("channelID"));

   *   

   *    if (type.equal("latestDiaries")){

   *      RSSGenerator generator = new  LatestDiariesRSS(feedType, entriesNum);

   *      generator.outputFeed();

   *    }else if(type.equal("latestAdvices")){

   *      RSSGenerator generator = new  LatestAdvicesRSS(feedType, entriesNum);

   *      generator.outputFeed();

   *    }else if(type.equal("latestDiariesOfMyProcessGoal")){

   *      RSSGenerator generator = new  LatestDiariesOfMyProcessGoalRSS(feedType, entriesNum, userName);

   *      generator.outputFeed();

   *    }else if(type.equal("latestMyDiariesOfMyProcessGoal")){

   *      RSSGenerator generator = new  LatestMyDiariesOfMyProcessGoalRSS(feedType, entriesNum, userName);

   *      generator.outputFeed();

   *    }else if(type.equal("latestAdvicesOfMyDiaries")){

   *      RSSGenerator generator = new  LatestAdvicesOfMyDiariesRSS(feedType, entriesNum, userName);

   *      generator.outputFeed();

   *    }else if(type.equal("latestDiariesOfGoal")){

   *      RSSGenerator generator = new  LatestDiariesOfGoalRSS(feedType, entriesNum, channelID);

   *      generator.outputFeed();

   *    }else if(type.equal("latestAdvicesOfGoal")){

   *      RSSGenerator generator = new  LatestAdvicesOfGoalRSS(feedType, entriesNum, channelID);

   *      generator.outputFeed();

   *    }else if(type.equal("latestGoals")){

   *      RSSGenerator generator = new  LatestGoalsRSS(feedType, entriesNum);

   *      generator.outputFeed();

   *    }else if(type.equal("mostJoinedGoals")){

   *      RSSGenerator generator = new  MostJoinedGoalsRSS(feedType, entriesNum);

   *      generator.outputFeed();

   *    }else {

   *      show "error type" message;

   *    }

   *  }//end of excute() method

   *  

   */

  public ActionForward execute(

    ActionMapping mapping,

    ActionForm form,

    HttpServletRequest request,

    HttpServletResponse response) {

    //the rss feed type,includes:

    //latestDiariesOfMyProcessGoal, latestAdvicesOfMyDiaries,

    //latestGoals, mostJoinedGoals, latestDiaries, latestAdvices,

    //latestDiariesOfGoal, latestAdvicesOfGoal,etc..

    String type = request.getParameter("type");

    //feed type,includes:

    //RSS 0.90, RSS 0.91 Netscape, RSS 0.91 Userland,

    //RSS 0.92, RSS 0.93, RSS 0.94, RSS 1.0,

    // RSS 2.0, Atom 0.3, Atom 1.0

    String feedType = request.getParameter("feedType");

    //entries number:

    //user can specify how many entries he would like to see,

    //the default entries number is 39.

    int entriesNum = Integer.parseInt(request.getParameter("entriesNum"));

    //user's name:

    //for getting specified user's entries.

    String userName = request.getParameter("userName");

    //channel article's ID:

    //it is only for subscribing a goal's sub-entries,goalID.

    int channelID = 0;

    String channelIDStr = request.getParameter("channelID");

    if (channelIDStr != null && !channelIDStr.equals(""))

      channelID = Integer.parseInt(channelIDStr);

    try {

      if (type.equals("latestDiaries")) {

        RSSGenerator generator = new LatestDiariesRSS(feedType, entriesNum);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestDiaries:feedType="

            + feedType

            + " entriesNum="

            + entriesNum);

      } else if (type.equals("latestAdvices")) {

        RSSGenerator generator = new LatestAdvicesRSS(feedType, entriesNum);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestAdvices:feedType="

            + feedType

            + " entriesNum="

            + entriesNum);

      } else if (type.equals("latestDiariesOfMyProcessGoal")) {

        RSSGenerator generator =

          new LatestDiariesOfMyProcessGoalRSS(feedType, entriesNum, userName);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestDiariesOfMyProcessGoal:feedType="

            + feedType

            + " entriesNum="

            + entriesNum

            + " userName="

            + userName);

      } else if (type.equals("latestMyDiariesOfMyProcessGoal")) {

        RSSGenerator generator =

          new LatestMyDiariesOfMyProcessGoalRSS(feedType, entriesNum, userName);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestMyDiariesOfMyProcessGoal:feedType="

            + feedType

            + " entriesNum="

            + entriesNum

            + " userName="

            + userName);

      } else if (type.equals("latestAdvicesOfMyDiaries")) {

        RSSGenerator generator =

          new LatestAdvicesOfMyDiariesRSS(feedType, entriesNum, userName);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestAdvicesOfMyDiaries:feedType="

            + feedType

            + " entriesNum="

            + entriesNum

            + " userName="

            + userName);

      } else if (type.equals("latestDiariesOfGoal")) {

        RSSGenerator generator =

          new LatestDiariesOfGoalRSS(feedType, entriesNum, channelID);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestDiariesOfGoal:feedType="

            + feedType

            + " entriesNum="

            + entriesNum

            + " channelID="

            + channelID);

      } else if (type.equals("latestAdvicesOfGoal")) {

        RSSGenerator generator =

          new LatestAdvicesOfGoalRSS(feedType, entriesNum, channelID);

        generator.outputFeed(response);

        __log.info(

          "get feed of latestAdvicesOfGoal:feedType="

            + feedType

            + " entriesNum="

            + entriesNum

            + " channelID="

            + channelID);

      } else if (type.equals("latestGoals")) {

        RSSGenerator generator = new LatestGoalsRSS(feedType, entriesNum);

        generator.outputFeed(response);

        __log.info(

          "get feed of LatestGoalsRSS:feedType="

            + feedType

            + " entriesNum="

            + entriesNum);

      } else if (type.equals("mostJoinedGoals")) {

        RSSGenerator generator = new MostJoinedGoalsRSS(feedType, entriesNum);

        generator.outputFeed(response);

        __log.info(

          "get feed of mostJoinedGoals:feedType="

            + feedType

            + " entriesNum="

            + entriesNum);

      } else {

        return mapping.findForward("commonFailure");

      }

    } catch (IOException e1) {

      e1.printStackTrace();

    } catch (FeedException e2) {

      e2.printStackTrace();

    } catch (Exception e3) {

      e3.printStackTrace();

    }

    return null;

  }

}

  2、

//$ Id: RSSGenerator.java,v1.4  2006/02/26 20:49:06 dashing_meng Exp $

//Copyright (c) 2004-2005 Http://www.learndiary.com. All Rights Reserved.

//Permission to use, copy, modify, and distribute this software and its

//documentation without fee, and without a written agreement is hereby

//granted, provided that the above copyright notice and this paragraph

//appear in all copies.  This software program and documentation are

//copyrighted by http://www.learndiary.com. The software program and

//documentation are supplied "AS IS", without any accompanying services

//from The LearnDiary. The LearnDiary does not warrant that the operation

//of the program will be uninterrupted or error-free. The end-user

//understands that the program was developed for research purposes and is

//advised not to rely exclusively on the program for any reason.

//IN NO EVENT SHALL HTTP://WWW.LEARNDIARY.COM BE LIABLE TO ANY PARTY FOR

//DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES,

//INCLUDING LOST PROFITS, ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS

//DOCUMENTATION, EVEN IF HTTP://WWW.LEARNDIARY.COM HAS BEEN ADVISED OF THE

//POSSIBILITY OF SUCH DAMAGE. HTTP://WWW.LEARNDIARY.COM SPECIFICALLY

//DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED

//WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE

//SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND

//HTTP://WWW.LEARNDIARY.COM HAS NO OBLIGATIONS TO PROVIDE MAINTENANCE,

//SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.

package com.learndiary.website.util.rss;

import com.sun.syndication.feed.synd.SyndCategory;

import com.sun.syndication.feed.synd.SyndCategoryImpl;

import com.sun.syndication.feed.synd.SyndContent;

import com.sun.syndication.feed.synd.SyndContentImpl;

import com.sun.syndication.feed.synd.SyndEntry;

import com.sun.syndication.feed.synd.SyndEntryImpl;

import com.sun.syndication.feed.synd.SyndFeed;

import com.sun.syndication.io.FeedException;

import com.sun.syndication.io.SyndFeedOutput;

import com.learndiary.website.Constants;

import com.learndiary.website.Consts;

import com.learndiary.website.model.ArticleInfo;

import java.io.IOException;

import java.io.PrintWriter;

import java.text.DateFormat;

import java.text.ParseException;

import java.text.SimpleDateFormat;

import org.apache.commons.logging.Log;

import java.util.ArrayList;

import java.util.Iterator;

import java.util.List;

import com.learndiary.website.db.ArticleDB;

import com.learndiary.website.dao.TransContext;

import javax.servlet.http.HttpServletResponse;

/**

 * the base abstract class for generating rss feed.

 * @author http://www.learndiary.com,LearnDiary Develop Group

 */

public abstract class RSSGenerator {

  protected static final DateFormat DATE_PARSER =

    new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");

  /* {transient=false, volatile=false}*/

  protected Log __log = null; //should it be added "static" modifier?

  /* {transient=false, volatile=false}*/

  protected static TransContext trans = null;

  /* {transient=false, volatile=false}*/

  protected static ArticleDB myDB = null;

  /* {transient=false, volatile=false}*/

  protected String feedType = "rss_2.0";

  /* {transient=false, volatile=false}*/

  protected int entriesNum = 39;

  /* {transient=false, volatile=false}*/

  protected final List entries = new ArrayList();

  /* {transient=false, volatile=false}*/

  protected SyndFeed feed = null;

  /* {transient=false, volatile=false}*/

  protected String catName = null;

  /* {transient=false, volatile=false}*/

  /**

   *  output the rss feed xml page

   *  pseudo code:

   *  {

   *    res.setContentType("application/xml; charset=UTF-8");

   *    SyndFeedOutput output = new SyndFeedOutput();

   *    output.output(feed,res.getWriter());

   *  }

   * @param res the HttpServletResponse come from the excute() method of struts Action 

   */

  public void outputFeed(HttpServletResponse res)

    throws IOException, FeedException, Exception {

    try {

      this.setFeed();

    } catch (Exception e1) {

      e1.printStackTrace();

    }

    res.setContentType("application/xml; charset=UTF-8");

    SyndFeedOutput output = new SyndFeedOutput();

    PrintWriter out = res.getWriter();

    try {

      output.output(feed, out);

    } catch (IOException e) {

      e.printStackTrace();

    } catch (FeedException e) {

      e.printStackTrace();

    }

  }

  /**

   *  set rss feed

   */

  abstract protected void setFeed() throws Exception;

  /**

   *  set articles into the entries list of the rss feed

   *  {

   *    List artList=(ArrayList)myDB.getCPageList(0, entriesNum, "article", condition, Consts.ART_WRITE, Consts.DIR_DESC, Consts.HTML_FLAG);

   *    Iterator it=artList.listIterator();

   *     while (it.hasNext()) {

   *        ArticleInfo anArt = (ArticleInfo)it.next();

   *        entries.addEntry(anArt);

   *    }

   *  }

   * @param condition "WHERE" clause in the sql statement,for example:"WHERE parentID=1 AND typeID=2" 

   */

  protected void setEntries(String condition,int orderType,int direction,int htmlFlag) throws Exception {

    List artList = new ArrayList();

    __log.debug("setEntries() in RSSGenerator:entriesNum="+entriesNum+" condition is:"+condition);

    try {

      artList =

        (ArrayList) myDB.getCPageList(

          0,

          entriesNum,

          "article",

          condition,

          orderType,

          direction,

          htmlFlag);

    } catch (Exception e) {

      e.printStackTrace();

    }

    __log.debug("artList is:"+artList);

    if (artList == null)

      return;

    Iterator it = artList.listIterator();

    while (it.hasNext()) {

      ArticleInfo anArt = (ArticleInfo) it.next();

      this.addEntry(anArt);

    }

  }

  /**

   *  add an articleInfo into rss entries list

   *  pseudo code:

   *  {

   *    SyndEntry entry = new SyndEntryImpl();

   *    entry.setAuthor(anArt.getUserName());

   *    entry.setTitle(title);

   *    entry.setLink(link);

   *    entry.setPublishedDate(DATE_PARSER.parse(date));

   *    SyndContent description = new SyndContentImpl();

   *    description.setType("text/plain");

   *    description.setValue(blogContent);

   *    entry.setDescription(description);

   *    List categories = new ArrayList();

   *    SyndCategory category = new SyndCategoryImpl();

   *    category.setName(catName);

   *    categories.add(category);

   *    entry.setCategories(categories);

   *    entries.add(entry);

   *  }

   * @param anArt an article's information

   */

  private void addEntry(ArticleInfo anArt) throws Exception, ParseException {

    int artType = anArt.getTypeID();

    int artID = anArt.getArticleID();

    int parentID = anArt.getParentID();

    String parentName = anArt.getParentArticleName();

    String parentParentName = null;

    int parentType = 0;

    try {

      parentType = myDB.getArtTypeByID(parentID);

      if (parentType == Consts.DIARY_TYPE)

        parentParentName = myDB.getArtNameByID(myDB.getParentIDByID(parentID));

    } catch (Exception e1) {

      e1.printStackTrace();

    }

    String artName = anArt.getArticleName();

    String artAuthor = anArt.getUserName();

    String artContent = anArt.getArticleText();

    String artResource = anArt.getArticleResource();

    String writeDate = anArt.getWriteDate();

    SyndEntry entry = new SyndEntryImpl();

    entry.setAuthor(artAuthor);

    __log.debug("set entry's author is:" + artAuthor);

    entry.setTitle(artName);

    __log.debug("set entry's title is:" + artName);

    //get article's link and rss description head information;

    String link = null, headInfo = null;

    if (artType == Consts.GOAL_TYPE) {

      link =

        Constants.APPLICATION_PATH.concat(

          "/disGoalContentAction.do?goalID=" + artID);

      headInfo =

        "\""

          + artAuthor

          + "\" 在:"

          + writeDate

          + " 首先创建了目标:\""

          + artName

          + "\"<p>";

    } else if (artType == Consts.DIARY_TYPE) {

      link =

        Constants.APPLICATION_PATH.concat(

          "/disDiaryContentAction.do?goalID" + artID);

      headInfo =

        "\""

          + artAuthor

          + "\" 于:"

          + writeDate

          + " 在目标:\""

          + parentName

          + "\"下添加了日记:\""

          + artName

          + "\"<p>";

    } else if (

      artType == Consts.ADVICE_TYPE && parentType == Consts.GOAL_TYPE) {

      link =

        Constants.APPLICATION_PATH.concat(

          "/disGoalContentAction.do?goalID" + parentID);

      headInfo =

        "\""

          + artAuthor

          + "\" 于:"

          + writeDate

          + " 在目标:\""

          + parentName

          + "\"下添加了评论:\""

          + artName

          + "\"<p>";

    } else {

      link =

        Constants.APPLICATION_PATH.concat(

          "/disDiaryContentAction.do?goalID" + parentID);

      headInfo =

        "\""

          + artAuthor

          + "\" 于:"

          + writeDate

          + " 在目标:\""

          + parentParentName

          + "\"的日记:\""

          + parentName

          + "\"下添加了评论:\""

          + artName

          + "\"<p>";

    }

    entry.setLink(link);

    __log.debug("set entry's link is:" + link);

    try {

      entry.setPublishedDate(DATE_PARSER.parse(writeDate));

      __log.debug("set entry's publishedDate is:" + writeDate);

    } catch (ParseException e) {

      e.printStackTrace();

    }

    SyndContent description = new SyndContentImpl();

    description.setType("text/plain");

    String value =

      headInfo.concat("文章内容:<br>").concat(artContent).concat(

        "<p>相关资源:<br>" + artResource);

    description.setValue(value);

    __log.debug("set description's value is:" + value);

    entry.setDescription(description);

    List categories = new ArrayList();

    SyndCategory category = new SyndCategoryImpl();

    category.setName(catName);

    __log.debug("set category's name is:" + catName);

    categories.add(category);

    entry.setCategories(categories);

    entries.add(entry);

    __log.debug(

      "add an entry into entriesList.\n*********************************");

  }

}

  3、

//$ Id: LatestGoalsRSS.java,v 1.0 2006/02/26 20:49:06 dashing_meng Exp $

//Copyright (c) 2004-2005 Http://www.learndiary.com. All Rights Reserved.

//Permission to use, copy, modify, and distribute this software and its

//documentation without fee, and without a written agreement is hereby

//granted, provided that the above copyright notice and this paragraph

//appear in all copies.  This software program and documentation are

//copyrighted by http://www.learndiary.com. The software program and

//documentation are supplied "AS IS", without any accompanying services

//from The LearnDiary. The LearnDiary does not warrant that the operation

//of the program will be uninterrupted or error-free. The end-user

//understands that the program was developed for research purposes and is

//advised not to rely exclusively on the program for any reason.

//IN NO EVENT SHALL HTTP://WWW.LEARNDIARY.COM BE LIABLE TO ANY PARTY FOR

//DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES,

//INCLUDING LOST PROFITS, ARISING OUT OF THE USE OF THIS SOFTWARE AND ITS

//DOCUMENTATION, EVEN IF HTTP://WWW.LEARNDIARY.COM HAS BEEN ADVISED OF THE

//POSSIBILITY OF SUCH DAMAGE. HTTP://WWW.LEARNDIARY.COM SPECIFICALLY

//DISCLAIMS ANY WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED

//WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE

//SOFTWARE PROVIDED HEREUNDER IS ON AN "AS IS" BASIS, AND

//HTTP://WWW.LEARNDIARY.COM HAS NO OBLIGATIONS TO PROVIDE MAINTENANCE,

//SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.

package com.learndiary.website.util.rss;

import org.apache.commons.logging.LogFactory;

import com.learndiary.website.Constants;

import com.learndiary.website.Consts;

import com.learndiary.website.dao.TransContext;

import com.learndiary.website.db.ArticleDB;

import com.sun.syndication.feed.synd.SyndFeedImpl;

/**

 * for generating latest goals' rss feed.

 * @author http://www.learndiary.com,LearnDiary Develop Group

 */

public class LatestGoalsRSS extends RSSGenerator {

  public LatestGoalsRSS(String feedType, int entriesNum) {

    this.__log = LogFactory.getFactory().getInstance(this.getClass());

    try {

      RSSGenerator.trans = new TransContext();

      RSSGenerator.myDB = new ArticleDB(trans);

    } catch (Exception e) {

      e.printStackTrace();

    }

    this.feedType = feedType;

    this.entriesNum = entriesNum;

    this.catName = "最新创建的" + entriesNum + "个目标";

  }

  protected void setFeed() throws Exception {

    try {

      this.setEntries("WHERE typeID=1",Consts.ART_WRITE,Consts.DIR_DESC,Consts.HTML_FLAG);

    } catch (Exception e) {

      e.printStackTrace();

    }

    feed = new SyndFeedImpl();

    feed.setFeedType(feedType);

    feed.setTitle("最新创建的" + entriesNum + "个目标");

    feed.setLink(Constants.APPLICATION_PATH.concat("/indexAction.do"));

    feed.setDescription("学习日记里按时间排序的最新创建的" + entriesNum + "个目标。");

    feed.setCopyright(

      "除原作者特别声明外,本站所有帖子以<a rel=\"license\" href=\"http://creativecommons.org/licenses/by/2.0/\" target=\"creativecommons\">Creative Commons License</a>方式授权.");

    feed.setEntries(entries);

  }

}

一个非常成功使用目标分享的语言学习网站http://bulo.hjengl

  http://bulo.hjenglish.com/goal.htm

  我估计这个网站是模仿的www.43things.com的模式。但是,他们把这种模式成功的应用到他们网站的语言学习领域。这个网站的总体运作的模式值得深入研究。

  因为,还需要这种交流形式的网站在未来有可能成为学习日记系统的潜在用户,研究他们的需求是非常有意义的。

一个使用了xml_rpc和 Rome 0.6 for RSS / Atom feed generation开源blog

  他的站点是:https://fatima.dev.java.net/

  下面是简介,我想从中可以学习到相关的知识:

JavaPress: Java Blogging / Content Management System

This software is a content management system that runs in a Jakarta Tomcat container with AJAX additions.

Because it runs in Java, it provides a good alternative to the many PHP containers out there. From the technology perspective, it has custom category management, and category exclusion like Slashdot, Rome 0.5 API(s) from Sun Microsystems provides RSS 2.0, 1.x, and Atom x.3 feeds as well as auto generating feeds for each category and can generate Podcasts using the tag. It also has automated XML-RPC pinging using Apache's XML-RPC libraries and can ping up to 50 sites with custom categories (i.e. you can ping javablogs.com with only your "Java" category RSS feed if you wish). It also has a complete user management area where users can edit or delete their comments and manage their information, something lacking in other blogging software. It also includes internal messaging and email notification using JavaMail. It has a custom admin section as well to manage all aspects of the code, and can run on MySQL, PostgreSQL, or any XML JDBC interface using connection pooling. It also uses Hibernate for many Java Beans.

The project is delivered in two sections:

PressCore - The EAR file, although it can be simply deployed as classes in the WEB-INF/classes folder, contains all the workhorse code, including the Technorati integration, Hibernate code, Connection Pooling, JNDI, category management and exclusion, rss generation, podcasting manager, xml-rpc pinging (up to 40 sites now, database driven!) and many other neat things.

PressWeb - The WAR file as it were, or simply the content with the JSP tags and example WEB-INF and META-INF that implements all the db pooling, mailing and other features. Should be easy to set up if you use the /install directory after you deploy this WAR in your Tomcat container (WARNING: Delete this install directory before you release in to production!)

External API(s):

Sun Microsystem's Rome 0.6 for RSS / Atom feed generation

Apache XML-RPC libraries for weblog pinging

Sun Microsystem's Java API for XML Processing (JAXP) v1.2.6_01

Sun Microsystem's JavaServer Pages Standard Tag Library (JSTL) v1.1.1_01

Technorati Java API (jTechnorati)

学习日记在几个搜索引擎的结果中的排名

  目前,以“学习日记”为关键字,在google,百度,yahoo,163,tom等搜索引擎中排在搜索结果的第一个。我不知道,这些网站的搜索结果排名的依据是什么?到底对网站的成长有什么实际的意义没有?怎么样来利用这种结果为学习日记的发展服务。使学习日记真的实现“构建一个普遍适用的开源网络学习交流平台”的目标。

  不管怎么样,能排在第一个位置还是令人有点高兴的,虽然学习日记现在人气差劲,远远没有实现一些最基本的东西。我是否应该寻求那些对此感兴趣的人气资源丰富的开源项目网站的帮助?毕竟,我不是专业人士。