Edited at

acts_as_followerを使ってフォロー/フォロワー機能を実装

More than 1 year has passed since last update.


前説

フォロー、フォロワー機能を実装しました。

イメージとしてはデータベースのテーブル関係とはどうするんだろうとかと、ハードル高そうに感じていました。

しかしgemを用いると結構すぐに実装できました。


実装


  • 非同期でフォロー、フォロワー機能を実装


コード

以下のgemを導入します。

gem 'acts_as_follower'

  follow_users POST   /users/:id/follow(.:format)                  users#follow 

unfollow_users POST /users/:id/unfollow(.:format) users#unfollow

導入部に関してはこちらを参考にして頂けた方がわかりやすいかと思います。

気になっていたデータベースとつなぐmodelの部分。


model/follow.rb

class Follow < ActiveRecord::Base

extend ActsAsFollower::FollowerLib
extend ActsAsFollower::FollowScopes

# NOTE: Follows belong to the "followable" interface, and also to followers
belongs_to :followable, :polymorphic => true
belongs_to :follower, :polymorphic => true

def block!
self.update_attribute(:blocked, true)
end

end


ここで知らないデータベース関連がでてきました。

polymorphic => true

followerとfollowableの二つの情報があるのに対し、用意されているテーブルは一つだけ。

つまり、フォローもフォロワーも親クラスから見た操作や情報がほとんど同じである為、一つのテーブルにまとめてしまおうというものらしい。

https://shirusu-ni-tarazu.hatenablog.jp/entry/2012/11/04/173742

↑参考記事


model/user.rb

class User < ApplicationRecord

acts_as_followable # フォロワー機能
acts_as_follower # フォロー機能
end



cotroller/user_controller.rb

def follow

@user = User.find(params[:id])
#ログイン中のユーザーで対象のユーザー(@user)をフォローする
current_user.follow(@user)
end

def unfollow
@user = User.find(params[:id])
#ログイン中のユーザーで対象のユーザー(@user)をフォロー解除する
current_user.stop_following(@user)
end



user/show.html.erb

<li id="user-<%= @user.id %>" class="collection-item">

<%= render 'users/follow', user: @user %>
</li>


user/_follow.html.erb

#任意のユーザーのマイページにて

#マイページのユーザーが現在ログインしているユーザーでない時->フォロー/フォロワーボタンを設置
<% if user.id != current_user.id %>
<li class="collection-item">
#現在のユーザーが対象のユーザーをフォローしてない時->「フォローするボタン」を設置
<% unless current_user.following?(user) %>
<div class="action">
<%= link_to 'フォローする' ,follow_users_path,method: :post, class: "btn waves-effect waves-light" ,remote: true %>
</div>
#現在のユーザーが対象のユーザーをフォローしてる時->「フォロー解除ボタン」を設置
<% else %>
<div class="action">
<%= link_to 'フォローを解除する' ,unfollow_users_path, method: :post,class: "btn waves-effect waves-light",remote: true %>
</div>
<% end %>
</li>
<% end %>


follow.js.erb

$("#user-<%= @user.id %>").html("<%= j(render partial: 'users/follow', locals: { user: @user }) %>")



unfollow.js.erb

$("#user-<%= @user.id %>").html("<%= j(render partial: 'users/follow', locals: { user: @user }) %>")



結果

スクリーンショット 2018-05-08 23.32.15.png

フォローするでしょ


終わりに

感じたこととしてはいいね機能の実装と近い感じがしました。


今後の実装


  • フォロワーの数を数えてランキングにもしたい

  • フォローしているユーザーによるタイムラインの実装とか