import unittest from game import * logging.basicConfig(level=logging.DEBUG) class TestGameBasics(unittest.TestCase): def setUp(self): self.players = ["a@a.com", "b@b.com", "c@c.com", "d@d.com"] def test_bad_players(self): self.assertRaises(PlayersNotListException, Game) self.assertRaises(InsufficientPlayersException, Game, players=[]) self.assertRaises(PlayersNotListException, Game, players=3) self.assertRaises(InsufficientPlayersException, Game, players=["a"]) self.assertRaises(InsufficientPlayersException, Game, players=["a","b"]) self.assertRaises(EmailAddressInvalidException, Game, players=["a","b","c"]) self.assertRaises(EmailAddressRepeatedException, Game, players=["a@example.com","b@example.com","a@example.com"]) def test_players(self): game = Game(players=self.players) self.assertEqual(len(game.players), len(self.players)) for player in self.players: self.assert_(player in [str(x) for x in game.players]) def test_customs_officer(self): game = Game(players=self.players) self.assertEqual(str(game.customs_officer), self.players[0]) def test_custom_deck(self): self.assertRaises(DeckInvalidException, Game, players=self.players, deck="a") # obviously short self.assertRaises(DeckInvalidException, Game, players=self.players, deck=("l" * 24) + "rdnnmmmaaaappppbbbbcccccwwwwww" + "B") # extra letter self.assertRaises(DeckInvalidException, Game, players=self.players, deck=("l" * 24) + "rdnnmmmaaaappppbbbbcccccwwwww") # w missing self.assertRaises(DeckInvalidException, Game, players=self.players, deck=("l" * 24) + "rdnnmmmaaaappppbbbbcccccwwwwwww") # extra w def test_money(self): game = Game(players=self.players) for p in game.players: self.assertEqual(p.money, 500) class TestStateMachine(unittest.TestCase): def setUp(self): self.players = ["a@a.com", "b@b.com", "c@c.com"] self.deck = "wlllclablppppdwwwclllllllllllllllllllrnnmmmaaabbbcccww" self.game = Game(players=self.players, deck=self.deck) def test_AAA_invalid_moves(self): # this is the beginning of the game, so players[0] is customs officer, # players[1] is to move by discarding, and holds hand wlll self.assertRaises(WrongPlayerException, self.game.move, self.players[0], None) self.assertRaises(WrongPlayerException, self.game.move, self.players[2], None) self.assertRaises(NoSuchMoveException, self.game.move, self.players[1], "wibble") # never heard of that move self.assertRaises(InappropriateMoveException, self.game.move, self.players[1], "challenge") # can't challenge now self.assertRaises(InvalidMoveException, self.game.move, self.players[1], "declare") # specified no cards self.assertRaises(InvalidMoveException, self.game.move, self.players[1], "declare", None) # specified no cards self.assertRaises(InvalidMoveException, self.game.move, self.players[1], "declare", "XXXX") # no such card self.assertRaises(InvalidMoveException, self.game.move, self.players[1], "declare", "lll") # must declare 4 cards self.assertRaises(InvalidMoveException, self.game.move, self.players[1], "declare", "dlll") # can't declare the DB and others def confirmMove(self, player_to_move, current_move_state, current_hand, move_to_make, move_parameter=None): # check what the state of the game is and then make the specified move self.assertEqual(str(self.game.state.player), player_to_move) self.assertEqual(self.game.state.move, current_move_state) self.assertEqual(self.game.state.hand, current_hand) self.game.move(player_to_move, move_to_make, move_parameter) def test_game_1(self): # players[1] draws 4 cards, players[0] is CO, hand is wlll self.assertNotEqual(self.game.state.hand, "wlll") # hand is in alpha order # players[1] declares clll self.confirmMove(self.players[1], "declare", "lllw", "declare", "clll") self.assertRaises(InappropriateMoveException, self.game.move, self.players[0], "declare", "dlll") # customs officer needs to challenge now # CO elects to accept declaration; players[1] pays 50 for declared c self.confirmMove(self.players[0], "challenge", "lllw", "accept") self.assertEqual(self.game.players[0].money, 550) # received 50 from [1] self.assertEqual(self.game.players[1].money, 450) # paid 50 to [0] # players[2] elects to accept declaration and not be an informer self.confirmMove(self.players[2], "challenge", "lllw", "accept") # players[2] receives existing hand, must discard one, discards an l self.assertRaises(InvalidMoveException, self.game.move, self.players[2], "discard", "d") # doesn't have the DB self.confirmMove(self.players[2], "discard", "lllw", "discard", "l") # players[2] gets a c for current hand wllc and declares llll self.confirmMove(self.players[2], "declare", "cllw", "declare", "llll") # CO does not believe and searches; players[2] pays 150 for undeclared cw self.confirmMove(self.players[0], "challenge", "cllw", "challenge") self.assertEqual(self.game.players[0].money, 700) self.assertEqual(self.game.players[2].money, 350) # all non-CO players have now played. CO should now be players[1] self.assertEqual(str(self.game.customs_officer), self.players[1]) # and it should be players[0]'s turn with 4 new cards, hand labl, declares a lie self.confirmMove(self.players[0], "declare", "abll", "declare", "bbll") # CO elects to accept declaration; players[0] pays 150 for declared bb self.confirmMove(self.players[1], "challenge", "abll", "accept") self.assertEqual(self.game.players[0].money, 550) self.assertEqual(self.game.players[1].money, 600) # players[2] elects to challenge as an informer, gets 100 from CO, players[0] pays 500 red duty self.confirmMove(self.players[2], "challenge", "abll", "challenge") self.assertEqual(self.game.players[0].money, 50) self.assertEqual(self.game.players[1].money, 1000) self.assertEqual(self.game.players[2].money, 450) # players[2] gets four new cards and fradulently declares the Bag self.confirmMove(self.players[2], "declare", "pppp", "declare", "d") # CO (p1) challenges, p2 pays red 1000 + extra 200 for diplomat impersonation self.confirmMove(self.players[1], "challenge", "pppp", "challenge") self.assertEqual(self.game.players[0].money, 50) self.assertEqual(self.game.players[1].money, 2200) self.assertEqual(self.game.players[2].money, -750) # next round: p2 is CO, p0 gets 4 new cards including the Bag and declares it self.assertEqual(self.game.customs_officer, self.game.players[2]) self.confirmMove(self.players[0], "declare", "dwww", "declare", "d") # p2 accepts, p0 pays nothing self.confirmMove(self.players[2], "challenge", "dwww", "accept") # p1 accepts. All monies are unchanged self.confirmMove(self.players[1], "challenge", "dwww", "accept") self.assertEqual(self.game.players[0].money, 50) self.assertEqual(self.game.players[1].money, 2200) self.assertEqual(self.game.players[2].money, -750) # the hand passes to p1. since the Bag is in the hand game should autodiscard d # so this next move is *not* a discard move but instead p1's declare self.confirmMove(self.players[1], "declare", "cwww", "declare", "llll") # CO (p2) accepts self.confirmMove(self.players[2], "challenge", "cwww", "accept") # p0 is the informer and challenges. CO (p2) -> p0, 100. p1 -> p2, 250 (red) self.confirmMove(self.players[0], "challenge", "cwww", "challenge") self.assertEqual(self.game.players[0].money, 150) self.assertEqual(self.game.players[1].money, 1950) self.assertEqual(self.game.players[2].money, -600) # game is over! self.assertEqual(self.game.state.move, "end") self.assertEqual(self.game.state.player, None) if __name__ == "__main__": unittest.main()