昨天的測試沒有通過,下面是錯誤的訊息:
到底發生了什麼?該怎麼讓它通過?那串紅色的字看起來就很不順眼,快點來通過它
閱讀錯誤到通過測試
來看看測試指出錯誤的地方在哪,首先是這串:
Failure/Error: burger = Burger.new('Big mac')
但好像沒有告訴我們錯在哪裡耶?再往下看
NameError:
uninitialized constant Burger
他的意思是並沒有初始化一個常數 Burger
這是一個在寫 Ruby 非常常見的錯誤訊息。
此刻我們需要擁有一個類別,然後呼叫 initialize
這個方法,這樣才可以生出 burger
這個物件!
至於要寫在哪裡呢?其實可以直接寫在測試的上面,但這並不是一個好方法,寫測試的時候會希望把每個檔案分開的放置,這樣看起來才專業啊
現在這是我們的檔案結構,明顯地可以理解到 burger_spec.rb
就是拿來測試 burger.rb
這個檔案的!
接著在 burger.rb
中寫入:
class Burger
end
再輸入一次 rspec spec/burger_spec.rb
,看看錯誤的訊息是什麼?
雖然錯誤的還是同一行,但內容已經不一樣了,繼續來解決這個問題,系統說給予的參數是錯誤的,代表說需要在類別初始化的時候加入參數,來讓這個錯誤訊息通過,實作吧!
class Burger
def initialize(type)
@type = type
end
end
好的,一樣再執行一次 rspec spec/burger_spec.rb
通常看到錯誤訊息有所改變的時候,都會覺得鬆一口氣的感覺,至少不是無頭蒼蠅,有一個方向的感覺
因為又更近了一步了!代表每一次的改動都有正中紅心,也有根據錯誤訊息來做正確的改動!
這次的錯誤也是很常見的 NoMethodError
意指沒有 type
這個方法
事實上在 Ruby 的世界裡都是物件,而取值也會是物件的其中一個方法,包括設置值也是!
class Burger
def initialize(type)
@type = type
end
def type # 這個是取值的方法
@type
end
def type=(type) # 這個是賦值的方法
@type = type
end
end
來看看把取值的方法加上去之後會發生什麼事情吧?
成功啦!我們通過這次的測試了!
但別高興得太早,還記得 TDD 測試中通過綠色後要進行的環節嗎?
沒錯,就是重構的部分,這也是非常重要的!
這時候回頭看一下我們 測試碼
以及 真實程式碼
有沒有什麼需要改進的地方。
測試的部分因為只有兩行,好像沒什麼可以縮減的部分了,我們就看看 真實程式碼
!
關於取值、賦值兩個方法,Ruby 其實有提供更便捷的方式來用,不需要這樣子寫到六行,來重構看看這段程式碼!
class Burger
attr_accessor :type
def initialize(type)
@type = type
end
end
這個的效果,和原先寫的方式是一樣的!但礙於這個主要是在介紹 RSpec,關於 Ruby 的基礎就不提到太多!主要還是以通過測試的邏輯為主。
測驗區
從第一天到現在也說了蠻多的東西了,有一些小測驗希望可以讓剛學的人回想一下,自己想的是錯誤還是正確!
- 哪一個方法可以在 RSpec 中建立一個
example
? - 哪一個方法可以在 RSpec 中建立一個
example group
? - 哪一個方法可以在 RSpec 中建立一個
assertion
? ( 類似主張、斷言的感覺) expect.eq(1 + 1, 2)
這是正確的寫法嗎?如果是錯的,為什麼?- 我想要建立一個
example
,只要打開一個_spec.rb
的檔案直接寫就可以了嗎? describe
語法一定要有參數才可以運作嗎?- 測試的順序是什麼?(
E2E Test, Integration Test, Unit Test
) - 要初始化一個 Rspec 測試的終端機指令是什麼?
- 你應該寫測試在你寫 Code 之前嗎?為什麼?
這些答案在之前的文章都有提過!
結語
明天會在一個添加許多的 example
在一個測試之中,順便訓練思考 TDD 的思緒,然後繼續的面對錯誤,修正,重構,這樣自然而然就會越來越有感覺