Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 44 additions & 3 deletions minitest/navy.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
class Admiral
attr_reader :battleship

def initialize(battleship)
@battleship = battleship
end
Expand All @@ -10,12 +12,51 @@ def fire_upon_target
end

class Battleship
attr_reader :ammunition
def initialize
@ammunition = 100
attr_reader :ammunition, :armory, :fate
def initialize(armory, fate)
@ammunition = 10
@armory = armory
@fate = fate
end

def fire!
@ammunition = @ammunition - 1
reload! if @ammunition == 0
fate.report
end

def reload!
@ammunition += @armory.request_ammunition(10)
end
end

class Armory
attr_reader :ammunition_reserves

def initialize(reserves)
@ammunition_reserves = reserves
end

def request_ammunition(amount)
if amount <= @ammunition_reserves
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

one final recommendation (this is a new one of mine) --- if you have an attr_reader for ammunition_reserves, it works well to only refer to it by the ammunition_reserves method.

  if amount <= ammunition_reserves

Why? Because later you can move ammunition_reserves from an instance variable to another object... And you could

def ammunition_reserves
  Reserves.calculate_ammunition(self)
end

and the request_ammunition method wouldn't know the difference.

@ammunition_reserves = @ammunition_reserves - amount
amount
else
available = @ammunition_reserves
@ammunition_reserves = 0
available
end
end

end

class Fate

def initialize(randomizer=Random)
@randomizer = randomizer
end

def report
@randomizer.rand(11).even?
end
end
94 changes: 86 additions & 8 deletions minitest/navy_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,10 @@ def setup
@admiral = Admiral.new(@battleship)
end

def test_the_admiral_has_a_battleship
assert_equal @battleship.object_id, @admiral.battleship.object_id
end

def test_can_tell_the_battleship_to_fire
@battleship.expect :fire!, nil
@admiral.fire_upon_target
Expand All @@ -17,19 +21,93 @@ def test_can_tell_the_battleship_to_fire
end

class TestBattleship< MiniTest::Unit::TestCase
def setup
@armory = MiniTest::Mock.new
@fate = MiniTest::Mock.new
@battleship = Battleship.new(@armory, @fate)
@starting_ammunition = @battleship.ammunition
end

def test_starts_with_ten_rounds_of_ammunition
assert_equal 10, @starting_ammunition
end

def test_will_decrease_ammunition_when_firing
battleship = Battleship.new
starting_ammunition = battleship.ammunition
battleship.fire!
assert_equal (starting_ammunition - 1), battleship.ammunition
@fate.expect(:report, true)
@battleship.fire!
assert_equal @starting_ammunition - 1, @battleship.ammunition
end
end

describe Battleship do

let(:armory) { MiniTest::Mock.new }
let(:fate) { MiniTest::Mock.new }
let(:ship) { Battleship.new(armory, fate) }

it "should decrease ammo" do
battleship = Battleship.new
starting_ammunition = battleship.ammunition
battleship.fire!
battleship.ammunition.must_equal (starting_ammunition -1)
fate.expect(:report, true)
starting_ammo = ship.ammunition
ship.fire!
ship.ammunition.must_equal(starting_ammo - 1)
end

it "can request more ammo" do
fate.expect(:report, true)
armory.expect(:request_ammunition, 10, [Integer])
while ship.ammunition >= 2
ship.fire!
end
ship.fire!
armory.verify
end

it "should recieve more ammo" do
fate.expect(:report, true)
armory.expect(:request_ammunition, 10, [Integer])
starting_ammo = ship.ammunition
ship.reload!
ship.ammunition.must_equal(starting_ammo + 10)
end

it "should know if there was a hit or miss after firing" do
fate.expect(:report, true)
ship.fire!.must_equal(true)
end

end

describe Armory do

subject { Armory.new(100) }

it "should have reserve ammunition" do
subject.ammunition_reserves.must_equal(100)
end

it "should provide ammunition if it has enough" do
subject.request_ammunition(10).must_equal 10
end

it "should provide partial ammunition if it doesn't have enough" do
available = subject.ammunition_reserves
subject.request_ammunition(available + 10).must_equal available
end
end

describe Fate do

it "should return true if rand is even" do
mock_rand = MiniTest::Mock.new
fate = Fate.new(mock_rand)
mock_rand.expect(:rand, 6, [Integer])
fate.report.must_equal true
end

it "should return false if rand is odd" do
mock_rand = MiniTest::Mock.new
fate = Fate.new(mock_rand)
mock_rand.expect(:rand, 5, [Integer])
fate.report.must_equal false
end
end