質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Ruby on Rails 6

Ruby on Rails 6は、オープンソースのWebアプリケーションフレームワークです。「同じことを繰り返さない」というRailsの基本理念のもと、他のフレームワークより少ないコードで簡単に開発できるよう設計されています。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

非同期処理

非同期処理とは一部のコードを別々のスレッドで実行させる手法です。アプリケーションのパフォーマンスを向上させる目的でこの手法を用います。

Q&A

解決済

2回答

2697閲覧

jsで非同期通信を使ったいいね機能を実装したいのですが、Processing by ActiveStorage::DiskController#show as JPEG

kawasaki4563

総合スコア32

Ruby on Rails 6

Ruby on Rails 6は、オープンソースのWebアプリケーションフレームワークです。「同じことを繰り返さない」というRailsの基本理念のもと、他のフレームワークより少ないコードで簡単に開発できるよう設計されています。

JavaScript

JavaScriptは、プログラミング言語のひとつです。ネットスケープコミュニケーションズで開発されました。 開発当初はLiveScriptと呼ばれていましたが、業務提携していたサン・マイクロシステムズが開発したJavaが脚光を浴びていたことから、JavaScriptと改名されました。 動きのあるWebページを作ることを目的に開発されたもので、主要なWebブラウザのほとんどに搭載されています。

非同期処理

非同期処理とは一部のコードを別々のスレッドで実行させる手法です。アプリケーションのパフォーマンスを向上させる目的でこの手法を用います。

0グッド

0クリップ

投稿2021/04/01 02:30

編集2021/04/06 11:38

以下のサイトを参考にして非同期通信を使ったいいね機能を実装しようと思ったのですが、エラーの解決ができません。
【Rails】いいね機能完全版!同期いいね、いいね数の表示、非同期いいね、アイコン表示、それぞれの実装方法についてまとめて解説

CREATE 500 internal server rails-ujs.js:216 error

とコンソールに出てきます(検証ツール)

原因としては、javasctiptで返さないといけないのにHTMLで返されてしまっているからだと考えました。
なのでいいね機能を実装しているコントローラーを

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

#問題のソースコード

ルーティング

Rails.application.routes.draw do devise_for :users resources :movies do resources :movie_comments, only: %i[create destroy] end resources :posts do resources :comments, only: %i[create destroy] end post 'like/:id', to: 'likes#create', as: 'create_like' delete 'like/:id', to: 'likes#destroy', as: 'destroy_like' post 'movie_like/:id', to: 'movie_likes#create', as: 'create_movie_like' delete 'movie_like/:id', to: 'movie_likes#destroy', as: 'destroy_movie_like' root 'posts#index' end

いいね機能に関する部分テンプレート(_like.html.erb)

<% if user_signed_in? %> <div class="like"> <h3>いいね件数: <%= post.likes.count %></h3> <div class = 'like-button'> <% if current_user.liked_by?(post.id) %> <td><%= link_to 'いいねを外す', destroy_like_path(post), class: "like-link", method: :DELETE,remote: true %></td> <i class="fa fa-heart unlike-btn"></i> <% else %> <td><%= link_to 'いいね', create_like_path(post), class: "like-link", method: :post, remote: true %></td> <i class="fa fa-heart like-btn"></i> <% end %> </div> </div> <% end %>

いいね機能(ajax)部分に関するテンプレート
名前:create.js.erb

document.getElementById('post_<%= @post.id %>').innerHTML = '<%= j(render @post) %>' alert('いいねが押せている!');

同じくいいね機能(ajax)部分に関するテンプレート
名前:destroy.js.erb

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

alertは確認のために載せているので、後々削除します

投稿一覧のコード

<div class="content-wrapper"> <div class="content-block"> <% @posts.each do |post| %> <div class="content"> <div class="user-about"> <div class="image"> <% if post.user.image.attached? %> <%= image_tag post.user.image %> <% else %> <%= image_tag 'no.user.png' %> <% end %> </div> <div class="profile"> <div class="name-history"> <div class="name"> <%= post.user.nickname %> </div> <div class="mania-histry"> <%= "学習歴:#{post.user.mania_histry}年" %> </div> </div> <div class="enjoy-point"> <%= "楽しいポイント#{post.user.enjoy_point}"%> </div> </div> </div> <div class="text"> <p><%= post.content %></p> </div> <% if post.images.attached? %> <% post.images.each do |image| %> <div class = 'images'> <%= image_tag image, class: "content-image" %> </div> <% end %> <% end %> <div class="action-menu"> <tr id="post_<%= post.id %>"> <%= render 'post', post: post %> </tr> <div class="comment"> <h3>コメント件数: <%= post.comments.count %></h3> <%= link_to "コメントする", "/posts/#{post.id}", class: "comment-buttom" %> </div> <%if user_signed_in?%> <% if current_user.id == post.user.id %> <%= link_to "編集", edit_post_path(post) %> <%= link_to "削除", post_path(post), method: :delete %> <% end %> <% end %> </div> </div> <% end %> </div> <div class="sidebar"> <%= render 'shared/menu'%> </div> </div>

##続いていいね機能に関するコントローラーです

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

##続いていいね機能に関するモデルです

class Like < ApplicationRecord belongs_to :user belongs_to :post end

いいねするユーザーに関するモデルです

class User < ApplicationRecord # Include default devise modules. Others available are: # :confirmable, :lockable, :timeoutable, :trackable and :omniauthable devise :database_authenticatable, :registerable, :recoverable, :rememberable, :validatable has_one_attached :image has_many :posts has_many :likes has_many :movielikes has_many :comments, dependent: :destroy has_many :movies def liked_by?(post_id) likes.where(post_id: post_id).exists? end with_options presence: true do validates :nickname validates :mania_histry validates :enjoy_point validates :email validates :password, length: { minimum: 6 } end validate :image_presence def image_presence if image.attached? if !image.content_type.in?(%('image/jpeg image/png')) errors.add(:image, 'にはjpegまたはpngファイルを添付してください') end else errors.add(:image, 'ファイルを添付してください') end end end

#エラーログ

method: postに変更しました

Started DELETE "/like/2" for 172.24.0.1 at 2021-04-06 01:31:40 +0000 web_1 | Cannot render console from 172.24.0.1! Allowed networks: 127.0.0.0/127.255.255.255, ::1 web_1 | Processing by LikesController#destroy as JS web_1 | Parameters: {"id"=>"2"} web_1 | Post Load (0.6ms) SELECT `posts`.* FROM `posts` WHERE `posts`.`id` = 2 LIMIT 1 web_1 | ↳ app/controllers/likes_controller.rb:15:in `post_params' web_1 | User Load (0.7ms) SELECT `users`.* FROM `users` WHERE `users`.`id` = 1 ORDER BY `users`.`id` ASC LIMIT 1 web_1 | ↳ app/controllers/likes_controller.rb:9:in `destroy' web_1 | Like Load (0.8ms) SELECT `likes`.* FROM `likes` WHERE `likes`.`user_id` = 1 AND `likes`.`post_id` = 2 LIMIT 1 web_1 | ↳ app/controllers/likes_controller.rb:9:in `destroy' web_1 | (0.3ms) BEGIN web_1 | ↳ app/controllers/likes_controller.rb:9:in `destroy' web_1 | Like Destroy (0.7ms) DELETE FROM `likes` WHERE `likes`.`id` = 6 web_1 | ↳ app/controllers/likes_controller.rb:9:in `destroy' web_1 | (2.4ms) COMMIT web_1 | ↳ app/controllers/likes_controller.rb:9:in `destroy' web_1 | Rendering likes/destroy.js.erb web_1 | (0.7ms) SELECT COUNT(*) FROM `likes` WHERE `likes`.`post_id` = 2 web_1 | ↳ app/views/posts/_post.html.erb:3 web_1 | Like Exists? (0.9ms) SELECT 1 AS one FROM `likes` WHERE `likes`.`user_id` = 1 AND `likes`.`post_id` = 2 LIMIT 1 web_1 | ↳ app/models/user.rb:16:in `liked_by?' web_1 | Rendered posts/_post.html.erb (Duration: 10.5ms | Allocations: 1795) web_1 | Rendered likes/destroy.js.erb (Duration: 13.8ms | Allocations: 2045) web_1 | Completed 200 OK in 42ms (Views: 15.0ms | ActiveRecord: 7.1ms | Allocations: 6942)

#ソースコードを表示をした結果

イメージ説明

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答2

0

自己解決

解決できました。

<tr id="post_<%= post.id %>">   <%= render 'post', post: post %> </tr>

のtrをdivに変えたら実装できました。

投稿2021/04/07 01:18

kawasaki4563

総合スコア32

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

0

ActionController::UnknownFormat in LikesController#create
LikesController#create is missing a template for this request format and variant. request.formats: ["text/html"] request.variant: []

html を返すビューファイル(create.html.erb)がないため、エラーになってるように見えます。
なぜ html なのかというと、リンクが remote: true になっていないからです。

_like.html.erb

erb

1<td><%= link_to 'いいね外す', destroy_like_path(post), method: :DELETE, remote: true %></td> 2 3<td><%= link_to 'いいねする', create_like_path(post), method: :POST, remote: true %></td>

ArgumentError in LikesController#create
too few arguments

format.json が原因だと思います。この行は多分意味がないので削除してみましょう。

投稿2021/04/04 11:03

neko_daisuki

総合スコア2090

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

kawasaki4563

2021/04/05 01:41

回答ありがとうございます やってみたのですが、`500 internal server error`となってしまいました console.log(@post.id)とやってみても反応はありませんでした
neko_daisuki

2021/04/05 02:13

エラーの詳細を教えてください。 あやしいのは ・アクション(create/destroy)で@postを設定していないのに view で @post を参照している ・render @post としてますが、これは posts/_post.html.erb を指しているのでは
kawasaki4563

2021/04/05 02:29

ありがとうございます。 コードを修正したので、質問自体を編集します
neko_daisuki

2021/04/06 00:33

rails がエラーを出してるはずですので、そのログを張り付けてください。
kawasaki4563

2021/04/06 01:30 編集

コメント本当にありがとうございます。 エラーログの方貼り付けました。
neko_daisuki

2021/04/06 01:26

create というHTTP リクエストメソッドがないのでエラーになってます。 <td><%= link_to 'いいね', create_like_path(post), class: "like-link", method: :create, remote: true %></td> method: :post に変更してください。 <td><%= link_to 'いいね', create_like_path(post), class: "like-link", method: :post, remote: true %></td>
kawasaki4563

2021/04/06 02:02 編集

postに変えても変わらないですね。ただエラーログに変化はありました。 そして新たにわかったことなのですが、一度リロードすると表示に変化ありました。 ですが未だにできないですね。非同期通信のいいね機能
kawasaki4563

2021/04/06 02:34

今試しに `alert('いいねが押せている!');` を入れてみたのですが、起動していないので、リクエストの処理ができていないみたいです
neko_daisuki

2021/04/06 02:38

create.js.erb で ID like_<%= @post.id %> を書き換えようとしていますが、これが view に見当たりません。 destroy.js.erb と同じように post_<%= @post.id %> に書き換えてみてください。
kawasaki4563

2021/04/06 03:11

最後のrenderの部分も変えてみたのですが、post_<%= post.id %>にしても解消はできないですね。
neko_daisuki

2021/04/06 04:46

ブラウザのコンソールにはエラーが出ていませんか?
kawasaki4563

2021/04/06 08:33 編集

Uncaught TypeError: Cannot set property 'innerHTML' of null となってますので、リクエストで、post_idが送られていないのかな?って思ってます レス遅くなってすいません
neko_daisuki

2021/04/06 09:12

ブラウザが create.js.erb(destroy.js.erb) の内容を実行しようとして post_<%= post.id %>(あるいは like_<%= @post.id %>)という ID の要素が見つからないため、 そのエラーになってるんだと思います。 つまり、リクエスト→レスポンス は上手くいっていて、javascript の実行でエラー。
neko_daisuki

2021/04/06 09:14

tr の中に <%= render 'post', post: post %> とありますが、 この render 'post' っていうのは _like.html.erb なんでしょうか? _like.html.erb を見ると、td の外に div があったりして その辺がよく分からないです。
kawasaki4563

2021/04/06 09:54 編集

コメントありがとうございます _like.html.erbを_post.html.erbにサイト道理に改名してみました。 よく見たらサイトと違っていることに気がついたので。 そうして一度ブラウザをリロードしてやってみたのですがエラーは Uncaught TypeError: Cannot set property 'innerHTML' of null になっています
kawasaki4563

2021/04/06 10:02

検証ツールで一度調べてみたのですが、 document.getElementById('post_2').innerHTML = ' <div class=\"like\">\n <h3>いいね件数: 1</h3>\n <div class = \'like-button\'>\n <td><a class=\"like-link\" data-remote=\"true\" rel=\"nofollow\" data-method=\"DELETE\" href=\"/like/2\">いいねを外す</a></td>\n <i class=\"fa fa-heart unlike-btn\"></i>\n\n </div>\n </div>\n ' となってますね。これ一体何なんだろうと思って推測してみたのですが、やっぱりidが渡されてないことを示していると感じますね。
neko_daisuki

2021/04/06 11:12

そのエラーは document.getElementById('post_[id]') が null だと言ってます。 「投稿一覧のコード」を見ると、<tr id="post_<%= post.id %>">としているので null のはずがないんですが、 一度ブラウザの「ページのソースを表示」からソースを確認して post_[id] が指定された要素があるか確認してみてください。
kawasaki4563

2021/04/06 11:27

了解です。 やってみます
kawasaki4563

2021/04/06 11:30

<tr id="post_1">となってたので、指定された要素はありますね 一旦ソースコード全部更新してみます。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問