$ yarn add @fortawesome/fontawesome-free
require("scripts")
import "@fortawesome/fontawesome-free/css/all.css"
,在node-modules找<%= link_to "<i class='far fa-thumbs-up'></i>",'#'%>
.html_safe
<%= link_to "<i class='far fa-thumbs-up'></i>".html_safe,'#'%>
<% link_to favorite_post_path(@post), method: 'post' do %>
require('./post')
接下來要想辦法讓JS可以取到文章的id,用data: { id: @post.id }
(當中的id:可以自取名字name:,會形成data-name="#"),將post_id帶給link_to,寫成
<%= link_to '#',id: 'favorite_btn', data: { id: @post.id } do %>
可以做出data-id="7"
console.log(e.currentTarget)
可以印出發生的事件的對象,這裡是favorite_btn
console.log(e.currentTarget.dataset)
加上dataset可以印出全部的data-name
console.log(e.currentTarget.dataset.id)
加上.name(這裡是要id)可以印出指定的data-name
$ yarn add axios
const postId = e.currentTarget.dataset.id
/posts/${postId}/favorite
,在JS中帶變數要用 'esc下方的特殊符號' 包住這樣就完成token的放入
建立一個新的model來處理按讚
$ rails g model FavoritePost user:belongs_to post:belongs_to
確認migration沒問題再建立表格
$ rails db:migrate
在post.rb與user.rb加上
has_many :favorite_posts
到目前為止建立了post與favorite_post以及user與favorite_post之間的關聯,但實際上我們需要的是user與post的關聯,透過favorite_post就可以建立兩者之間的關聯
在post.rb加上
has_many :users, through: :favorite_posts
但是在post.rb已經有belongs_to :user,為了避免混淆可以改寫users
(這裡的users只會做出一個方法並不是真的model所以可以自由改名稱)
has_many :favorite_users, through: :favorite_posts
在user.rb加上
has_many :posts, through: :favorite_posts
posts也與原有的has_many :posts衝突,所以也改名稱
has_many :my_favorites, through: :favorite_posts
在rails c中測試
這裡會出現錯誤,因為我們把原來的users改掉,rails無法判斷要找尋的對象,要再加上一個source給它來源變成
has_many :favorite_users, through: :favorite_posts, source: 'user'
source後面可以用字串'user'或符號:user,不能用'User'
has_many :my_favorites, through: :favorite_posts, source: 'post'
就變成
*修改show.html.erb
目前的post.js會在application.js中用require("scripts")引入,所以全部地方都會執行,雖然我們有檢查按鈕存在才執行,但萬一有出現一樣名稱favorite_btn的按鈕就會衝突
可以在app/views/layouts/application.html.erb的<body>加上類別,讓頁面的body變得可區分
< body class="<%= controller_name %>-<%= action_name %>">
原來post.js的按鈕監聽加上.posts-show的class
就可以避免監聽到其他的同名稱按鈕(如果有的話)
前置作業
將app/frontend/scripts/index.js的require('./post')註解掉關閉本來post.js的功能
先安裝stimulus,會出現在package.json的清單中,同時在javascripts資料夾底下增加一個controllers的資料夾,還會在app/frontend/packs/application.js裡import "controllers"
$ rails webpacker:install:stimulus
將app/views/posts/show.html.erb的h2標籤加上data-controller="名稱",會去呼叫app/frontend/controllers/名稱_controller.js
<h2 data-controller="favorite">
就會去呼叫favorite_controller.js
因為post.js已經關閉,所以show.html.erb本來提供給它用的id: 'favorite_btn'
就可以清掉,並為圖示加上data-target="favorite.icon
,link_to加上action: 'favorite#go'
target用.連接目標名稱,action用#連接方法
this.data.get
去抓取controller的資料,這裡我們要的是id,同樣用console.log印出id來檢查其中這兩行不需要
另外id已經抓出來了,所以${postId}
可以改為${id}
import ax from 'axios'
來取代const ax = require('axios')
import { Controller } from "stimulus"
import ax from 'axios'
因為現在的this指的是function(resp)本身,也就是
iconTarget其實不存在這之中,所以會undefind
function(resp)改成fat arrow(胖箭頭)寫法,因為function本身會有scope會擋住,fat arrow沒有自己的this所以會向外找iconTarget