Rails 计算每个标签的文章和每个标签的相关文章
Rails count article per tag and related article by tag
大家好,我是 rails 的新手,尝试做一些我以前从未做过的事情。
首先我现在 Rails 有 gems acts_as_taggable 但我试过了但对我没有用 可能需要学习如何安装他(已经安装 acts_as_votable)。
所以这是我的问题,我想为每篇文章展示相关文章(带标签)。并且还想把article.count by tag放到我的标签里。
article.rb
class Article < ApplicationRecord
acts_as_votable
belongs_to :category
belongs_to :user
has_many :taggings
has_many :tags, through: :taggings
def tag_list
self.tags.collect do |tag|
tag.name
end.join(", ")
end
def tag_list=(tags_string)
tag_names = tags_string.split(",").collect{|s| s.strip.downcase}.uniq
new_or_found_tags = tag_names.collect { |name| Tag.find_or_create_by(name: name) }
self.tags = new_or_found_tags
end
has_attached_file :image, styles: { front: "400x500>" ,medium: "700x500>", small: "350x250>" }
validates_attachment_content_type :image, content_type: /\Aimage\/.*\Z/
end
tag.rb
class Tag < ApplicationRecord
has_many :taggings
has_many :articles, through: :taggings
def to_s
name
end
end
tagging.rb
class Tagging < ApplicationRecord
belongs_to :article
belongs_to :tag
end
articles_controller.rb
class ArticlesController < ApplicationController
before_action :find_article, only: [:show, :edit, :update, :destroy, :upvote, :downvote]
before_action :authenticate_user!, except: [:show, :index]
def index
if params[:category].blank?
@articles = Article.page(params[:page]).per(10).order('created_at DESC')
else
@category_id = Category.find_by(name: params[:category]).id
@articles = Article.where(category_id: @category_id).order("created_at DESC")
end
@tags = Tag.all
end
def show
# if params[:tag]
# @articles = Article.tagged_with(params[:tag])
# @tag = @articles
# end
end
def new
@article = current_user.articles.build
end
def create
@article = current_user.articles.build(article_params)
if @article.save
redirect_to @article
else
render 'new'
end
end
def edit
end
def update
if @article.update(article_params)
redirect_to @article
else
render 'edit'
end
end
def destroy
@artice.destroy
redirect_to root_path
end
def upvote
@article.upvote_by current_user
redirect_to :back
end
def downvote
@article.downvote_by current_user
redirect_to :back
end
private
def find_article
@article = Article.find(params[:id])
end
def article_params
params.require(:article).permit(:title, :content, :category_id, :image, :tag_list)
end
end
tags_controller.rb
class TagsController < ApplicationController
def show
@tag = Tag.find(params[:id])
end
end
这是要展示相关文章的展示页面
articles/show.html.haml
.container
.row
.col-md-8.col-offset-2
%h1= @article.title
= image_tag @article.image.url(:medium)
%br/
- @article.tags.each do |tag|
%h4
%strong
%span.label.label-danger
%i.fa.fa-tag
= link_to tag.name, tag
= tag.name.count
.pull-right
- if @article.user == current_user
.btn-group
= link_to 'Edit', edit_article_path, class: "btn btn-default"
= link_to 'Delete', article_path, method: :delete, data: {confirm: 'Are you sure ?'}, class: 'btn btn-danger'
%hr/
%p
%i.fa.fa-pencil
%strong=@article.user.username
%button.btn.btn-primary
%i.fa.fa-hand-o-left
Follow
%p
%i.fa.fa-clock-o
%em= time_ago_in_words(@article.created_at) + ' ago'
%hr/
%p= simple_format(@article.content)
.row
.col-md-4
= link_to like_article_path(@article), method: :get, class: 'btn btn-primary data' do
%i.fa.fa-thumbs-o-up
= @article.get_upvotes.size
= link_to dislike_article_path(@article), method: :get, class: 'btn btn-danger data' do
%i.fa.fa-thumbs-o-down
= @article.get_downvotes.size
.col-md-6.pull-right
%h3 Share this Article
= social_share_button_tag
%hr/
= render 'layouts/disqus'
-# .col-md-3.col-md-offset-1
-# %h2.text-center Articles Related
-# %hr/
-# - if @article(params[:tag])
-# - @tag.articles.each do |article|
-# .thumbnail
-# = link_to image_tag(article.image.url(:small)), article
-# .caption
-# %h3.text-center= @article.title
-# = link_to 'Read', @article, class: "btn btn-danger"
-# .pull-right
-# %span.badge.upvote
-# %i.fa.fa-thumbs-o-up
-# = @article.get_upvotes.size
-# %span.badge.downvote
-# %i.fa.fa-thumbs-o-down
-# = @article.get_downvotes.size
您应该查看 acts-as-taggable-on。有很多使用它的教程。我试过了,效果很好。 enter link description here
如果您想设置自己的标签表,您应该研究多对多关系:enter link description here
如果您尝试为每篇文章和计数显示相关文章,并且您正确设置了所有内容,它应该像这样简单:
(我准备写erb)
<% @articles.each do |article| %>
<%= article.title %>
<% article.tags.each do |tag| %>
Tag: <%= tag.to_s + "Related count: (#{tag.articles.count})" %>
Related articles:
<% tag.articles.each do |related_article| %>
<%= related_article.title %>
<% end %>
<% end %>
<% end %>
大家好,我是 rails 的新手,尝试做一些我以前从未做过的事情。 首先我现在 Rails 有 gems acts_as_taggable 但我试过了但对我没有用 可能需要学习如何安装他(已经安装 acts_as_votable)。
所以这是我的问题,我想为每篇文章展示相关文章(带标签)。并且还想把article.count by tag放到我的标签里。
article.rb
class Article < ApplicationRecord
acts_as_votable
belongs_to :category
belongs_to :user
has_many :taggings
has_many :tags, through: :taggings
def tag_list
self.tags.collect do |tag|
tag.name
end.join(", ")
end
def tag_list=(tags_string)
tag_names = tags_string.split(",").collect{|s| s.strip.downcase}.uniq
new_or_found_tags = tag_names.collect { |name| Tag.find_or_create_by(name: name) }
self.tags = new_or_found_tags
end
has_attached_file :image, styles: { front: "400x500>" ,medium: "700x500>", small: "350x250>" }
validates_attachment_content_type :image, content_type: /\Aimage\/.*\Z/
end
tag.rb
class Tag < ApplicationRecord
has_many :taggings
has_many :articles, through: :taggings
def to_s
name
end
end
tagging.rb
class Tagging < ApplicationRecord
belongs_to :article
belongs_to :tag
end
articles_controller.rb
class ArticlesController < ApplicationController
before_action :find_article, only: [:show, :edit, :update, :destroy, :upvote, :downvote]
before_action :authenticate_user!, except: [:show, :index]
def index
if params[:category].blank?
@articles = Article.page(params[:page]).per(10).order('created_at DESC')
else
@category_id = Category.find_by(name: params[:category]).id
@articles = Article.where(category_id: @category_id).order("created_at DESC")
end
@tags = Tag.all
end
def show
# if params[:tag]
# @articles = Article.tagged_with(params[:tag])
# @tag = @articles
# end
end
def new
@article = current_user.articles.build
end
def create
@article = current_user.articles.build(article_params)
if @article.save
redirect_to @article
else
render 'new'
end
end
def edit
end
def update
if @article.update(article_params)
redirect_to @article
else
render 'edit'
end
end
def destroy
@artice.destroy
redirect_to root_path
end
def upvote
@article.upvote_by current_user
redirect_to :back
end
def downvote
@article.downvote_by current_user
redirect_to :back
end
private
def find_article
@article = Article.find(params[:id])
end
def article_params
params.require(:article).permit(:title, :content, :category_id, :image, :tag_list)
end
end
tags_controller.rb
class TagsController < ApplicationController
def show
@tag = Tag.find(params[:id])
end
end
这是要展示相关文章的展示页面
articles/show.html.haml
.container
.row
.col-md-8.col-offset-2
%h1= @article.title
= image_tag @article.image.url(:medium)
%br/
- @article.tags.each do |tag|
%h4
%strong
%span.label.label-danger
%i.fa.fa-tag
= link_to tag.name, tag
= tag.name.count
.pull-right
- if @article.user == current_user
.btn-group
= link_to 'Edit', edit_article_path, class: "btn btn-default"
= link_to 'Delete', article_path, method: :delete, data: {confirm: 'Are you sure ?'}, class: 'btn btn-danger'
%hr/
%p
%i.fa.fa-pencil
%strong=@article.user.username
%button.btn.btn-primary
%i.fa.fa-hand-o-left
Follow
%p
%i.fa.fa-clock-o
%em= time_ago_in_words(@article.created_at) + ' ago'
%hr/
%p= simple_format(@article.content)
.row
.col-md-4
= link_to like_article_path(@article), method: :get, class: 'btn btn-primary data' do
%i.fa.fa-thumbs-o-up
= @article.get_upvotes.size
= link_to dislike_article_path(@article), method: :get, class: 'btn btn-danger data' do
%i.fa.fa-thumbs-o-down
= @article.get_downvotes.size
.col-md-6.pull-right
%h3 Share this Article
= social_share_button_tag
%hr/
= render 'layouts/disqus'
-# .col-md-3.col-md-offset-1
-# %h2.text-center Articles Related
-# %hr/
-# - if @article(params[:tag])
-# - @tag.articles.each do |article|
-# .thumbnail
-# = link_to image_tag(article.image.url(:small)), article
-# .caption
-# %h3.text-center= @article.title
-# = link_to 'Read', @article, class: "btn btn-danger"
-# .pull-right
-# %span.badge.upvote
-# %i.fa.fa-thumbs-o-up
-# = @article.get_upvotes.size
-# %span.badge.downvote
-# %i.fa.fa-thumbs-o-down
-# = @article.get_downvotes.size
您应该查看 acts-as-taggable-on。有很多使用它的教程。我试过了,效果很好。 enter link description here
如果您想设置自己的标签表,您应该研究多对多关系:enter link description here
如果您尝试为每篇文章和计数显示相关文章,并且您正确设置了所有内容,它应该像这样简单:
(我准备写erb)
<% @articles.each do |article| %>
<%= article.title %>
<% article.tags.each do |tag| %>
Tag: <%= tag.to_s + "Related count: (#{tag.articles.count})" %>
Related articles:
<% tag.articles.each do |related_article| %>
<%= related_article.title %>
<% end %>
<% end %>
<% end %>