🎄teratailクリスマスプレゼントキャンペーン2024🎄』開催中!

\teratail特別グッズやAmazonギフトカード最大2,000円分が当たる!/

詳細はこちら
Ruby on Rails 6

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

RSpec

RSpecはRuby用のBDD(behaviour-driven development)フレームワークです。

Q&A

解決済

1回答

365閲覧

「管理者が承認していない投稿は見れない」というテストを書きたいです。

KouKuma

総合スコア2

Ruby on Rails 6

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

RSpec

RSpecはRuby用のBDD(behaviour-driven development)フレームワークです。

0グッド

1クリップ

投稿2021/02/21 03:17

前提・実現したいこと

回答者の皆様

現在で駐輪場の検索アプリを作っており、 管理者が承認していない投稿は投稿者以外閲覧ができないという機能を実装しました。
実装後にRspecでテストを書いたのですが、テストが通らず困っております。
解決策等ご教示頂ければと思い、こちらで質問させて頂きます。
お忙しい中誠に恐れ入りますが、ご回答いただけると幸いです。

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

1) Parkings GET /show 投稿者と閲覧者が違うユーザーの場合 投稿が承認されていない場合 ホーム画面にリダイレクトされること Failure/Error: expect(response).to have_http_status(302) expected the response to have status code 302 but it was 200 # ./spec/requests/parkings_request_spec.rb:51:in `block (5 levels) in <top (required)>' 2) Parkings GET /show ログインしていない場合 投稿が承認されていない場合 ホーム画面にリダイレクトされること Failure/Error: expect(response).to have_http_status(302) expected the response to have status code 302 but it was 200

該当のソースコード

spec/requests/parkings_request_spec.rb

require 'rails_helper' RSpec.describe "Parkings", type: :request do # parkingに関してはdestroyアクションをテストする前にデータが保存されていないと # エラーが出たため、let!とした。 let(:user) { create(:user) } let!(:parking) { create(:parking, user_id: user.id) } let(:other_user) { create(:user) } describe "GET /show" do context 'ユーザー本人の投稿の場合、かつ投稿が承認されていない場合' do before do user.confirm sign_in user end it '正常にレスポンスを返すこと' do parking.approval = nil get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿者と閲覧者が違うユーザーの場合' do before do other_user.confirm sign_in other_user end context '投稿が承認されている場合' do it '正常にレスポンスを返すこと' do get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿が承認されていない場合' do it 'ホーム画面にリダイレクトされること' do parking.approval = nil get parking_url(parking) expect(response).to have_http_status(302) expect(response.body).to include '投稿が未承認のため、閲覧できません。' end end end context 'ログインしていない場合' do context '投稿が承認されている場合' do it '正常にレスポンスを返すこと' do get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿が承認されていない場合' do it 'ホーム画面にリダイレクトされること' do parking.approval = nil get parking_url(parking) expect(response).to have_http_status(302) expect(response.body).to include '投稿が未承認のため、閲覧できません。' end end end end end

app/controllers/parkings_controller.rb

class ParkingsController < ApplicationController before_action :authenticate_user!, only: [:new, :create, :edit, :destroy, :update, :search, :favorites, :current_spot_search] before_action :permit_update_delete, only: [:edit, :destroy, :update] before_action :permit_show, only: [:show] def index @parkings = Parking.page(params[:page]).per(10) end def show @parking = Parking.find(params[:id]) # ログインしており、投稿者でない場合かつ投稿が承認されていない場合   if user_signed_in? && @parking.user_id != current_user.id && @parking.approval != 'approval' flash[:notice] = '投稿が未承認のため、閲覧できません。' redirect_to root_path   # ログインしていなくて、かつ投稿が承認されていない場合 elsif !user_signed_in? && @parking.approval != 'approval' flash[:notice] = '投稿が未承認のため、閲覧できません。' redirect_to root_path end end

試したこと

  • parkings_controller.rbを以下のように修正してみた。

→エラーメッセージに変化はなかった。

class ParkingsController < ApplicationController before_action :authenticate_user!, only: [:new, :create, :edit, :destroy, :update, :search, :favorites, :current_spot_search] before_action :permit_update_delete, only: [:edit, :destroy, :update] before_action :permit_show, only: [:show] def index # @parkings = Parking.where(approval: 1).page(params[:page]).per(10) @parkings = Parking.page(params[:page]).per(10) end def show @parking = Parking.find(params[:id]) end private def permit_show @parking = Parking.find(params[:id]) if user_signed_in? && @parking.user_id != current_user.id && @parking.approval != 'approval' flash[:notice] = '投稿が未承認のため、閲覧できません。' redirect_to root_path elsif !user_signed_in? && @parking.approval != 'approval' flash[:notice] = '投稿が未承認のため、閲覧できません。' redirect_to root_path end end end
  • ブラウザで動作確認を行った。

→ブラウザでは問題なく動作した。

  • システムスペックの変更

→下記のように変更したら、エラーメッセージが変わった。
spec/requests/parkings_request_spec.rb

require 'rails_helper' RSpec.describe "Parkings", type: :request do # parkingに関してはdestroyアクションをテストする前にデータが保存されていないと # エラーが出たため、let!とした。 let(:user) { create(:user) } let!(:parking) { create(:parking, user_id: user.id) } let(:other_user) { create(:user) } describe "GET /show" do context 'ユーザー本人の投稿の場合、かつ投稿が承認されていない場合' do before do user.confirm sign_in user end it '正常にレスポンスを返すこと' do parking.approval = nil get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿者と閲覧者が違うユーザーの場合' do before do other_user.confirm sign_in other_user end context '投稿が承認されている場合' do it '正常にレスポンスを返すこと' do get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿が承認されていない場合' do it 'ホーム画面にリダイレクトされること' do parking.approval = nil get parking_url(parking) expect(response.body).to include '投稿が未承認のため、閲覧できません。' end end end context 'ログインしていない場合' do context '投稿が承認されている場合' do it '正常にレスポンスを返すこと' do get parking_url(parking) expect(response).to have_http_status(200) end end context '投稿が承認されていない場合' do it 'ホーム画面にリダイレクトされること' do parking.approval = nil get parking_url(parking) expect(response.body).to include '投稿が未承認のため、閲覧できません。' end end end end end

変更後のエラーメッセージ

2) Parkings GET /show ログインしていない場合 投稿が承認されていない場合 ホーム画面にリダイレクトされること Failure/Error: get parking_url(parking) expected "<!DOCTYPE html>\n<html class=\"w-full\">\n <head>\n <title>Myapp</title>\n <meta name=\"viewp... sm:text-xl\">Copyright©. All Rights Reserved.</p>\n</footer> \n </body>\n</html>\n" to include "投稿が未承認のため、閲覧できません。" # 以下、投稿詳細ページのhtmlがエラーメッセージに表示されていた。

どうやらリダイレクトされずに投稿詳細ページが読み込まれてしまっているらしい、、、
→つまり、原因はシステムスペックに存在する??

おそらくシステムスペックの書き方に原因があるということまでは絞り込めたのですが、そこからどうコードを変えていくかというところで詰まってしまいました。
「Failure/Error: expect(response).to have_http_status(302)」で検索をしたのですが、解決に繋がる記事を見つけることができませんでした。

何か不足している情報等ございましたらご連絡いただけると幸いです。
お忙しい中誠に恐れ入りますが、ご回答の程宜しくお願い致します。

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

  • Ruby 2.6.6
  • Rails 6.1.0
  • Rspec-rails 4.0.2

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

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

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

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

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

guest

回答1

0

ベストアンサー

parking.approval = nil これは読み込まれた parking の状態を変更していますが、DBのデータの状態は変化ありません、
parking.update(approval: nil) とすれば通るでしょう。

let (un_approved_parking) てのを用意したほうが分かりやすいかも

投稿2021/02/21 09:55

winterboum

総合スコア23567

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

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

KouKuma

2021/02/21 11:04

winterboum様 お世話になっております。 DB内のデータの状態を変化させる必要があったとのことで、ご指摘いただいたようにテストを書き直したら無事に通りました! 前回に引き続き、今回もご回答いただき誠にありがとうございました!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

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

ただいまの回答率
85.36%

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

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

質問する

関連した質問