iT邦幫忙

DAY 29
12

Rails 的簡單任務系列 第 31

[RoR] 小小複雜模仿 del.icio.us 的個人化的社會標籤 per user tagging

繼續上一篇 [RoR] 小小複雜建置 Social Tagging 社會標籤功能 的測試操作,透過這一篇,就可將網站,建置成網址像:http://delicious.com/twtw 列出該使用者 所標籤的所有項目,而 http://delicious.com/twtw/ror 可列出該使用者有標籤為 ror 的項目。
在網頁顯示該項目有幾人標籤

要在各項目列出有幾人標籤,在 app/views/bibles/index.html.erb 的適當位置加入:

<%= User.having_bible(bible.id).size %>人標籤
# 用 size 的語法算出有幾個 user ;點該項目後,才要列出哪些 user 及其此項目的 標籤 出來。

在 app/models/user.rb 加入以下語法:

 def self.having_bible(bibleid)
  User.find_by_sql ["select distinct users.* from users inner join tags on users.id = tags.user_id inner join tagships on tagships.tag_id = tags.id inner join bibles on bibles.id = tagships.model_id where bibles.id = ? ;", bibleid]
 end

也是利用 INNER JOIN 的方式,來查詢某項目中,列出哪些 user 有 tagging 此項目。
只要 User.having_bible(1) 就可以查出有標籤該項目的 user 。

列出有在該項目做標籤的 User 及標籤名稱

# 先在 app/controllers/bibles_controller.rb 的 def show 之中加入:
    @users = User.having_bible(@bible.id)
# 然後在原有的 app/views/bibles/show.html.erb 中加入:
<h4>哪些人標籤此</h4>
<ul>
<% @users.each do |u| -%>
<li>
<%= link_to u.login, user_tag_home_path(u.login) %>
標籤:
<% Tag.userid_itemid(u.id,@bible.id,'Bible').each do |t| %>
<%= link_to t.name, user_per_tag_path(u.login,t.name) %>
<% end %>
</li>
<% end %>
</ul>

定義成像 del.icio.us 般的個人、標籤路徑
上述的 user_tag_home_path 及 user_per_tag_path 即是本文一開始所提及的 使用者的家、所有標籤過項目的家 的路徑,像 http://delicious.com/twtw 一般:

以及其所屬各個標籤 的路徑,像 http://delicious.com/twtw/ror

在 config/routes.rb 定義 每個使用者曾標籤項目的列表、列出使用者屬於某標籤的項目列表

  map.user_tag_home ':username', :controller => 'bibles', :action => 'user_tag_home'
  map.user_per_tag ':username/:tag', :controller => 'bibles', :action => 'user_per_tag'

接下來把上述需要的 action 加入:

# 類似 http://delicious.com/twtw 找出所有 user 所標示過的項目列表
  def user_tag_home
   @user = User.find_by_login(params[:login])
   @userbibles = Bible.find_tagged_by(@user.id, :order => 'ts.created_at desc' )
   @bibles = @userbibles.paginate :per_page => 10, :page => params[:page]
  end
# 類似 http://delicious.com/twtw/ror 列出 user 某標籤名稱的所有項目
  def user_per_tag
   @user = User.find_by_login(params[:login])
   @userbibles = Bible.find_by_sql ["select bibles.* from bibles inner join tagships on bibles.id = tagships.model_id inner join tags on tags.id = tagships.tag_id inner join users on users.id = tags.user_id where users.login = ? and tags.name = ?;",params[:login], params[:tag]]
   @bibles = @userbibles.paginate :per_page => 3, :page => params[:page]
# 所得的結果,去共同 user_tag_home 的 template
   render :action => 'user_tag_home'
  end

編輯 app/views/bibles/user_tag_home.html.erb 來顯示 user 所列的標籤項目

<!-- 這邊做一個類似「麵包屑」的顯示,透過正執行的 action 名稱,來決定 user.login 要不要 hyperlink 及秀出哪一個 標籤名稱 為標題 -->
<h2><%= link_to '聖經測試首頁', bibles_url %> >>
<% if controller.action_name == 'user_tag_home' -%>
  <%= @user.login -%>
<% else -%>
  <%= link_to @user.login, user_tag_home_path(@user.login) -%> >>
  <%= params[:tag] -%>
<% end -%>
</h2>
<% if controller.action_name == 'user_per_tag' -%>
  <h4>有 <%= params[:tag] -%> 標籤項目</h4>
<% else -%>
  <h4>所有的標籤項目</h4>
<% end -%>
<ol>
<% @bibles.each do |b| %>
<li><%= link_to b.txt, bible_path(b.id) %><%= b.chineses %><%= b.chap%>:<%= b.sec %><br />
標籤:
<% Tag.userid_itemid(@user.id,b.id,'Bible').each do |t| %>
<%= link_to t.name, user_per_tag_path(@user.login,t.name) %>
<% end %>...
<%= User.having_bible(b.id).size %> 人標籤此項
</li>
<% end %>
</ol>

從上述已做成各項目、各使用者標籤之家、各標籤名稱之間的連結;下一篇 續編 再分享有關增減標籤的做法。


上一篇
[RoR] 小小複雜建置 Social Tagging 社會標籤功能
下一篇
[RoR] 小小複雜模仿 del.icio.us 的個人化的社會標籤 per user tagging (續)
系列文
Rails 的簡單任務33

1 則留言

0
gric
iT邦高手 1 級 ‧ 2009-03-14 15:44:48

2009/03/09遲到 11:55 到

gric iT邦高手 1 級‧ 2009-03-14 15:46:05 檢舉

SORRY!是感恩謝謝分享!

我要留言

立即登入留言