Rails

【Rails】いいね機能完全版!同期いいね、いいね数の表示、非同期いいね、アイコン表示、それぞれの実装方法についてまとめて解説

Rails

 

今回は「いいね機能」の実装手順を、ミニアプリ制作を通して解説したいと思います。TwitterやInstagramでよく見かける「いいね機能」の大まかな実装手順をこの記事で学習し、ぜひ自分のアプリケーションにも導入してみてください。

実装内容は「同期いいね」「いいね数の表示」「非同期いいね」「アイコン表示」の4つになっています。

いいね機能実装のポイント

まずは、いいね機能実装のポイントについて予習しておきます。ここを理解しておくと実装がグッとやりやすくなるので、ぜひ理解して上で実装に取り掛かりましょう。

例えば、ユーザー登録(= usersテーブル)と投稿機能(= postsテーブル)を持ったアプリケーションがあるとします。加えてこれら2つのテーブルは1対多の関係になっています。

ユーザーと投稿の関係

 

ここにさらに、ユーザーが押した「いいね」を保存するテーブル(= likesテーブル)があると仮定します。その場合、これら3つのテーブル関係は以下のようになります。具体的には、「ユーザー」と「いいね」は1対多、「投稿」と「いいね」も1対多の関係となります。

likesテーブルとの関係
上記の図だと、ユーザー1が投稿2に、ユーザー2が投稿2と3にいいねを押していることになるね。

 

ここから分かる通り、「いいね」とはユーザーと投稿のidがセットになっている状態のことを指します。反対に、どちらか片方のidが存在していなければいいね機能は実装できないので、その点に注意しましょう。

いいね機能実装のポイント

「いいね」とはユーザーと投稿のidがセットになっている状態にならなければならない。

いいね機能実装の流れ

これから実装する「いいね機能」の大まかな流れは以下のようになります。この流れを頭に入れておきながら作業していきましょう。

  1. アプリケーション作成
  2. いいね機能実装(同期いいね)
  3. いいね機能実装(いいね数の表示)
  4. いいね機能実装(非同期いいね)
  5. いいね機能実装(アイコン表示)
非同期いいねの実装にはjs.erbを使用し、JavaScriptで記述します。
「非同期いいね」ではjQueryを使用している記事が多いですが、今回はJavaScriptで実装していきます。

実装手順【アプリケーション作成】

アプリケーションの立ち上げ

まずは以下のコマンドでアプリケーションの立ち上げを行いましょう。データベースの作成も同時に行います。

% rails new favorite-app -d mysql
% cd favorite-app
% rails db:create

今回開発するアプリケーションの環境は以下のようになります。

  • アプリケーション名:favorite-app
  • Rails:6.0.3.2
  • Ruby:2.6.5
  • DB:MySQL

deviseを用いたユーザー登録

ユーザー登録の実装には、deviseというgemを使用します。Github通り、以下の手順でdeviseをアプリケーションに導入しましょう。

# Gemfileの下部に以下を追記

gem 'devise'
% bundle install
% rails g devise:install
% rails g devise user
% rails db:migrate

トップページの作成

続いてトップページの作成です。

「home_controller.rb」を作成し、ルーティングとビューを編集しましょう。ここまでで、ユーザー登録機能が完成です。

% rails g controller home
# routes.rb

Rails.application.routes.draw do
  devise_for :users
  # 以下の1行を追記
  root 'home#index'
end
<%# views/home/index.html.erb %>

<% if user_signed_in? %>
  <%= link_to 'ログアウト', destroy_user_session_path, method: :delete %>
<% else %>
  <%= link_to 'ログイン', new_user_session_path %>
  <%= link_to '新規登録', new_user_registration_path %>
<% end %>
「devise_for :users」はdeviseの導入で自動的に生成されるルーティングです。

投稿機能の実装

次は投稿機能の実装です。

投稿機能の実装には、Railsの便利機能「scaffold」を使用します。「scaffold」の使い方はここでは解説しませんので、「scaffold」について詳しく知りたい方はこちらの記事を参考にしてください。

Rails
【Rails】秒速でアプリケーション開発できる、scaffoldの使い方を簡単にまとめてみた手っ取り早くアプリケーションを開発することができるscaffold(スキャフォールド)の使い方について簡単に解説しています。新しい機能実装をテストしてみたい、すぐにでもアプリケーションを立ち上げたいといった場合に便利な機能なので、ぜひ覚えておきましょう。...

 

まずは以下のコマンドで投稿機能を作成しましょう。シンプルなアプリケーション開発を目指すため、今回のカラムは「title」と「user_id」のみにしています。

% rails g scaffold post title:string user_id:integer
% rails db:migrate

 

現在のビューにはユーザー登録関係のリンクしかありません。「views/home/index.html.erb」に以下のコードを追記し、投稿ページへ遷移するボタンを追加しましょう。

<%# views/home/index.html.erbの最下部に以下を追記 %>

<%= link_to '投稿ページへ', posts_path %>
リンク先のパスは「rails routes」で確認しましょう。

 

ここで1つ問題があります。

それは「scaffold」の機能を用いて投稿機能を作成したことで、必要のない「user_id」のフォームまで作成されてしまいました。そこで、下記の記述を削除しましょう。

<%# views/posts/_form.html.erbの以下の記述を削除してください %>

<div class="field"> 
  <%= form.label :user_id %>
  <%= form.number_field :user_id %>
</div>
<%# views/posts/index.html.erbの以下の1行を削除してください %>

<td><%= post.user_id %></td>

 

「posts_controller.rb」のストロングパラメーターである「user_id」も必要ないので、「:user_id」も削除しましょう。

# posts_controller.rb

def post_params
  params.require(:post).permit(:title, :user_id)
end

↓ 「:user_id」を削除

def post_params
  params.require(:post).permit(:title)
end

 

最後に、投稿時にログインしているユーザーのidを保存する記述を追記します。これは、postsテーブルには「user_idカラム」が存在しているためです。

# posts_controller.rb

def create
  @post = Post.new(post_params)

  # 以下の1行を追記
  @post.user_id = current_user.id

  respond_to do |format|
    if @post.save
      format.html { redirect_to @post, notice: 'Post was successfully created.' }
      format.json { render :show, status: :created, location: @post }
    else
      format.html { render :new }
      format.json { render json: @post.errors, status: :unprocessable_entity }
    end
  end
end
user_idが必要な理由
# 省略

private

def post_params
  params.require(:post).permit(:title).merge(user_id: current_user.id)
end

 

上記のように、ストロングパラメーターにmergeメソッドを用いて「user_id」を付与することも可能です。

リダイレクト処理

今のままでは、ログインせずとも投稿ができてしまいます。posts_contoroller.rbに「before_action :authenticate_user!」を追加し、ログインしているユーザー以外はリダイレクトさせる処理を実装しましょう。

# posts_controller.rbに以下を追記

before_action :authenticate_user!
「before_action :authenticate_user!」を記述することで、そこで行われる処理はログインユーザーによってのみ実行可能となります。

アソシエーションの定義

冒頭でも解説した通り、ユーザーと投稿は1対多の関係になります。UserモデルとPostモデルにアソシエーションの記述を追記しましょう。

# user.rb

class User < ApplicationRecord
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :validatable
  has_many :posts
end
# post.rb

class Post < ApplicationRecord
  belongs_to :user
end

挙動確認

ここまでで「いいね機能」を実装する前の大まかな準備ができました。ここで一旦挙動を確かめてみます。

リダイレクト処理
Image from Gyazo
ユーザー登録
Image from Gyazo
投稿機能
Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

実装手順【同期いいね】

ではここからいいね機能の実装に取り掛かります。まずは「同期いいね」です。

likesテーブルの作成

まずはユーザーIDと投稿IDを保存するため「Likeモデル」を作成しましょう。カラムは外部キーである「user_id」と「post_id」のみです。

% rails g model Like user_id:integer post_id:integer
% rails db:migrate

アソシエーションの定義

次に「usersテーブル」「postsテーブル」「likesテーブル」のアソシエーションを定義します。それぞれのテーブル関係は、下の図を参考にしてください。

likesテーブルとの関係
# user.rb

class User < ApplicationRecord
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :validatable
  has_many :posts

  # 以下の1行を追記
  has_many :likes
end
# post.rb

class Post < ApplicationRecord
  belongs_to :user

  # 以下の1行を追記
  has_many :likes
end
# like.rb

class Like < ApplicationRecord
  # 以下の2行を追記
  belongs_to :user
  belongs_to :post
end

「いいね」の表示

ビューでは「いいね」を押すことができるリンクを作成しましょう。

以下のように「views/posts/index.html.erb」を編集し、「いいねを外す」と「いいね」がそれぞれ表示されるよう設定します。

<%# views/posts/index.html.erb %>

<p id="notice"><%= notice %></p>
<h1>Posts</h1>
<table>
  <thead>
    <tr>
      <th>Title</th>

      <%# Userの1行を削除 %>
      <th colspan="2"></th>
    </tr>
  </thead>
  <tbody>
    <% @posts.each do |post| %>
      <tr>
        <td><%= post.title %></td>

        <%# 以下を追記 %>
        <% if current_user.liked_by?(post.id) %>
          <td>いいねを外す</td>
        <% else %>
          <td>いいね</td>
        <% end %>
        <td><%= link_to 'Show', post %></td>
        <td><%= link_to 'Edit', edit_post_path(post) %></td>
        <td><%= link_to 'Destroy', post, method: :delete, data: { confirm: 'Are you sure?' } %></td>
      </tr>
    <% end %>
  </tbody>
</table>
<br>
<%= link_to 'New Post', new_post_path %>
「liked_by?(post.id)」は、ユーザーが「いいね」を押しているかどうかを判別するためのメソッドです。このメソッドは次の項目で定義します。

「liked_by?」メソッドの定義

では先ほど記述した「liked_by?」メソッドをモデルに定義しましょう。whereメソッドを使用し、likesテーブルに「post_id」が存在しているかどうか検索をかけています。

# user.rbに以下を追記

def liked_by?(post_id)
  likes.where(post_id: post_id).exists?
end
テーブルとのやりとりに関するメソッドはモデルに置きます。
exists?メソッドは、該当の値があればtrue、なければfalseを返すメソッドです。

いいねを押す

ここまででビューに「いいね」を表示させることができました。しかし、まだリンクを付与していないため「いいね」をクリックすることができません。ここからはいいねを押す、いいねを解除できる機能を実装していきます。

まずはコントローラーの作成から行いましょう。

% rails g controller likes

 

作成したlikesコントローラーにcreateアクションを定義します。createアクションはいいねを押す機能のアクションです。

# likes_controller.rb

class LikesController < ApplicationController
  def create
    Like.create(user_id: current_user.id, post_id: params[:id])
    redirect_to posts_path
  end
end

 

ルーティングを作成しましょう。

# routes.rb

Rails.application.routes.draw do
  devise_for :users
  root 'home#index'
  resources :posts

  # 以下の1行を追記
  post 'like/:id' => 'likes#create', as: 'create_like'
end
rails routesを実行すると「create_like POST /like/:id(.:format) likes#create」が出力されます。
Rails
【Rails基礎】URLを自在にカスタマイズ!ルーティングに名前を指定する方法を解説ルーティングに名前を指定する方法を解説しています。この方法をマスターすることで、自由にパスやURLをカスタマイズできるようになります。ぜひマスターして実装の幅を広げていきましょう。...

 

「いいね」にリンクを付与するため、ビューを編集しましょう。

<%# views/posts/index.html.erb %>

<td>いいね</td>

↓ 以下のように編集

<td><%= link_to 'いいね', create_like_path(post), method: :POST %></td>

 

ここまでの実装で「いいね」をクリックすることができるようになりました。

いいねを解除する

続いて、いいねを解除する機能を実装していきます。

likes_controller.rbにdestroyアクションを定義しましょう。destroyアクションはいいねを解除する機能のアクションです。

# likes_controller.rb

class LikesController < ApplicationController
  def create
    Like.create(user_id: current_user.id, post_id: params[:id])
    redirect_to posts_path
  end

  def destroy
    Like.find_by(user_id: current_user.id, post_id: params[:id]).destroy
    redirect_to posts_path
  end
end

「find_byメソッド」は、複数の検索条件を指定することができるメソッドです。

↓ 「user_id: 1, post_id: 1」を条件に指定した場合

% rails c
irb(main):001:0> Like.find_by(user_id: 1, post_id: 1)
   (0.7ms)  SET NAMES utf8mb4,  @@SESSION.sql_mode = CONCAT(CONCAT(@@sql_mode, ',STRICT_ALL_TABLES'), ',NO_AUTO_VALUE_ON_ZERO'),  @@SESSION.sql_auto_is_null = 0, @@SESSION.wait_timeout = 2147483
  Like Load (2.0ms)  SELECT `likes`.* FROM `likes` WHERE `likes`.`user_id` = 1 AND `likes`.`post_id` = 1 LIMIT 1
=> #<Like id: 11, user_id: 1, post_id: 1, created_at: "2020-07-07 02:42:56", updated_at: "2020-07-07 02:42:56">

 

同様にルーティングも編集しましょう。

# routes.rb

Rails.application.routes.draw do
  devise_for :users
  root 'home#index'
  resources :posts
  post 'like/:id' => 'likes#create', as: 'create_like'

  # 以下の1行を追記
  delete 'like/:id' => 'likes#destroy', as: 'destroy_like'
end
rails routesを実行すると「destroy_like DELETE /like/:id(.:format) likes#destroy」が出力されます。

 

「いいねを外す」にリンクを付与するため、ビューを編集しましょう。

<%# views/posts/index.html.erb %>

<td>いいねを外す</td>

↓ 以下のように編集

<td><%= link_to 'いいねを外す', destroy_like_path(post), method: :DELETE %></td>

 

これでいいねを解除することができるようになりました。

挙動確認

これで「同期いいね」を実装することができました。実際に挙動を確認してみましょう。

Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

実装手順【いいね数の表示】

では次に、いいねが押された数を表示させましょう。

いいね数の取得には「countメソッド」を使用することで簡単に実装することができます。「index.html.erb」を以下のように編集しましょう。

<%# views/posts/index.html.erb %>

<% if current_user.liked_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE %></td>
<% else %>
  <td><%= link_to 'いいね', create_like_path(post), method: :POST %></td>
<% end %>

↓ 以下のように編集

<% if current_user.favorited_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE %> <%= post.likes.count %></td>
<% else %>
  <td><%= link_to 'いいねする', create_like_path(post), method: :POST %> <%= post.likes.count %></td>
<% end %>

 

これで「いいね」の右側に「いいね」の数が表示されるようになりました。

Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

実装手順【非同期いいね】

では続いて、非同期でのいいね機能を実装していきます。ここからやや実装が複雑になってくるので、あらかじめ実装内容を解説します。

まずはそれぞれの投稿を部分テンプレートで切り出します。これは「いいね」もしくは「いいねを外す」を押した瞬間に、JavaScriptでHTML構造を置き換えるためです。

部分テンプレートで切り出す

 

では、どの部分テンプレートを置き換えるのか判別するのでしょうか?

この問題はそれぞれの投稿に異なるidを付与してあげることで解決できます。このidが投稿を判別する指標となります。

どの部分テンプレートを置き換えるのか

 

これらを頭に入れた上で実装に進みましょう。

部分テンプレートの切り出し

まずは「いいね」の箇所を部分テンプレートで切り出します。いいね部分を切り分けることで、その部分だけを変更できるようにします。

<%# app/views/posts/index.html.erb %>

<tbody>
  <% @posts.each do |post| %>
    <tr>
      <td><%= post.title %></td>
      <% if current_user.liked_by?(post.id) %>
        <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE %> <%= post.likes.count %></td>
      <% else %>
        <td><%= link_to 'いいねする', create_like_path(post), method: :POST %> <%= post.likes.count %></td>
      <% end %>
      <td><%= link_to 'Show', post %></td>
      <td><%= link_to 'Edit', edit_post_path(post) %></td>
      <td><%= link_to 'Destroy', post, method: :delete, data: { confirm: 'Are you sure?' } %></td>
    </tr>
  <% end %>
</tbody>

↓以下のように変更

<tbody>
  <% @posts.each do |post| %>
    <tr>
      <%= render 'post', post: post %>
    </tr>
  <% end %>
</tbody>
<%# app/views/posts/_post.html.erb %>

<td><%= post.title %></td>
<% if current_user.liked_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE %> <%= post.likes.count %></td>
<% else %>
  <td><%= link_to 'いいねする', create_like_path(post), method: :POST %> <%= post.likes.count %></td>
<% end %>
<td><%= link_to 'Show', post %></td>
<td><%= link_to 'Edit', edit_post_path(post) %></td>
<td><%= link_to 'Destroy', post, method: :delete, data: { confirm: 'Are you sure?' } %></td>

remote: trueの付与

以下のように、link_toメソッドに「remote: true」を付与します。非同期いいねでは、「remote: true」が必須なので、忘れずに付与させましょう。

<% if current_user.liked_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE %> <%= post.likes.count %></td>
<% else %>
  <td><%= link_to 'いいねする', create_like_path(post), method: :POST %> <%= post.likes.count %></td>
<% end %>

↓ 以下のように編集

<% if current_user.liked_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE, remote: true %> <%= post.likes.count %></td>
<% else %>
  <td><%= link_to 'いいねする', create_like_path(post), method: :POST, remote: true %> <%= post.likes.count %></td>
<% end %>

「remote: true」を付与することで、パラメーターがHTML形式ではなくJS形式で送られるようになります。

今回の場合は「remote: true」をlink_toメソッドに付与することで、likes_controller.rbのcreateアクション後は、views/likes/create.js.erbが呼び出されます。

redirect_toの削除

likes_controller.rbの「redirect_to」の記述を削除しましょう。「redirect_to」を記述すると画面遷移が行われてしまい、非同期処理ができなくなってしまうためです。

また「before_action」を使用して、投稿のidを取得できるようにしましょう。

# likes_controller.rb

class LikesController < ApplicationController
  def create
    Like.create(user_id: current_user.id, post_id: params[:id])
    redirect_to posts_path
  end

  def destroy
    Like.find_by(user_id: current_user.id, post_id: params[:id]).destroy
    redirect_to posts_path
  end
end

↓ 以下のように変更

class LikesController < ApplicationController
  before_action :post_params

  def create
    Like.create(user_id: current_user.id, post_id: params[:id])
  end

  def destroy
    Like.find_by(user_id: current_user.id, post_id: params[:id]).destroy
  end

  private

  def post_params
    @post = Post.find(params[:id])
  end
end

js.erbファイルの作成

では続いて、createアクションとdestroyアクションのjs.erbファイルをそれぞれ作成しましょう。今回はjs.erbファイルがきちんと発火するかどうかを確認するため、alertを記載しておきます。

<%# app/views/likes/create.js.erb %>

alert('いいねが押せている!');
<%# app/views/likes/destroy.js.erb %>

alert('いいねを解除できている!');

 

このように非同期でアラート表示がされれば成功です。

Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

指標の作成(idの付与)

次に部分テンプレートを切り替える部分にidを付与しましょう。具体的には「id=”post_<%= post.id %>”」と記述することで、投稿それぞれ異なるidを付与します。

<%# app/views/posts/index.html.erb %>

  <tbody>
    <% @posts.each do |post| %>
      <tr>
        <%= render 'post', post: post %>
      </tr>
    <% end %>
  </tbody>

↓ idを付与

  <tbody>
    <% @posts.each do |post| %>
      <tr id="post_<%= post.id %>">
        <%= render 'post', post: post %>
      </tr>
    <% end %>
  </tbody>

 

これで部分テンプレートを切り替えるための指標を作ることができました。

js.erbファイルの編集

では部分テンプレートの切り替えができるように、それぞれのjs.erbファイルを編集しましょう。「innerHTMLメソッド」を使用することで、特定のHTML要素を置き換えることができます。

<%# app/views/likes/create.js.erb %>

document.getElementById('post_<%= @post.id %>').innerHTML = '<%= j(render @post) %>'
<%# app/views/likes/destroy.js.erb %>

document.getElementById('post_<%= @post.id %>').innerHTML = '<%= j(render @post) %>'

「j」とは「escape_javascriptメソッド」の省略形で、部分テンプレート内の改行をエスケープ処理してくれます。

省略せず、以下のように記述することもできます。

document.getElementById('post_<%= @post.id %>').innerHTML = '<%= escape_javascript(render @post) %>'

挙動確認

ここまでの実装で「非同期いいね」が実装できました。

Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

実装手順【アイコン使用】

ここからはTwitterやInstagramのような、アイコンを用いたいいね機能を実装していきます。アイコンにはFontAwesomeを使用します。

FontAwesome:https://fontawesome.com/

FontAwsomeの導入

まずはFontAwesomeの導入から行います。詳しくは解説しませんので、手順通り進めていきましょう。

まずはGemの導入です。

# Gemfileに以下を追記

gem 'font-awesome-sass'
% bundle install

 

続いて「application.css」を「application.scss」に変更します。その後以下のコードを追記しましょう。

// application.scssに以下の2行を追記(既存のコードは消さないでください)

@import "font-awesome-sprockets";
@import "font-awesome";

 

これでコード内でFontAwesomeを使用することができるようになりました。

Rails6でのFontAwesomeの導入は、以下の記事を参考にしてください。

Rails
【Rails】Rails6でFontAwesomeを導入・表示させるための手順を初心者向けに解説Rails6でFontAwesomeを導入・表示させる手順について初心者向けに解説しています。Rails6ではWebpackerというパッケージを使用することにより、以前よりグッと簡単にFontAwesomeを導入することができるようになりました。ぜひこの機会に導入を検討してみてください。...

アイコンの表示

次にアイコンをビュー上で表示させましょう。「いいね」と「いいね解除」を区別するため、それぞれのアイコンに「like-btn」と「unlike-btn」というクラス名を付与しています。

また、link_toメソッドにも「like-link」というクラスを付与している点にも注意してください。

<%# app/views/posts/_post.html.erb %>

<td><%= post.title %></td>
<% if current_user.liked_by?(post.id) %>
  <td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE, remote: true %> <%= post.likes.count %></td>
<% else %>
  <td><%= link_to 'いいねする', create_like_path(post), method: :POST, remote: true %> <%= post.likes.count %></td>
<% end %>
<td><%= link_to 'Show', post %></td>
<td><%= link_to 'Edit', edit_post_path(post) %></td>
<td><%= link_to 'Destroy', post, method: :delete, data: { confirm: 'Are you sure?' } %></td>

↓ 以下のように編集

<td><%= post.title %></td>
<% if current_user.liked_by?(post.id) %>
  <td>
    <%= link_to destroy_like_path(post), class: "like-link", method: :DELETE, remote: true do %>
      <i class="fa fa-heart unlike-btn"></i>
    <% end %>
    <%= post.likes.count %>
  </td>
<% else %>
  <td>
    <%= link_to create_like_path(post), class: "like-link", method: :POST, remote: true do %>
      <i class="fa fa-heart like-btn"></i>
    <% end %>
    <%= post.likes.count %>
  </td>
<% end %>
<td><%= link_to 'Show', post %></td>
<td><%= link_to 'Edit', edit_post_path(post) %></td>
<td><%= link_to 'Destroy', post, method: :delete, data: { confirm: 'Are you sure?' } %></td>
「link_to do ~~~ end」を使用することで、アイコンがリンク化されます。

デザインの変更

最後にCSSを用いてアイコンの色を変更していきます。

// likes.scss

.like-link {
  text-decoration: none;
}

.like-link:hover {
  background-color: #fff!important;
}

.like-btn {
  font-size: 15px;
  color: #808080;
}
 
.unlike-btn {
  font-size: 15px;
  color: #e54747;
}

Scaffoldでアプリケーションを作成すると、以下のような記述がデフォルトで入ってしまいます。

a {
  color: #000;

  &:visited {
    color: #666;
  }

  &:hover {
    color: #fff;
    background-color: #000;
  }
}

 

アイコンをhoverした際に、背景が黒になってしまうのを避けるため「!important」を使用してコードを上書きしています。

.like-link:hover {
  background-color: #fff!important;
}

挙動確認

これでアイコンでのいいね表示が完成しました。

Image from Gyazo
上記GIFをクリックすると別タブで見ることができます。

参考記事

escape_javascriptメソッド:
https://api.rubyonrails.org/classes/ActionView/Helpers/JavaScriptHelper.html

innerHTMLメソッド:
https://www.nishishi.com/javascript-tips/innerhtml.html

FontAwesomeの導入:
https://qiita.com/tai-fuj/items/fdb129866c03ae44ea93

!importantの使い方:
https://techacademy.jp/magazine/9424

 

 

今回は「同期いいね機能」「いいね数の表示」「非同期いいね機能」「アイコンいいね機能」の4つをそれぞれ解説しました。いいね機能に関してはほぼ網羅したので、ぜひ理解して自身のアプリケーションにも組み込んでみてください。