我正在寻找在Rails 3中生成Feed的最佳做法/标准模式。http://railscasts.com/episodes/87-generating-rss-feeds仍然有效吗?
答案 0 :(得分:113)
首先,现在我建议使用ATOM提要而不是RSS 。
ATOM feed的规范提供了比RSS更具价值的国际化,内容类型和其他东西和每个现代提要阅读器都支持它。
有关ATOM vs RSS的更多信息,请访问:
关于编码:
此示例假定:
NewsItem
的模型,具有以下属性:
title
content
author_name
news_items_controller.rb
),您将添加feed
操作我们将使用一个构建器模板和Ruby on Rails atom_feed helper,它非常有用。
<强> 1。将操作添加到控制器
转到app/controllers/news_items_controller.rb
并添加:
def feed
# this will be the name of the feed displayed on the feed reader
@title = "FEED title"
# the news items
@news_items = NewsItem.order("updated_at desc")
# this will be our Feed's update timestamp
@updated = @news_items.first.updated_at unless @news_items.empty?
respond_to do |format|
format.atom { render :layout => false }
# we want the RSS feed to redirect permanently to the ATOM feed
format.rss { redirect_to feed_path(:format => :atom), :status => :moved_permanently }
end
end
<强> 2。设置构建器模板
现在让我们添加模板来构建Feed。
转到app/views/news_items/feed.atom.builder
并添加:
atom_feed :language => 'en-US' do |feed|
feed.title @title
feed.updated @updated
@news_items.each do |item|
next if item.updated_at.blank?
feed.entry( item ) do |entry|
entry.url news_item_url(item)
entry.title item.title
entry.content item.content, :type => 'html'
# the strftime is needed to work with Google Reader.
entry.updated(item.updated_at.strftime("%Y-%m-%dT%H:%M:%SZ"))
entry.author do |author|
author.name entry.author_name
end
end
end
end
第3。用路线连接
提供Feed默认情况下,这会使用ATOM格式调用操作,并将/feed.rss
重定向到/feed.atom
。
转到config/routes.rb
并添加:
resources :news_items
match '/feed' => 'news_items#feed',
:as => :feed,
:defaults => { :format => 'atom' }
<强> 4。在布局上添加指向ATOM和RSS源的链接
最后,剩下的就是将Feed添加到布局中。
转到app/views/layouts/application.html.erb
并添加<head></head>
部分:
<%= auto_discovery_link_tag :atom, "/feed" %>
<%= auto_discovery_link_tag :rss, "/feed.rss" %>
可能有一两个错字,所以请告诉我这是否适合你。
答案 1 :(得分:10)
我做了类似的事情但没有创建新动作。
atom_feed :language => 'en-US' do |feed|
feed.title "Articles"
feed.updated Time.now
@articles.each do |item|
next if item.published_at.blank?
feed.entry( item ) do |entry|
entry.url article_url(item)
entry.title item.title
entry.content item.content, :type => 'html'
# the strftime is needed to work with Google Reader.
entry.updated(item.published_at.strftime("%Y-%m-%dT%H:%M:%SZ"))
entry.author item.user.handle
end
end
end
除非你有像我这样的特殊代码,否则你不需要在控制器中做任何特殊的事情。例如,我使用的是will_paginate gem,对于原子提要,我不希望它分页,所以我这样做是为了避免这种情况。
def index
if current_user && current_user.admin?
@articles = Article.paginate :page => params[:page], :order => 'created_at DESC'
else
respond_to do |format|
format.html { @articles = Article.published.paginate :page => params[:page], :order => 'published_at DESC' }
format.atom { @articles = Article.published }
end
end
end