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

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

ただいまの
回答率

88.64%

別のコントローラのインスタント変数をビューに参照したい

解決済

回答 2

投稿 編集

  • 評価
  • クリップ 0
  • VIEW 227

keisuke.F

score 16

お世話になっております。

現在、画像の投稿アプリケーションを作成しています。

解決したい事

ユーザーマイページで、投稿した画像を一覧表示させたい。

仮説

tweetsコントローラのインスタンス変数をusers/show.html.hamlで用いようとしているから

実装した事

usersコントローラのshowアクションに    @images = current_user.image
を付与したら

undefined method `image' 


のエラーが出た。

以上からわからない事

アソシエーションを組んでいるのに、なぜ別テーブルのカラムをコントローラに記述できないのか。

下記がコードです。
tweets.controller.rb

class TweetsController < ApplicationController
  before_action :set_tweet, only: [:edit, :show]

  def index
    @tweets = Tweet.all.order(created_at: :desc).includes(:user)
  end

  def new
    @tweet = Tweet.new
  end

  def create
    Tweet.create(tweet_params)
  end

  def destroy
    tweet = Tweet.find(params[:id])
    tweet.destroy
  end

  def edit
  end

  def update
    tweet = Tweet.find(params[:id])
    tweet.update(tweet_params)
  end

  def show
  end

  private
  def tweet_params
    params.require(:tweet).permit(:name, :image, :text).merge(user_id: current_user.id)
  end

  def set_tweet
    @tweet = Tweet.find(params[:id]) 
  end

end

users.controller.rb

class UsersController < ApplicationController
  def show
    @nickname = current_user.nickname
    @images = current_user.image
  end
end

tweet.rb

class Tweet < ApplicationRecord
  validates :image, presence: true

  mount_uploader :image, ImageUploader

  belongs_to :user
end

user.rb

class User < ApplicationRecord
  # Include default devise modules. Others available are:
  # :confirmable, :lockable, :timeoutable, :trackable and :omniauthable
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :validatable

  validates :email, presence: true, format: { with: /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i }
  validates :password, presence: true, length: {minimum: 7},format: { with: /\A(?=.*?[a-z])(?=.*?\d)[a-z\d]{7,128}+\z/i, message: "は英字と数字両方を含むパスワードを設定してください" }

  has_many :tweets
end

tweets/show.html.haml

= render "header"

.main
  .contents
    .h1.contents__head ○○さんの投稿
    .contents__item
      .contents__item--image{style: "background-image: url(#{@tweet.image});"}
        .info-contents
          %p= Date.today 
          %p= @tweet.name
          %p= @tweet.text
      = link_to 'トップへ戻る', root_path
= render "footer"

users/show.html.haml

.tweetsTitle
  = @user.nickname
  さんの投稿一覧
.contents
  .contents__item
    - @tweets.each do |tweet|
      .contents__item--image{style: "background-image: url(#{tweet.image});"} 

最下部 ↑ users/show.html.hamlのtweet.imageの記述でエラーが出ています。

単純な問題かもしれないですが、ご教授よろしくお願い致します。

追記

問題のusers.controller.rbに記述していた

@images = current_user.tweets.image


image以外のカラムのnameカラムに変更してみました。

@images = current_user.tweets.name

そうしたらエラーが解決しました。
each文の@tweetの定義エラー等が出たので、
現在のusers.controller.rbはこちらになります。

class UsersController < ApplicationController
  def show
    @nickname = current_user.nickname
    @images = current_user.tweets.image
    @tweets = Tweet.all
  end
end

やはり、imageにするとエラーが出ます。
エラー文です。

NoMethodError in UsersController#show
undefined method `image' for #<Tweet::ActiveRecord_Associations_CollectionProxy:0x00007f35acdd8248>
  • 気になる質問をクリップする

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

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

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 2

checkベストアンサー

0

@images = current_user.tweets.image
これがエラーになるのはcurrent_user.tweets が Tweetのインスタンスではなく、その集合体だからです。Tweetには imageがありますが集合体にはないです。

users_controller の show で @tweets = Tweet.all としてviewで
@tweets.each do |tweet| とやるとcurrent_user以外の全ての人のtweetが一覧されてしまいます。
やるなら @tweets = current_user.tweets です。

最下部 ↑ users/show.html.hamlのtweet.imageの記述でエラーが出ています。

これcurrentエラーメッセージを載せてほしいな、、、
ここはどういうhtmlにしたいのでしょう。
.contents__item- ここは <div class="contents__item-">...</div>にしたいのだな、とはわかりますがそのあとの-image{style: "background-image: url(#{tweet.image});"}が????

なお、tweet.image は画像のURLを得たいのだと思いますが、でしたらtweet.image.url ではないかと思います。

投稿

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/08/27 18:57

    指示通りに実装したところ、エラーが出ずに反映されました。

    しかしながら、
    ビューに
    /uploads/tweet/image/11/BB38ACA4-FFB4-4FFB-BC38-6CD144E1BB97.JPG
    /uploads/tweet/image/12/IMG_0533.jpg

    と、画像のurlそのものが表示されてしまいます。

    これcurrentエラーメッセージを載せてほしいな、、、に関しては、私の記述ミスで出た”NoMethodError in Users#show”のエラーです。
    そちらは、書き方のミスで解決済みです。
    ご指示の通り、
    -image{style: "background-image: url(#{tweet.image});"}
    の箇所を、
    tweet.image.url に変更しました。

    キャンセル

  • 2020/08/27 19:06

    image_tagにしたところ、解決できました!!
    ありがとうございました!

    キャンセル

0

@images = current_user.imageに違和感あります

current_user.tweets.image
でしょうか

current_user.tweet.imageかもしれません

いずれにしても

rails c 


コンソールから
同様のインスタンスを作成し、検証してみるのが一番質問者様の理解につながると思います

 追記

current_user.tweets.image
でいいんだと思うんですが、current_user.tweetsが複数あるために

<Tweet::ActiveRecord_Associations_CollectionProxy:0x00007f35b61633c8>
エラーとなっているものと思われます

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2020/08/27 00:53

    current_user.tweets.imageを入力すると、

    undefined method `image' for #<Tweet::ActiveRecord_Associations_CollectionProxy:0x00007f35b61633c8>
    というエラー、

    current_user.tweet.imageに変えると
    undefined method `tweet' for #<User:0x00007f35b59e26a8> Did you mean? tweets tweets=

    という風に出ます...。

    tweetsにすると、imageが定義されていないと言うエラーがですので、tweetsまでは正解で、imageに問題があるのでしょうか?
    間違いなくtweetsテーブルのカラムはimageなのですが...。

    キャンセル

  • 2020/08/27 01:09

    当初
    `current_user.image`
    とされていましたがTweetモデルのカラムということですのでtweet:image= 1:1ですよね?

    キャンセル

  • 2020/08/27 01:37 編集

    imageはテーブルで用意しておらず、tweetテーブルのカラムです。

    tweetsとusersのアソシエーションも組んであります。

    上記に進展を追記しました。
    ご確認をお願いします。

    キャンセル

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

  • ただいまの回答率 88.64%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る