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

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

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

Rubyはプログラミング言語のひとつで、オープンソース、オブジェクト指向のプログラミング開発に対応しています。

Ruby on Rails

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

Q&A

解決済

3回答

1021閲覧

NoMethodError in Trainings#indexを解消したい。

syosinsya123

総合スコア3

Ruby

Rubyはプログラミング言語のひとつで、オープンソース、オブジェクト指向のプログラミング開発に対応しています。

Ruby on Rails

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

0グッド

0クリップ

投稿2021/10/11 04:10

前提・実現したいこと

マイページ内のカレンダーで予定をクリックし、予定の詳細を表示させようと考えています。
ですが、NoMethodError in Trainings#indexが表示されてマイページに遷移すらできない状態です。
エラーの該当箇所のパスを"#"にするとマイページに遷移はできるのですが、予定の詳細を見ようとするとNoMethodError in Trainings#indexが表示されます。

発生している問題・エラーメッセージ

NoMethodError in Trainings#index https://gyazo.com/bf63487e5052a718bd92ba903549953e

該当のソースコード

routes.rb

ruby

1Rails.application.routes.draw do 2 devise_for :users 3 root to: "users#index" 4 resources :user do 5 resources :trainings, only: :show 6 end 7 post 'posts', to: 'trainings#create' 8 get 'trainings', to: 'trainings#index' 9end 10

trainings.controller.rb

ruby

1class TrainingsController < ApplicationController 2 before_action :set_user, except: :index 3 def index 4 @trainings = current_user.trainings 5 end 6 7 def show 8 @trainings = current_user.trainings.find(params[:id]) 9 end 10 11 def new 12 @trainings = current_user.trainings 13 end 14 15 def edit 16 @training = current_user.trainings.find(params[:id]) 17 end 18 19 def update 20 @training = current_user.trainings.find(params[:id]) 21 @training.update(update_params) 22 redirect_to trainings_path(@user.id) 23 end 24 25 def create 26 @training = current_user.trainings.new(training_memo) 27 if @training.save 28 redirect_to trainings_path 29 else 30 redirect_to new_training_path 31 end 32 end 33 34 def destroy 35 @trainings = current_user.trainings.find(params[:id]) 36 @trainings.destroy 37 redirect_to trainings_path(@user.id) 38 end 39 40 41 private 42 def training_memo 43 params.permit(:start_time,:title, :content,:user_id) 44 end 45 46 def set_user 47 @user = User.find(params[:id]) 48 end 49 50 def update_params 51 params.require(:training).permit(:start_time,:title, :content,:user_id) 52 end 53end

index.html.erb

ruby

1<head> 2 <meta charset="utf-8"> 3 <meta name="viewport" content="width=device-width, initial-scale=1"> 4 <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bulma@0.9.3/css/bulma.min.css"> 5</head> 6 7<nav class="navbar is-primary" role="navigation" aria-label="main navigation"> 8 <div id="example" class="py-5 navbar-menu"> 9 <div class="navbar-start"> 10 <a class="navbar-item" href="/">Your Training</a> 11 </div> 12 <div class="navbar-end"> 13 <div class="navbar-item"> 14 <% if user_signed_in? %> 15 <%= link_to "ログアウト", destroy_user_session_path, method: :delete %> 16 <%= link_to "マイページ", trainings_path %> 17 <% else %> 18 <%= link_to "ログイン", new_user_session_path, class: "post" %> 19 <%= link_to "新規登録", new_user_registration_path, class: "post" %> 20 </div> 21 <% end %> 22 </div> 23 </div> 24 </div> 25</nav> 26 27<div class="columns"> 28 <div class="column is-three-quarters"> 29 <%= month_calendar events: @trainings do |date, trainings| %> 30 <%= date.day %> 31 <% trainings.each do |training| %> 32 <div> 33 <%= link_to training.title, user_training_path(@trainings.id) %> 34 </div> 35 <% end %> 36 <% end %> 37 </div> 38 <div class="column"> 39 <div class="field"> 40 <%= form_with model: @user, url: "/posts", method: :post, local: true do |f|%> 41 <label class="label">タイトル</label> 42 <%= f.text_field :title %> 43 <label class="label">トレーニング内容</label> 44 <%= f.text_area :content%> 45 <label class="label">トレーニングをした日</label> 46 <%= f.date_select :start_time%> 47 <%= f.submit '記録する'%> 48 <% end %> 49 </div> 50 </div> 51</div>

show.html.erb

ruby

1<%= render partial: 'shared/header' %> 2 3<table class="table"> 4 <thead> 5 <tr> 6 <th>トレーニング名</th> 7 <th>トレーニング内容</th> 8 <th></th> 9 <th></th> 10 </tr> 11 </thead> 12 <tbody> 13 <tr> 14 <td><%= training.title%></td> 15 <td><%= training.content%></td> 16 <td><%=link_to "削除", "#", method: :delete , data: {confirm:"削除しますか?"} ,:class=>"btn03"%></td> 17 <tr> 18 </tbody> 19</table>

試したこと

<%= link_to training.title, user_training_path(@trainings.id) %>

<%= link_to training.title, user_training_path(@user.trainings.id) %>
に修正したり、
<%= link_to training.title, user_training_path(training.id) %>
に変更したりしましたが、解消できませんでした。

補足情報(FW/ツールのバージョンなど)

gem 'rails', '~> 6.0.0'

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

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

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

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

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

maisumakun

2021/10/11 04:16

ルーティングはどのようになっていますか?
guest

回答3

0

<% trainings.each do |training| %> <div> <%= link_to training.title, user_training_path(@trainings.id) %> </div> <% end %>

ここでは何をしたいのですか?
current_userが登録しているtraining各々へのlinkを一つずつ書くのでは?
そうすると渡すIDはeadh loop のその回で着目しているtrainingです。
ですから @trainings.id ではなく training.id
ただそれでも多分エラーがでます。

maisumakun さんの回答にある
user_training_pathがどんな引数を取るのかを確認
はしましたか?

投稿2021/10/11 09:19

winterboum

総合スコア23567

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

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

syosinsya123

2021/10/11 09:30

仰る通り、training各々へのlinkを1つずつ書こうとして記述しております。 引数の確認はrails routesを行い、 user_training GET /user/:user_id/trainings/:id(.:format) trainings#show と確認致しました。 このことからuserのidとtrainingsのidが必要そうだと考えましたが、どのように記述すればエラーが解消できるか分からない状態です。 training.idに変更してリロードしましたが、ActionController::UrlGenerationError in Trainings#index のエラーが出ております。
winterboum

2021/10/11 09:35

rails routing 階層化 あたりで調べてみて
syosinsya123

2021/10/11 09:42

承知しました。ありがとうございます。 もし不明点や解消できなかった場合、再度質問させて頂くかもしれません。 その時はお手数ですが再度ご教授頂けると幸いです。
guest

0

自己解決ではございませんが、maisumakun様、winterboum様から頂いたご教授をもとに調べて以下のように修正した結果、遷移できなくなっていた予定の一覧表示のページと予定の詳細ぺージを表示させることができました。
お二方をベストアンサーにさせて頂きたいところですが、お1人しかできないことが残念です...。
貴重なお時間を割いてご教授頂き、本当にありがとうございました。

routes.rb

ruby

1Rails.application.routes.draw do 2 devise_for :users 3 root to: "users#index" 4 resources :user do 5 resources :trainings, only: [:index, :new, :create] 6 end 7 resources :trainings, only: [:show, :edit, :update, :destroy] 8 post 'posts', to: 'trainings#create' 9 get 'trainings', to: 'trainings#index' 10end

trainings.controller.rb(一部抜粋)

ruby

1class TrainingsController < ApplicationController 2 before_action :set_user, except: [:index, :show, :create] 3 def index 4 @trainings = current_user.trainings 5 end 6 7以下省略

index.html.erb(一部抜粋)

ruby

1<% trainings.each do |training| %> 2 <div> 3 <%= link_to training.title, training_path(training.id) %> 4 </div> 5<% end %> 6 7以下省略

投稿2021/10/11 13:24

編集2021/10/11 13:28
syosinsya123

総合スコア3

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

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

0

ベストアンサー

エラーメッセージのとおりです。@traningsはレコードの集合体(配列のようなもの)ですので、単体のidは取れません。

user_training_pathがどんな引数を取るのかを確認して、適切な引数を与えてください。

投稿2021/10/11 04:18

maisumakun

総合スコア146018

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

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

syosinsya123

2021/10/11 05:39

回答して頂きありがとうございます。 rails routesでルーティングを確認し、userとtrainingsのidが必要そうだと仮説を立てprivateメソッドで@userの情報を取得しているので、user_training_path(@user.trainings.id)と修正してみましたが、undefined method `trainings' for nil:NilClassのエラーが出てしまいました。 この場合はまず@userの情報をきちんと取得できるように修正をし、その後どういった引数を設定するか考えるという流れで修正していくのでしょうか?
maisumakun

2021/10/11 05:54

そうですね、ご提示のエラーは「@userがnil」ということです。
syosinsya123

2021/10/11 06:29

before_actionで@userの情報をshowアクションに渡せていないと考えてはいるのですが、なぜ渡せていないのか見当がつきません...。 以前ご指摘頂いた際にindexアクションに誤って@userの情報が渡ってしまっていると理解できたため、今回もshowアクションで情報の取得ができていると考えたのですが...。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.35%

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

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

質問する

関連した質問