TDDの基礎
TDDの要点を見てみましょう。
この例では、テスト駆動プロセスを通じて計算機を構築します。Rubyテストでは、表現力豊かなDSLと優れたコミュニティサポートを備えた人気のテストライブラリであるRSpecを使用します。この例では、RSpecの自動実行機能を使用して、ファイルを更新するたびにテストを実行します。通常、この機能は使用しませんが、トレイル中の作業の確認が速くなります。
最初のテストを書く
まず、テストを作成します。RSpecはネストされたブロックを使用してテストをグループ化します。最も外側のブロックはクラス(Calculator)を記述し、の次のレベルはメソッドを記述します#add。もう1つのレベルで、itブロック内の最初の動作の仕様を記述します。
describe Calculator do
describe "#add" do
it "adds two numbers" do
calculator = Calculator.new
expect(calculator.add(1, 1)).to eq(2)
end
endend
スペックの内容はほとんどがあなたがすでに知っているRubyです。RSpecのDSLは、テストに英語の読みやすさを与えるいくつかのメソッドを提供します。#expect テスト結果の検証を実行するようにRSpecに指示する方法です。
私たちの最初のエラー:赤
テストスイートを最初に実行すると、エラーが発生します。これはいい!TDDのエラーは、次に実行する増分ステップを決定するのに役立ちます。新しいコードは、エラーを解決するために(理由の範囲内で)可能な限り単純なロジックを実装する必要があります。
まず、Calculator定義されていないことが原因でエラーが発生するため、クラスを追加します。クラスを追加すると、未定義のメソッドに関するエラーが発生します#add。実装Calculator#addすると、引数の数が正しくないというエラーが発生します。与える#add引数は、その後されて返された値に関するエラーにつながるnil合計ではなく。次に、メソッドロジックを実装します。
class Calculator
def add(a, b)
endend
テスト合格:緑
#add戻っ15てテストに合格するためのハードコーディングは悪い考えのように思えるかもしれませんが、まだ完了していません。テストに合格したので、より一般化されたソリューションを必要とする別のテストを作成します。2番目のテストでは、ハードコードされた戻り値が不適切なソリューションとして公開され、両方のテストに合格するには、より適切な実装が必要です。
最初にハードコードされた値を使用してテストを解決する必要は必ずしもありませんが、最初の実装と一般的な実装への迅速な反復は、TDDが機能を提供するために必要な最小限のコードにどのように導くことができるかを示しています。
次の機能の実装:階乗
#add私たちが望むような方法が働いて、それの時間は、私たちの電卓に新しい機能を追加した結果を返すために階乗を。
階乗には2つのケースがあります。数値の階乗は、1からその数値までのすべての正の整数に互いに乗算されたものです。階乗0、特別な場合はです1。これらの各ケースを処理するためのテストを作成します。
describe "#factorial" do
it "returns 1 when given 0 (0! = 1)" do
calc = calculator.new
expect(calc.factorial(0)).to eq(1)
end
it "returns 120 when given 5 (5! = 120)" do
calc = calculator.new
expect(calc.factorial(5)).to eq(120)
endend
最も単純なケースである階乗から始めて、各テストのエラーを個別に解決します0。最初にメソッドを定義し、次にメソッドに引数を指定してから、期待される結果を返します。
def factorial(n)
1end
私たちの仕様は合格し、まだ失敗しているより複雑な一般的なケースに進むことができます。再帰的な解決策は単純なアプローチif であり、0ケースを防ぐ条項があります。
def factorial(n)
if n == 0
1
else
n * factorial(n-1)
endend
リファクタリング
テストに合格すると、私たちは全面的に環境に配慮しています。この状態は、リファクタリングを行うのに最適な時期ですが、コードの理解は新鮮であり、テストスイートはリグレッションを防ぐ準備ができています。
運動
今度は、TDDの練習で手を汚す時が来ました。
このコードをファイルにコピーし、名前を付けspec.rbます。
RSpecをインストールします: gem install rspec
テストを実行します。 rspec spec.rb
保留中の仕様を具体化された失敗した仕様に変える
テストを実行し、失敗を観察します
red-green-refactorを使用して、仕様を通過させるコードを実装します。
コメントでまだ書かれていないテストを構築し続けます
#TDDの原則を使用して、個人の名前機能を構築します。
#要件は次のとおりです。
#-フルネームを文字列として返すメソッドを追加します。 フルネームには
#姓、名、ミドルネーム。 ミドルネームが欠落している場合は、存在すべきではありません
#余分なスペースがあります。
#-ミドルネームのイニシャルを持つフルネームを返すメソッドを追加します。 ミドルネームの場合
#が欠落しているため、余分なスペースやピリオドがあってはなりません。
#-すべてのイニシャルを返すメソッドを追加します。 ミドルネームが欠落している場合、
#イニシャルは2文字のみにする必要があります。
#
## full_nameの仕様の説明はすでにスケッチしています。 試してみてください
#そのメソッドの仕様を作成し、それらが失敗するのを監視してから、次のコードを記述します。
#合格させる。 次に、他の2つの方法に進みますが、今回は
#上記の要件に一致する説明を作成します。
class Person
def initialize(first_name:, middle_name: nil, last_name:)
@first_name = first_name
@middle_name = middle_name
@last_name = last_name
end
# implement your behavior hereend
RSpec.describe Person do
describe "#full_name" do
it "concatenates first name, middle name, and last name with spaces"
it "does not add extra spaces if middle name is missing"
end
describe "#full_name_with_middle_initial"
describe "#initials"end