iT邦幫忙

2023 iThome 鐵人賽

DAY 19
0
SideProject30

placeholder系列 第 19

30天打造線上多人桌遊網站-Day 19-加入RSpec

  • 分享至 

  • xImage
  •  

0. 前情提要

昨天我們寫了 Game Class 準備將 chat_room_channel.rb 的遊戲處理邏輯搬出來。

在改動一個原本功能正常的程式碼時,要如何確保改完不會影響既有的功能?

我們可以利用測試來驗證程式仍然運作正常

以下我們使用 RSpec 來撰寫測試案例,讓我們可以安心重構程式碼,改壞時能夠第一時間處理,減少出現 Bug 炸到使用者的情況 XD

1. 安裝 RSpec

https://rspec.info/

https://github.com/rspec/rspec-rails

選擇安裝整合好 Rails 的 rspec-rails

$ bundle add rspec-rails

$ rails generate rspec:install

2. 新增一個測試

可以用 RSpec generator 產生 spec

$ rails generate rspec:model Game

# create spec/models/game_spec.rb

產生的內容

require 'rails_helper'

RSpec.describe Game, type: :model do
  pending "add some examples to (or delete) #{__FILE__}"
end

執行測試

$ rspec

https://ithelp.ithome.com.tw/upload/images/20231006/20150987OnttWGivye.png

3. 增加測驗項目(規格)

在遊戲物件初始化時,會從 GameRoomgame_data 拿出資料,組成 Game 的實體。

一個 Game 應該要有

  1. 名稱
  2. 模式
  3. 狀態
  4. 參與的玩家
  5. 資料庫的ID

其中狀態(state)表示遊戲正處於哪個階段

STATE = {
    GAME_INIT: 0,
    GAME_PROCESSING: 1,
    GAME_ENDING: 2,
    GAME_COMPLETED: 3
}

GAME_INIT 時,
遊戲

  1. 應該要有名稱
  2. 應該要有模式
  3. 狀態應該是 STATE[GAME_INIT]
  4. 參與的玩家應該 >= 1
  5. 應該要有資料庫的ID

據此

來撰寫我們的 game_spec.rb

RSpec.describe Game, type: :model do
  context "#new" do
    let(:game_room) { GameRoom.create(name: "new game", game_data: {}) }
    let(:game) { Game.new(game_room) }

    it "要有名稱" do
      expect(game.name).to be_truthy
    end

    it "要有模式" do
      expect(game.mode).to be_truthy
    end

    it "狀態是 `STATE[GAME_INIT]`" do
      expect(game.state).to eq Game::STATE[:GAME_INIT]
    end

    it "參與的玩家 >= 1" do
      expect(game.players.size).to be >= 1
    end

    it "要有資料庫的ID" do
      expect(game.id).to be_truthy
    end
  end
end

跑看看測試

https://ithelp.ithome.com.tw/upload/images/20231006/20150987KPGzvDhfkE.png

4. 修改程式碼, 目標通過測試

app/models/game.rb

+ MODE = {
+   "基本 5 色": 0,
+   "6 色 10 張": 1,
+   "6 色 5 張": 2,
+   "彩色": 3,
+ }

- attr_accessor :name, :state, :game_room_id, :game_room
+ attr_accessor :id, :name, :mode, :players, :state, :game_room_id, :game_room

- @name = params.dig :name
- @players = []
+ @id = game_room.id
+ @name = game_room.name
+ @mode = params.dig "mode"
+ @players = params.dig "players"

在建立遊戲時,傳入建立的玩家作為第一個玩家

spec/models/game_spec.rb

+ let(:host) { SecureRandom.urlsafe_base64 }
- let(:game_room) { GameRoom.create(name: "new game") }
+ let(:game_room) { GameRoom.create(name: "new game", game_data: {mode: 0, players: [host]}) }

https://ithelp.ithome.com.tw/upload/images/20231006/20150987gl1nh4CKNb.png

順利通過啦

$ rspec --help
Usage: rspec [options] [files or directories]

    -f, --format FORMATTER           Choose a formatter
                                       [p]rogress (default - dots)
                                       [d]ocumentation (group and example names)
                                       [h]tml
                                       [t]extmate
                                       custom formatter class name

可以使用 rspec -fd 獲得每項測試的說明

https://ithelp.ithome.com.tw/upload/images/20231006/20150987VOPoofMnjq.png

5. 結語

慢慢將遊戲邏輯搬出來


Demo url -> https://ironman2023-hanabi.zeabur.app/


上一篇
30天打造線上多人桌遊網站-Day 18-PORO
下一篇
(TBD)30天打造線上多人桌遊網站-Day-20-建立玩家模組
系列文
placeholder20
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

1 則留言

0
Mike_Lai
iT邦新手 4 級 ‧ 2023-10-05 22:33:36

痾... 我不小心把你的遊戲房間刪掉了.......
我以為是我在前幾天建立的房間..............

noracami iT邦新手 2 級 ‧ 2023-10-06 00:08:53 檢舉

XDD
沒擋就是開放給大家玩的 /images/emoticon/emoticon61.gif

我要留言

立即登入留言