def setUp(self): super(TestPlayer, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_spawn_points()[0] self.world_update_task = task.LoopingCall(self.world.processing_step) self.world_update_task.clock = self.clock self.world_update_task.start(1.0 / 30) self.player = Archer(self.world, reactor=self.clock) self.player.spawn(self.spawn_point)
def test_get_frame(self): self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.connection.on('frame', self.callback) self.clock.advance(1) frame = self.get_last_callback_arguments() items_expected = self.get_items_expected('get_frame_message') self.assertEqual(len(frame), len(items_expected)) for message in frame: matching_expected_item = items_expected.pop(message['id']) self.assertEqual(message['x'], int(settings.PPM*matching_expected_item.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM*matching_expected_item.get_position()['y'])) self.assertEqual(message['direction'], matching_expected_item.get_direction()) self.assertEqual(len(items_expected), 0) self.clock.advance(1) frame = self.get_last_callback_arguments() # Nothing has changed! self.assertEqual(len(frame), 0) self.archer.want_move(directions['south']) self.advance_clock(1) frame = self.get_last_callback_arguments() self.assertEqual(len(frame), 1) message = frame.pop() self.assertEqual(message['x'], int(settings.PPM*self.archer.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM*self.archer.get_position()['y'])) self.assertEqual(message['direction'], self.archer.get_direction())
def test_player_kills_player(self): attacker_spawn = self.world.get_object_by_name('spawn2') defender_spawn = self.world.get_object_by_name('spawn3') attacker = Archer(self.world, name="attacker", reactor=self.clock) defender = Archer(self.world, name="defender", reactor=self.clock) attacker.spawn(attacker_spawn) defender.spawn(defender_spawn) attacker.want_attack(directions['south']) self.advance_clock(1) self.assertEqual(attacker.state, "shooting") self.assertEqual(defender.state, "standing") self.advance_clock(50) self.assertEqual(attacker.state, "standing") self.assertEqual(defender.state, "dying") self.advance_clock(250) self.assertEqual(defender.state, "dead")
def setUp(self): super(TestArcher, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_spawn_points()[0] self.world_update_task = task.LoopingCall(self.world.step) self.world_update_task.clock = self.clock self.world_update_task.start(settings.TIME_STEP) self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point)
def test_get_update(self): self.connection.on('update', self.callback) self.clock.advance(1) items_expected = self.get_items_expected('get_update_message') update = self.get_last_callback_arguments() self.assertEqual(len(update), len(items_expected)) for message in update: self.assertIsInstance(message, UpdateMessage) matching_expected_item = items_expected.pop(message['id']) self.assertEqual(message['id'], matching_expected_item.id) # self.assertEqual(message['center'], False) #TEST MORE self.assertEqual(len(items_expected), 0) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertIsNone(update) self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertEqual(len(update), 1)
def test_archer_kills_archer(self): attacker_spawn = self.world.get_object_by_name('spawn2') defender_spawn = self.world.get_object_by_name('spawn3') attacker = Archer(self.world, name="attacker", reactor=self.clock) defender = Archer(self.world, name="defender", reactor=self.clock) attacker.spawn(attacker_spawn) defender.spawn(defender_spawn) attacker.want_attack(directions['south']) self.advance_clock(1) self.assertEqual(attacker.state, "shooting") self.assertEqual(defender.state, "standing") self.advance_clock(50) self.assertEqual(attacker.state, "standing") self.assertEqual(defender.state, "dying") self.advance_clock(250) self.assertEqual(defender.state, "dead")
def test_get_frame(self): self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.connection.on('frame', self.callback) self.clock.advance(1) frame = self.get_last_callback_arguments() items_expected = self.get_items_expected('get_frame_message') self.assertEqual(len(frame), len(items_expected)) for message in frame: matching_expected_item = items_expected.pop(message['id']) self.assertEqual( message['x'], int(settings.PPM * matching_expected_item.get_position()['x'])) self.assertEqual( message['y'], int(settings.PPM * matching_expected_item.get_position()['y'])) self.assertEqual(message['direction'], matching_expected_item.get_direction()) self.assertEqual(len(items_expected), 0) self.clock.advance(1) frame = self.get_last_callback_arguments() # Nothing has changed! self.assertEqual(len(frame), 0) self.archer.want_move(directions['south']) self.advance_clock(1) frame = self.get_last_callback_arguments() self.assertEqual(len(frame), 1) message = frame.pop() self.assertEqual(message['x'], int(settings.PPM * self.archer.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM * self.archer.get_position()['y'])) self.assertEqual(message['direction'], self.archer.get_direction())
def __init__(self, world, cache): super(Connection, self).__init__() self.session_id = uuid.UUID(bytes=urandom(16)) self.world = world self.cache = cache self.known = dict() self.last_world_index = 0 self.last_frame_index = 0 self.archer = Archer(self.world, player=self) self.meta = { "id": self.archer.id, "username": "******", "gender": "male", "slots": {}, "kills": 0, "deaths": 0, "score": 0, "budget": settings.initial_budget, "attributes": self.archer.attributes } self.archer.interface = self logging.info("New connection %s" % self.session_id) self.world.on('destroy_object', self.on_destroy) self.world.on('step', self.on_step) self.on('useraction', self.on_user_action) self.on('disconnect', self.on_disconnect) self.on('usermsg', self.on_user_message) self.on('kill', self.on_kill) self.on('die', self.on_die) self.on('mob', self.on_mob) self.on('pickup', self.on_pickup) self.on('spawn', self.on_spawn)
def test_get_update(self): """ Test raw execution performance of the 'get_update'""" self.connection = Connection(self.world, self.cache) archers = list() for i in range(50): archer = Archer(self.world, reactor=self.clock) archer.spawn(self.spawn_point) archer.want_move(directions['south']) archers.append(archer) self.pr.enable() for i in range(100): self.connection.get_update() self.pr.disable() print self.process_stats('test_get_update.txt')
class TestPlayer(BaseTestCase): def setUp(self): super(TestPlayer, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_spawn_points()[0] self.world_update_task = task.LoopingCall(self.world.processing_step) self.world_update_task.clock = self.clock self.world_update_task.start(1.0 / 30) self.player = Archer(self.world, reactor=self.clock) self.player.spawn(self.spawn_point) def tearDown(self): self.player.destroy() self.world_update_task.stop() def count_player_arrows(self, player): arrows = self.world.get_objects_by_type('arrow') count = 0 for arrow in arrows: if (arrow.owner == player): count = count + 1 return count def get_player_arrows(self, player): arrows = self.world.get_objects_by_type('arrow') player_arrows = list() for arrow in arrows: if (arrow.owner == player): player_arrows.append(arrow) return player_arrows def test_player_spawned(self): self.assertEqual(self.spawn_point.x, self.player.physics.position.x) self.assertEqual(self.spawn_point.y, self.player.physics.position.y) def test_player_moved(self): self.player.want_move(directions['north']) self.advance_clock(1) self.assertLess(self.player.physics.position.y, self.spawn_point.y) def test_player_collides(self): self.player.want_move(directions['east']) self.advance_clock(100) self.assertLess(self.player.physics.position.x, 6.0) self.assertGreater(self.player.physics.position.x, self.spawn_point.x) def test_player_shoots(self): self.player.want_attack(directions['south']) self.advance_clock(40) self.assertEqual(self.count_player_arrows(self.player), 1) self.advance_clock(1000) self.assertEqual(self.count_player_arrows(self.player), 0) def test_arrow_flies(self): self.player.want_attack(directions['south']) self.advance_clock(40) arrow = self.get_player_arrows(self.player)[0] self.assertEqual(self.player.physics.position.x, arrow.physics.position.x) player_position_plus_2m = self.player.physics.position + directions[ 'south'] * 2 self.assertGreater(arrow.physics.position.y, player_position_plus_2m.y) def test_arrow_collides(self): self.player.want_attack(directions['south']) self.advance_clock(40) arrow = self.get_player_arrows(self.player)[0] self.assertLess(arrow.physics.position.x, 6.0) self.assertGreater(arrow.physics.position.y, self.player.physics.position.y) def test_player_kills_player(self): attacker_spawn = self.world.get_object_by_name('spawn2') defender_spawn = self.world.get_object_by_name('spawn3') attacker = Archer(self.world, name="attacker", reactor=self.clock) defender = Archer(self.world, name="defender", reactor=self.clock) attacker.spawn(attacker_spawn) defender.spawn(defender_spawn) attacker.want_attack(directions['south']) self.advance_clock(1) self.assertEqual(attacker.state, "shooting") self.assertEqual(defender.state, "standing") self.advance_clock(50) self.assertEqual(attacker.state, "standing") self.assertEqual(defender.state, "dying") self.advance_clock(250) self.assertEqual(defender.state, "dead")
def spawn_archer(): global archer world = archers.world spawn_point = world.get_spawn_points()[0] archer = Archer(world) archer.spawn(spawn_point)
def spawn_sucker(): world = archers.world spawn_point = world.get_spawn_points()[2] sucker = Archer(world) sucker.spawn(spawn_point)
class Connection(EventsMixins): def __str__(self): return self.meta['username']; def __init__(self, world, cache): super(Connection, self).__init__() self.session_id = uuid.UUID(bytes=urandom(16)) self.world = world self.cache = cache self.known = dict() self.last_world_index = 0 self.last_frame_index = 0 self.archer = Archer(self.world, player=self) self.meta = { "id": self.archer.id, "username": "******", "gender": "male", "slots": {}, "kills": 0, "deaths": 0, "score": 0, "budget": settings.initial_budget, "attributes": self.archer.attributes } self.archer.interface = self logging.info("New connection %s" % self.session_id) self.world.on('destroy_object', self.on_destroy) self.world.on('step', self.on_step) self.on('useraction', self.on_user_action) self.on('disconnect', self.on_disconnect) self.on('usermsg', self.on_user_message) self.on('kill', self.on_kill) self.on('die', self.on_die) self.on('mob', self.on_mob) self.on('pickup', self.on_pickup) self.on('spawn', self.on_spawn) def on_spawn(self): self.meta['budget'] = settings.initial_budget self.trigger('meta', self.meta) def on_kill(self, prey): self.meta['kills'] = self.meta['kills'] + 1 self.meta['score'] = self.meta['score'] + settings.score['kill'] logging.info("%s fragged %s" % (self.meta['username'], prey.meta['username'])) self.trigger('meta', self.meta) def on_die(self, killer=None): self.meta['deaths'] = self.meta['deaths'] + 1 logging.info("%s died by the hand of %s" % (self.meta['username'], killer or "[unknown]")) self.trigger('meta', self.meta) def on_mob(self): self.meta['score'] = self.meta['score'] + settings.score['mob'] self.trigger('meta', self.meta) def on_pickup(self, bonus): self.meta['budget'] = self.meta["budget"] + bonus.value self.trigger('meta', self.meta) def on_user_message(self, meta): changed = False if('username' in meta): new_username = meta['username'][0:10] if(new_username != self.meta['username']): self.meta['username'] = new_username logging.info("%s is now known as %s" % (self.session_id, self.meta['username'])) changed = True if('gender' in meta and meta['gender'] != self.meta['gender']): self.meta['gender'] = meta['gender'] changed = True if('slots' in meta and meta['slots'] != self.meta['slots']): if(verify_slots(meta['slots'], self.meta['budget'])): self.meta['slots'] = meta['slots'] changed = True else: logging.info("%s provided incorrect meta msg (%s). Discarding" % (self.meta['username'], meta['slots'])) if(changed): self.archer.update_attributes() # self.trigger('meta', self.meta) def on_disconnect(self): self.world.off('destroy_object', self.on_destroy) self.world.off('step', self.on_step) self.off() self.archer.destroy() def on_user_action(self, message): spawn_points = self.world.get_spawn_points() shuffle(spawn_points) logging.info(message); if(message['action'] == 'spawn'): if(self.archer.can_spawn()): if(verify_slots(self.meta['slots'], self.meta['budget'])): self.archer.spawn(spawn_points[0]) else: logging.info('denying %s spawn, incorrect slots %s' % (self.meta['username'], self.meta['slots'])) if(message['action'] == 'suicide'): self.archer.kill(); if(message['action'] == 'stop'): self.archer.want_stop() if(message['action'] == 'move'): self.archer.want_move(message['direction']) if(message['action'] == 'attack'): self.archer.want_attack(message['direction']) def on_destroy(self, world_object): messages = list() if(hasattr(world_object, 'get_destroy_message')): msg = world_object.get_destroy_message() if(msg): messages.append(msg) self.trigger('remove', messages) def on_step(self, world): self.trigger('update', self.get_update()) self.trigger('frame', self.get_frame()) def get_update(self): messages = list() if(self.last_world_index != self.world.object_index.index): for index in range(self.last_world_index, self.world.object_index.index): index = index+1 try: world_object = self.world.get_object_by_id(index) if(hasattr(world_object, 'get_update_message')): msg = world_object.get_update_message(recipient=self) if(msg): messages.append(msg) except KeyError: pass self.last_world_index = index return messages def get_frame(self): items = self.world.object_index.values() update = self.cache.get_frame_message_from_cache(self.world.step) if(update): return update update = list() for item in items: if(hasattr(item, 'get_frame_message')): data = item.get_frame_message() update.append(data) # if data and not(item in self.known.keys() and self.known[item] == data): # self.known[item] = data self.cache.cache_frame_messages(self.world.step, update) return update
class TestArcher(BaseTestCase): def setUp(self): super(TestArcher, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_spawn_points()[0] self.world_update_task = task.LoopingCall(self.world.step) self.world_update_task.clock = self.clock self.world_update_task.start(settings.TIME_STEP) self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) def tearDown(self): self.archer.destroy() self.world_update_task.stop() def count_archer_arrows(self, archer): arrows = self.world.get_objects_by_type('arrow') count = 0 for arrow in arrows: if(arrow.owner == archer): count = count + 1 return count def get_archer_arrows(self, archer): arrows = self.world.get_objects_by_type('arrow') archer_arrows = list() for arrow in arrows: if(arrow.owner == archer): archer_arrows.append(arrow) return archer_arrows def test_archer_spawned(self): self.assertEqual(self.spawn_point.x, self.archer.physics.position.x) self.assertEqual(self.spawn_point.y, self.archer.physics.position.y) def test_archer_moved(self): self.archer.want_move(directions['north']) self.advance_clock(1) self.assertLess(self.archer.physics.position.y, self.spawn_point.y) def test_archer_collides(self): self.archer.want_move(directions['east']) self.advance_clock(100) self.assertLess(self.archer.physics.position.x, 6.0) self.assertGreater(self.archer.physics.position.x, self.spawn_point.x) def test_archer_shoots(self): self.archer.want_attack(directions['south']) self.advance_clock(40) self.assertEqual(self.count_archer_arrows(self.archer), 1) self.advance_clock(1000) self.assertEqual(self.count_archer_arrows(self.archer), 0) def test_arrow_flies(self): self.archer.want_attack(directions['south']) self.advance_clock(40) arrow = self.get_archer_arrows(self.archer)[0] self.assertEqual(self.archer.physics.position.x, arrow.physics.position.x) archer_position_plus_2m = self.archer.physics.position + directions['south']*2 self.assertGreater(arrow.physics.position.y, archer_position_plus_2m.y) def test_arrow_collides(self): self.archer.want_attack(directions['east']) self.advance_clock(40) arrow = self.get_archer_arrows(self.archer)[0] self.assertLess(arrow.physics.position.x, 6.0) self.assertGreater(arrow.physics.position.x, self.archer.physics.position.x) def test_archer_kills_archer(self): attacker_spawn = self.world.get_object_by_name('spawn2') defender_spawn = self.world.get_object_by_name('spawn3') attacker = Archer(self.world, name="attacker", reactor=self.clock) defender = Archer(self.world, name="defender", reactor=self.clock) attacker.spawn(attacker_spawn) defender.spawn(defender_spawn) attacker.want_attack(directions['south']) self.advance_clock(1) self.assertEqual(attacker.state, "shooting") self.assertEqual(defender.state, "standing") self.advance_clock(50) self.assertEqual(attacker.state, "standing") self.assertEqual(defender.state, "dying") self.advance_clock(250) self.assertEqual(defender.state, "dead")
class TestInterface(BaseTestCase): def setUp(self): super(TestInterface, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_object_by_name('spawn1') self.world_update_task = task.LoopingCall(self.world.processing_step) self.world_update_task.clock = self.clock self.world_update_task.start(1.0/30) self.networking_task = task.LoopingCall(self.world.networking_step) self.networking_task.clock = self.clock self.networking_task.start(1.0/30) self.connection = Connection(self.world) self.last_callback_data = None def tearDown(self): self.world_update_task.stop() self.networking_task.stop() def get_items_expected(self, expected_attr): # items_expected = self.world.object_lookup_by_name items_expected = self.world.object_index items_expected = {k: v for k, v in items_expected.items() if hasattr(v, expected_attr)} return items_expected def callback(self, *args, **kwargs): self.last_callback_data = list(*args) def get_last_callback_arguments(self): tmp = self.last_callback_data self.last_callback_data = None return tmp def test_get_frame(self): self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.connection.on('frame', self.callback) self.clock.advance(1) frame = self.get_last_callback_arguments() items_expected = self.get_items_expected('get_frame_message') self.assertEqual(len(frame), len(items_expected)) for message in frame: matching_expected_item = items_expected.pop(message['id']) self.assertEqual(message['x'], int(settings.PPM*matching_expected_item.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM*matching_expected_item.get_position()['y'])) self.assertEqual(message['direction'], matching_expected_item.get_direction()) self.assertEqual(len(items_expected), 0) self.clock.advance(1) frame = self.get_last_callback_arguments() # Nothing has changed! self.assertEqual(len(frame), 0) self.archer.want_move(directions['south']) self.advance_clock(1) frame = self.get_last_callback_arguments() self.assertEqual(len(frame), 1) message = frame.pop() self.assertEqual(message['x'], int(settings.PPM*self.archer.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM*self.archer.get_position()['y'])) self.assertEqual(message['direction'], self.archer.get_direction()) def test_get_update(self): self.connection.on('update', self.callback) self.clock.advance(1) items_expected = self.get_items_expected('get_update_message') update = self.get_last_callback_arguments() self.assertEqual(len(update), len(items_expected)) for message in update: self.assertIsInstance(message, UpdateMessage) matching_expected_item = items_expected.pop(message['id']) self.assertEqual(message['id'], matching_expected_item.id) # self.assertEqual(message['center'], False) #TEST MORE self.assertEqual(len(items_expected), 0) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertIsNone(update) self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertEqual(len(update), 1) def get_fake_msg(self, x=1, y=3.33, direction=directions['south']): msg = FakeMessage() msg['x'] = x msg['y'] = y msg['direction'] = direction return msg def test_packing(self): msg = self.get_fake_msg() packed = msg.pack() self.assertEqual(packed[0:4], struct.pack('!I', 1)) self.assertEqual(packed[4:8], struct.pack('!f', 3.33)) self.assertEqual(packed[8:9], struct.pack('!B', DirectionMessageMixin.direction_lookup[directions['south']])) def test_dehydration(self): x = 12 y = 4.44 dir = DirectionMessageMixin.direction_lookup[directions['west']] dehydrated_item = [x, y, dir] msg = FakeMessage.from_dehydrated(dehydrated_item) self.assertEqual(msg['x'], x) self.assertEqual(msg['y'], y) self.assertEqual(msg['direction'], directions['west']) def test_unpacking(self): # packed = '\x00\x00\x00\x01\x00\x00\x00\x01\x00\x00\x00\x02\x02\n' x = 12 y = 7.77 dir = DirectionMessageMixin.direction_lookup[directions['west']] packed = struct.pack("!I", x) + struct.pack("!f", y) + struct.pack("!B", dir) + "\n" msg = FakeMessage.from_packed(packed) self.assertEqual(msg['x'], x) self.assertAlmostEqual(msg['y'], y, places=4) self.assertEqual(msg['direction'], directions['west']) def test_message_packing(self): msg = self.get_fake_msg() msg2 = self.get_fake_msg(x=5, direction=directions['east']) result = pack_messages([msg, msg2]) expected_byte_length = 1 + 2 * msg.get_byte_length() self.assertEqual(len(result), expected_byte_length) def test_message_unpacking(self): x1 = 12 y1 = 4.44 dir1 = DirectionMessageMixin.direction_lookup[directions['west']] packed = struct.pack("!I", x1) + struct.pack("!f", y1) + struct.pack("!B", dir1) x2 = 42 y2 = 9.987654 dir2 = DirectionMessageMixin.direction_lookup[directions['north']] packed = packed + struct.pack("!I", x2) + struct.pack("!f", y2) + struct.pack("!B", dir2) + "\n" packed = struct.pack("!B", 255) + packed messages = unpack_mesages(packed, message_types=message_types) self.assertEqual(len(messages), 2) self.assertEqual(messages[0]['x'], x1) self.assertAlmostEqual(messages[0]['y'], y1, places=4) self.assertEqual(messages[0]['direction'], directions['west']) self.assertEqual(messages[1]['x'], x2) self.assertAlmostEqual(messages[1]['y'], y2, places=4) self.assertEqual(messages[1]['direction'], directions['north']) def test_eating_own_dog_food(self): msg = self.get_fake_msg(y=1.0) packed = msg.pack() unpacked = FakeMessage.from_packed(packed) self.assertEqual(msg, unpacked)
class TestInterface(BaseTestCase): def setUp(self): super(TestInterface, self).setUp() path = os.path.dirname(os.path.os.path.realpath(__file__)) path = os.path.join(path, 'assets/test1.tmx') self.world = World(path) self.spawn_point = self.world.get_object_by_name('spawn1') self.world_update_task = task.LoopingCall(self.world.processing_step) self.world_update_task.clock = self.clock self.world_update_task.start(1.0 / 30) self.networking_task = task.LoopingCall(self.world.networking_step) self.networking_task.clock = self.clock self.networking_task.start(1.0 / 30) self.connection = Connection(self.world) self.last_callback_data = None def tearDown(self): self.world_update_task.stop() self.networking_task.stop() def get_items_expected(self, expected_attr): # items_expected = self.world.object_lookup_by_name items_expected = self.world.object_index items_expected = { k: v for k, v in items_expected.items() if hasattr(v, expected_attr) } return items_expected def callback(self, *args, **kwargs): self.last_callback_data = list(*args) def get_last_callback_arguments(self): tmp = self.last_callback_data self.last_callback_data = None return tmp def test_get_frame(self): self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.connection.on('frame', self.callback) self.clock.advance(1) frame = self.get_last_callback_arguments() items_expected = self.get_items_expected('get_frame_message') self.assertEqual(len(frame), len(items_expected)) for message in frame: matching_expected_item = items_expected.pop(message['id']) self.assertEqual( message['x'], int(settings.PPM * matching_expected_item.get_position()['x'])) self.assertEqual( message['y'], int(settings.PPM * matching_expected_item.get_position()['y'])) self.assertEqual(message['direction'], matching_expected_item.get_direction()) self.assertEqual(len(items_expected), 0) self.clock.advance(1) frame = self.get_last_callback_arguments() # Nothing has changed! self.assertEqual(len(frame), 0) self.archer.want_move(directions['south']) self.advance_clock(1) frame = self.get_last_callback_arguments() self.assertEqual(len(frame), 1) message = frame.pop() self.assertEqual(message['x'], int(settings.PPM * self.archer.get_position()['x'])) self.assertEqual(message['y'], int(settings.PPM * self.archer.get_position()['y'])) self.assertEqual(message['direction'], self.archer.get_direction()) def test_get_update(self): self.connection.on('update', self.callback) self.clock.advance(1) items_expected = self.get_items_expected('get_update_message') update = self.get_last_callback_arguments() self.assertEqual(len(update), len(items_expected)) for message in update: self.assertIsInstance(message, UpdateMessage) matching_expected_item = items_expected.pop(message['id']) self.assertEqual(message['id'], matching_expected_item.id) # self.assertEqual(message['center'], False) #TEST MORE self.assertEqual(len(items_expected), 0) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertIsNone(update) self.archer = Archer(self.world, reactor=self.clock) self.archer.spawn(self.spawn_point) self.clock.advance(1) update = self.get_last_callback_arguments() self.assertEqual(len(update), 1) def get_fake_msg(self, x=1, y=3.33, direction=directions['south']): msg = FakeMessage() msg['x'] = x msg['y'] = y msg['direction'] = direction return msg def test_packing(self): msg = self.get_fake_msg() packed = msg.pack() self.assertEqual(packed[0:4], struct.pack('!I', 1)) self.assertEqual(packed[4:8], struct.pack('!f', 3.33)) self.assertEqual( packed[8:9], struct.pack( '!B', DirectionMessageMixin.direction_lookup[directions['south']])) def test_dehydration(self): x = 12 y = 4.44 dir = DirectionMessageMixin.direction_lookup[directions['west']] dehydrated_item = [x, y, dir] msg = FakeMessage.from_dehydrated(dehydrated_item) self.assertEqual(msg['x'], x) self.assertEqual(msg['y'], y) self.assertEqual(msg['direction'], directions['west']) def test_unpacking(self): # packed = '\x00\x00\x00\x01\x00\x00\x00\x01\x00\x00\x00\x02\x02\n' x = 12 y = 7.77 dir = DirectionMessageMixin.direction_lookup[directions['west']] packed = struct.pack("!I", x) + struct.pack("!f", y) + struct.pack( "!B", dir) + "\n" msg = FakeMessage.from_packed(packed) self.assertEqual(msg['x'], x) self.assertAlmostEqual(msg['y'], y, places=4) self.assertEqual(msg['direction'], directions['west']) def test_message_packing(self): msg = self.get_fake_msg() msg2 = self.get_fake_msg(x=5, direction=directions['east']) result = pack_messages([msg, msg2]) expected_byte_length = 1 + 2 * msg.get_byte_length() self.assertEqual(len(result), expected_byte_length) def test_message_unpacking(self): x1 = 12 y1 = 4.44 dir1 = DirectionMessageMixin.direction_lookup[directions['west']] packed = struct.pack("!I", x1) + struct.pack("!f", y1) + struct.pack( "!B", dir1) x2 = 42 y2 = 9.987654 dir2 = DirectionMessageMixin.direction_lookup[directions['north']] packed = packed + struct.pack("!I", x2) + struct.pack( "!f", y2) + struct.pack("!B", dir2) + "\n" packed = struct.pack("!B", 255) + packed messages = unpack_mesages(packed, message_types=message_types) self.assertEqual(len(messages), 2) self.assertEqual(messages[0]['x'], x1) self.assertAlmostEqual(messages[0]['y'], y1, places=4) self.assertEqual(messages[0]['direction'], directions['west']) self.assertEqual(messages[1]['x'], x2) self.assertAlmostEqual(messages[1]['y'], y2, places=4) self.assertEqual(messages[1]['direction'], directions['north']) def test_eating_own_dog_food(self): msg = self.get_fake_msg(y=1.0) packed = msg.pack() unpacked = FakeMessage.from_packed(packed) self.assertEqual(msg, unpacked)
class Connection(EventsMixins): def __str__(self): return self.meta['username'] def __init__(self, world, cache): super(Connection, self).__init__() self.session_id = uuid.UUID(bytes=urandom(16)) self.world = world self.cache = cache self.known = dict() self.last_world_index = 0 self.last_frame_index = 0 self.archer = Archer(self.world, player=self) self.meta = { "id": self.archer.id, "username": "******", "gender": "male", "slots": {}, "kills": 0, "deaths": 0, "score": 0, "budget": settings.initial_budget, "attributes": self.archer.attributes } self.archer.interface = self logging.info("New connection %s" % self.session_id) self.world.on('destroy_object', self.on_destroy) self.world.on('step', self.on_step) self.on('useraction', self.on_user_action) self.on('disconnect', self.on_disconnect) self.on('usermsg', self.on_user_message) self.on('kill', self.on_kill) self.on('die', self.on_die) self.on('mob', self.on_mob) self.on('pickup', self.on_pickup) self.on('spawn', self.on_spawn) def on_spawn(self): self.meta['budget'] = settings.initial_budget self.trigger('meta', self.meta) def on_kill(self, prey): self.meta['kills'] = self.meta['kills'] + 1 self.meta['score'] = self.meta['score'] + settings.score['kill'] logging.info("%s fragged %s" % (self.meta['username'], prey.meta['username'])) self.trigger('meta', self.meta) def on_die(self, killer=None): self.meta['deaths'] = self.meta['deaths'] + 1 logging.info("%s died by the hand of %s" % (self.meta['username'], killer or "[unknown]")) self.trigger('meta', self.meta) def on_mob(self): self.meta['score'] = self.meta['score'] + settings.score['mob'] self.trigger('meta', self.meta) def on_pickup(self, bonus): self.meta['budget'] = self.meta["budget"] + bonus.value self.trigger('meta', self.meta) def on_user_message(self, meta): changed = False if ('username' in meta): new_username = meta['username'][0:10] if (new_username != self.meta['username']): self.meta['username'] = new_username logging.info("%s is now known as %s" % (self.session_id, self.meta['username'])) changed = True if ('gender' in meta and meta['gender'] != self.meta['gender']): self.meta['gender'] = meta['gender'] changed = True if ('slots' in meta and meta['slots'] != self.meta['slots']): if (verify_slots(meta['slots'], self.meta['budget'])): self.meta['slots'] = meta['slots'] changed = True else: logging.info( "%s provided incorrect meta msg (%s). Discarding" % (self.meta['username'], meta['slots'])) if (changed): self.archer.update_attributes() # self.trigger('meta', self.meta) def on_disconnect(self): self.world.off('destroy_object', self.on_destroy) self.world.off('step', self.on_step) self.off() self.archer.destroy() def on_user_action(self, message): spawn_points = self.world.get_spawn_points() shuffle(spawn_points) logging.info(message) if (message['action'] == 'spawn'): if (self.archer.can_spawn()): if (verify_slots(self.meta['slots'], self.meta['budget'])): self.archer.spawn(spawn_points[0]) else: logging.info('denying %s spawn, incorrect slots %s' % (self.meta['username'], self.meta['slots'])) if (message['action'] == 'suicide'): self.archer.kill() if (message['action'] == 'stop'): self.archer.want_stop() if (message['action'] == 'move'): self.archer.want_move(message['direction']) if (message['action'] == 'attack'): self.archer.want_attack(message['direction']) def on_destroy(self, world_object): messages = list() if (hasattr(world_object, 'get_destroy_message')): msg = world_object.get_destroy_message() if (msg): messages.append(msg) self.trigger('remove', messages) def on_step(self, world): self.trigger('update', self.get_update()) self.trigger('frame', self.get_frame()) def get_update(self): messages = list() if (self.last_world_index != self.world.object_index.index): for index in range(self.last_world_index, self.world.object_index.index): index = index + 1 try: world_object = self.world.get_object_by_id(index) if (hasattr(world_object, 'get_update_message')): msg = world_object.get_update_message(recipient=self) if (msg): messages.append(msg) except KeyError: pass self.last_world_index = index return messages def get_frame(self): items = self.world.object_index.values() update = self.cache.get_frame_message_from_cache(self.world.step) if (update): return update update = list() for item in items: if (hasattr(item, 'get_frame_message')): data = item.get_frame_message() update.append(data) # if data and not(item in self.known.keys() and self.known[item] == data): # self.known[item] = data self.cache.cache_frame_messages(self.world.step, update) return update