RSpecの導入と単体テストコードの書き方



目的
* RSpecでテストコードを書く準備をする
* 基本的なテストコードの書き方を理解する
* テストコードの実行方法を理解する

##RSpecでテストコードを書く準備
RspecをGemfileに追加する
Gemfile

```
group :development, :test do
  # Call 'byebug' anywhere in the code to stop execution and get a debugger console
  gem 'byebug', platforms: [:mri, :mingw, :x64_mingw]
  gem 'rspec-rails', '~> 4.0.0' 　　#これを追加する
end
```

ターミナル

```
bundle install
```
Rspecの設定を行う
ターミナル

```
rails g rspec install
```
テストコードをターミナルに可視化するコードを記入

```
.rspec
--format documentation
```
テストコードを記述するファイルを作成する
ターミナル

```
rails g rspec:model user
```
１行目にrequire 'rails_helper' があることを確認

```spec/models/user_spec.rb
require 'rails_helper'
RSpec.describe User, type: :model do
  pending "add some examples to (or delete) #{__FILE__}"
end
```

##テストコードの書き方
###雛形を作成する
どの機能に対してテストコードを作成するかをDescribe を用いて明らかにする
Describeの中身を詳細に記載する際にはItを用いる
Itの中をメソッドごとにグループ分けするため、Exampleを用いる
ExsampleはItメソッドの””ないに記入

```spec/models/user_spec.rb
require 'rails_helper'
RSpec.describe User, type: :model do
  describe "ユーザー新規登録" do
    it "nicknameが空では登録できない" do
      # nicknameが空では登録できないテストコードを記述します
    end
    it "emailが空では登録できない" do
      # emailが空では登録できないテストコードを記述します
    end
  end
end
```

ここで一度テストを実施

ターミナル

```
bundle exec rspec spec/models/user_spec.rb
```

###NIcknameが空の場合を想定する
単体テストコードを実行する際のながれ
・保存するデータのインスタンスを生成する
・インスタンスが保存されるかを確認する
・インスタンスが保存されない場合は挙動が想定通りかを確認する


nicknameが空のインスタンスを作成
valid?によりインスタンスにバリデーションを行うことができる。エラーはfalse、エラーがない場合はtrueを返す。
userにvalid?を行い、present:trueかを確認する。なお、userモデルにはvalidate:nickname ,presence:trueが記述されているものとする

```spec/models/user_spec.rb
Rrequire 'rails_helper'

RSpec.describe User, type: :model do
  describe "ユーザー新規登録" do
    it "nicknameが空だと登録できない" do
      user = User.new(nickname: "", email: "test@example", password: "000000", password_confirmation: "000000")
      user.valid?
    end
    it "emailが空では登録できない" do
    end
  end
end
```

エクスペクテーションにより、挙動が想定通りかを確認する。なお

```
expect().to matcher()
```
expectの()がmatcherの()：引数が挙動が一致しているかを表す。
matcherにはincludeとeqの２種類がある。

```spec/models/user_spec.rb
require 'rails_helper'
RSpec.describe User, type: :model do
  describe "ユーザー新規登録" do
    it "nicknameが空では登録できない" do
      user = User.new(nickname: "", email: "test@example", password: "000000", password_confirmation: "000000")
      user.valid?
      expect(user.errors.full_messages).to include("Nickname can't be blank")
    end
    it "emailが空では登録できない" do
    end
  end
end
```

バリデーションを行なっているため、user.validでfalseが表示されると想定される。
エラー内容はターミナル上でerrors記述し確認する
ターミナル

```
% rails c
[1] pry(main)> user = User.new(nickname: "", email: "test@example", password: "000000", password_confirmation: "000000")
[2] pry(main)> user.valid?
User Exists? (10.4ms)  SELECT 1 AS one FROM `users` WHERE `users`.`email` = BINARY 'test@example' LIMIT 1
=> false
[3] pry(main)> user.errors
=> #<ActiveModel::Errors:0x00007feb3e0120a8
 @base=
  #<User id: nil, email: "test@example", created_at: nil, updated_at: nil, nickname: "">,
 @details={:nickname=>[{:error=>:blank}]},
 @messages={:nickname=>["can't be blank"]}>
```
ターミナルでuser.errors.full_messagesを実行
上記の例に続けて以下を実行すると、エラーメッセージが表示される
ターミナル

```

[4] pry(main)> user.errors.full_messages
=> ["Nickname can't be blank"]
```
上記user.errors.full_messagesとNickname can't be blankが（）の引数となる。

テストコードを実行する
ターミナル

```
bundle exec rspec spec/models/user_spec.rb 
```