def apply(self, robot: Robot, *args): """ Apply the "PLACE" instruction to a given robot :param robot: the robot on which the instruction should be executed :type robot: Robot :param args: the arguments needed by the place instruction in the right order : - the x coordinate of the position (int or str) - the y coordinate of the position (int or str), - the direction to which the robot should look at (a string which must one these : "WEST", "NORTH", "EAST" or "SOUTH") :raise BadInstructionParamAmountError: when args does not contain exactly 3 arguments :raise BadInstructionParamTypeError: when one of the 3 given arguments in args is not in the right type :return: None """ if len(args) == 3: if isinstance(args[0], str) and not args[0].isdigit(): raise BadInstructionParamTypeError( 'X-axis coordinate should be an integer') if isinstance(args[0], str) and not args[1].isdigit(): raise BadInstructionParamTypeError( 'Y-axis coordinate should be an integer') if not args[2] in Direction.__members__: content = '''Direction should be a cardinal point (received "{}")'''.format(args[2]) raise BadInstructionParamTypeError(content) sub_args = (int(args[0]), int(args[1]), args[2] if isinstance( args[2], Direction) else Direction[args[2]]) robot.place(*sub_args) else: raise BadInstructionParamAmountError( 'Instruction is malformed (exactly 3 arguments are allowed) !')
def apply_function(self, robot: Robot): """ Apply the "RIGHT" instruction to a given robot :param robot: the robot on which the instruction should be executed :type robot: Robot :return: None """ robot.right()
class InstructionNoInitialPlaceTestCase(unittest.TestCase): def setUp(self): self.robot = Robot() def test_place(self): self.robot.place(0, 0, Direction.NORTH) self.assertEqual(self.robot.position, (0, 0)) self.assertEqual(self.robot.direction, Direction.NORTH) def test_right(self): self.robot.right() self.assertIsNone(self.robot.position) self.assertIsNone(self.robot.direction) def test_left(self): self.robot.left() self.assertIsNone(self.robot.position) self.assertIsNone(self.robot.direction) def test_move(self): self.robot.move() self.assertIsNone(self.robot.position) self.assertIsNone(self.robot.direction) def test_report(self): self.assertIsNone(self.robot.report())
class ReportTestCase(unittest.TestCase): def setUp(self): self.robot = Robot() self.robot.place(1, 2, Direction.SOUTH) self.report_instruction = ReportInstruction(output=StringIO()) @patch('robotic.robot.Robot.report') def test_good_params(self, report_patch): report_patch.return_value = { 'name': "Test", 'position': (1, 2), 'direction': Direction.SOUTH } self.report_instruction.apply(self.robot) report_patch.assert_called_once_with()
def run(self): """ Run the command :return: None """ args = self.parser.parse_args() x_size = args.x_size y_size = args.y_size if args.y_size is not None else args.x_size robot_params = { 'environment': RectangularEnvironment(x_size=x_size, y_size=y_size) } if args.name is not None: robot_params['name'] = args.name robot = Robot(**robot_params) verbose = args.verbose simulator = CliRobotSimulation(robot, verbose=verbose) # STANDARD INPUT if args.execute is not None and len(args.execute) > 0: for arg in args.execute: simulator.input(arg) # FILE READING elif args.file is not None: simulator.read_from_file(args.file) elif args.interactive: simulator.interactive() else: print('Please provide at least -i , -f or -x option')
def apply_function(self, robot: Robot): """ Apply the "REPORT" instruction to a given robot and print the result on self.output. :param robot: the robot on which the instruction should be executed :type robot: Robot :return: None """ report = robot.report() if report is not None: self.output.write(self.report_template.format(**report))
def setUp(self): self.robot = Robot() self.left_instruction = LeftInstruction()
def setUp(self): self.robot = Robot() self.robot_simulation = CliRobotSimulation(self.robot)
class RobotSimulationTestCase(unittest.TestCase): def setUp(self): self.robot = Robot() self.robot_simulation = CliRobotSimulation(self.robot) @patch('builtins.input', side_effect=['PLACE 0,0,NORTH', 'SHUTDOWN']) def test_interactive(self, mock): self.robot_simulation.interactive() self.assertEqual(self.robot.position, (0, 0)) self.assertEqual(self.robot.direction, Direction.NORTH) @patch('parsers.simple_parser.SimpleInstructionParser.parse_str') @patch('robotic.abstract_robot_simulation.AbstractRobotSimulation.exec', return_value=None) def test_input(self, mock_exec, mock_parse_str): mock_parse_str.return_value = [{ 'command': PlaceInstruction(), 'args': ['0', '0', 'NORTH'] }, { 'command': LeftInstruction(), 'args': [] }] self.robot_simulation.input('whatever') mock_exec.assert_called_once_with(mock_parse_str.return_value) @patch('instruction.place.PlaceInstruction.apply', side_effect=BadInstructionParamAmountError) @patch('sys.stdout', new_callable=StringIO) def test_exec_bad_param_amount(self, sys_mock, apply_mock): in_data = [{'command': PlaceInstruction(), 'args': []}] self.robot_simulation.output = sys_mock self.robot_simulation.exec(in_data) self.assertEqual( sys_mock.getvalue(), self.robot_simulation.error_messages['bad_params_amount'] + '\n') @patch('instruction.place.PlaceInstruction.apply', side_effect=BadInstructionParamTypeError) @patch('sys.stdout', new_callable=StringIO) def test_exec_bad_param_type(self, sys_mock, apply_mock): in_data = [{'command': PlaceInstruction(), 'args': []}] self.robot_simulation.output = sys_mock self.robot_simulation.exec(in_data) self.assertEqual( sys_mock.getvalue(), self.robot_simulation.error_messages['bad_param_type'] + '\n') def test_read_file(self): filename = 'bluh' test_data = 'PLACE 0,0,NORTH\nRIGHT' m = unittest.mock.mock_open(read_data=''.join(test_data)) m.return_value.__iter__ = lambda x: x m.return_value.__next__ = lambda x: next(iter(x.readline, '')) with patch('builtins.open', m): self.robot_simulation.read_from_file(filename) self.assertEqual(self.robot.position, (0, 0)) self.assertEqual(self.robot.direction, Direction.EAST) m.assert_called_once_with(filename) def test_print_border(self): spec_robot_simulation = CliRobotSimulation(self.robot, verbose=True, output=MagicMock()) self.assertTrue(hasattr(spec_robot_simulation, 'border')) self.assertIsNone(spec_robot_simulation.border) spec_robot_simulation._print_border() self.assertIsNotNone(spec_robot_simulation.border) firstly_generated = spec_robot_simulation.border self.assertEqual(spec_robot_simulation.border[0], '+') self.assertEqual(spec_robot_simulation.border[-2:], '+\n') self.assertEqual(spec_robot_simulation.border.strip('+\n'), '-' * spec_robot_simulation.robot.environment.x_size) spec_robot_simulation._print_border() self.assertIs(firstly_generated, spec_robot_simulation.border) def test_robot_repr(self): tests = { Direction.NORTH: '^', Direction.WEST: '<', Direction.EAST: '>', Direction.SOUTH: 'v' } for direction, char in tests.items(): self.robot.direction = direction self.assertEqual(self.robot_simulation._robot_repr(), char) def test_print_map(self): mock = StringIO() robot_simulation = CliRobotSimulation(self.robot, verbose=True, output=mock) position = (0, 0) direction = Direction.NORTH self.robot.place(*position, direction) robot_simulation._print_map() map_elements = mock.getvalue().strip().split('\n') map_borders = map_elements[0:1] + map_elements[-1:] # BORDERS for map_border in map_borders: self.assertEqual(map_border[0], '+') self.assertEqual(map_border[-1], '+') for char in map_border[1:-1]: self.assertEqual(char, '-') # LINES & ROBOT map_lines = map_elements[1:-1] for i, map_line in enumerate(reversed(map_lines)): self.assertEqual(map_line[0], '|') self.assertEqual(map_line[-1], '|') for j, char in enumerate(map_line[1:-1]): if self.robot.position == (i, j): self.assertNotEqual(char, '-') else: self.assertEqual(char, '-')
def setUp(self): self.robot = Robot()
def setUp(self): self.robot = Robot('Test') self.initial_x = 0 self.initial_y = 0 self.initial_dir = Direction.NORTH self.robot.place(self.initial_x, self.initial_y, self.initial_dir)
class RobotTestCase(unittest.TestCase): def setUp(self): self.robot = Robot('Test') self.initial_x = 0 self.initial_y = 0 self.initial_dir = Direction.NORTH self.robot.place(self.initial_x, self.initial_y, self.initial_dir) def test_place(self): self.robot.place(1, 2, Direction.SOUTH) self.assertEqual(self.robot.position, (1, 2)) self.assertEqual(self.robot.direction, Direction.SOUTH) def test_right(self): self.robot.right() self.assertEqual(self.robot.position, (self.initial_x, self.initial_y)) self.assertEqual(self.robot.direction, Compass.right(self.initial_dir)) def test_left(self): self.robot.left() self.assertEqual(self.robot.position, (self.initial_x, self.initial_y)) self.assertEqual(self.robot.direction, Compass.left(self.initial_dir)) def test_move_y(self): self.robot.move() self.assertEqual(self.robot.position, (self.initial_x, self.initial_y + 1)) self.assertEqual(self.robot.direction, self.initial_dir) def test_move_x(self): self.robot.right() self.robot.move() self.assertEqual(self.robot.position, (self.initial_x + 1, self.initial_y)) self.assertEqual(self.robot.direction, Compass.right(self.initial_dir)) def test_report(self): expected = { 'name': 'Test', 'position': (0, 0), 'direction': Direction.NORTH } self.assertDictEqual(self.robot.report(), expected) @patch('robotic.robot.Robot._prevent_fall') def test_move_outside_environment(self, prevent_fall_mock): self.robot.left() self.robot.move() self.assertEqual(self.robot.position, (self.initial_x, self.initial_y)) prevent_fall_mock.assert_called_once_with() @patch('robotic.robot.Robot._prevent_fall') def test_place_outside_environment(self, prevent_fall_mock): self.robot.place(1000, 1000, Direction.SOUTH) self.assertEqual(self.robot.position, (self.initial_x, self.initial_y)) self.assertEqual(self.robot.direction, self.initial_dir) prevent_fall_mock.assert_called_once_with()
def setUp(self): self.robot = Robot() self.right_instruction = RightInstruction()
def setUp(self): self.robot = Robot() self.robot.place(1, 2, Direction.SOUTH) self.report_instruction = ReportInstruction(output=StringIO())
def setUp(self): self.robot = Robot() self.place_instruction = PlaceInstruction() self.patcher = patch('robotic.robot.Robot.place') self.place_patch = self.patcher.start() self.place_patch.return_value = None
def setUp(self): self.robot = Robot() self.simple_instruction = SimpleInstruction("TEST")