def test_color_RGB_to_xy(self): """ Test color_RGB_to_xy. """ self.assertEqual((0, 0), util.color_RGB_to_xy(0, 0, 0)) self.assertEqual((0.3127159072215825, 0.3290014805066623), util.color_RGB_to_xy(255, 255, 255)) self.assertEqual((0.15001662234042554, 0.060006648936170214), util.color_RGB_to_xy(0, 0, 255)) self.assertEqual((0.3, 0.6), util.color_RGB_to_xy(0, 255, 0)) self.assertEqual((0.6400744994567747, 0.3299705106316933), util.color_RGB_to_xy(255, 0, 0))
def mock_turn_on(service): """ Will fake the component has been turned on. """ if service.data and ATTR_ENTITY_ID in service.data: entity_ids = extract_entity_ids(hass, service) else: entity_ids = hass.states.entity_ids(service.domain) for entity_id in entity_ids: domain, _ = split_entity_id(entity_id) if domain == "light": rgb_color = service.data.get(ATTR_RGB_COLOR) if rgb_color: color = color_RGB_to_xy( rgb_color[0], rgb_color[1], rgb_color[2]) else: cur_state = hass.states.get(entity_id) # Use current color if available if cur_state and cur_state.attributes.get(ATTR_XY_COLOR): color = cur_state.attributes.get(ATTR_XY_COLOR) else: color = random.choice(light_colors) data = { ATTR_BRIGHTNESS: service.data.get(ATTR_BRIGHTNESS, 200), ATTR_XY_COLOR: color } else: data = None hass.states.set(entity_id, STATE_ON, data)
def mock_turn_on(service): """ Will fake the component has been turned on. """ if service.data and ATTR_ENTITY_ID in service.data: entity_ids = extract_entity_ids(hass, service) else: entity_ids = hass.states.entity_ids(service.domain) for entity_id in entity_ids: domain, _ = split_entity_id(entity_id) if domain == "light": rgb_color = service.data.get(ATTR_RGB_COLOR) if rgb_color: color = color_RGB_to_xy(rgb_color[0], rgb_color[1], rgb_color[2]) else: cur_state = hass.states.get(entity_id) # Use current color if available if cur_state and cur_state.attributes.get(ATTR_XY_COLOR): color = cur_state.attributes.get(ATTR_XY_COLOR) else: color = random.choice(light_colors) data = { ATTR_BRIGHTNESS: service.data.get(ATTR_BRIGHTNESS, 200), ATTR_XY_COLOR: color } else: data = None hass.states.set(entity_id, STATE_ON, data)
def handle_light_service(service): """ Hande a turn light on or off service call. """ # Get and validate data dat = service.data # Convert the entity ids to valid light ids light_ids = [ent_to_light[entity_id] for entity_id in extract_entity_ids(hass, service) if entity_id in ent_to_light] if not light_ids: light_ids = list(ent_to_light.values()) transition = util.convert(dat.get(ATTR_TRANSITION), int) if service.service == SERVICE_TURN_OFF: light_control.turn_light_off(light_ids, transition) else: # Processing extra data for turn light on request # We process the profile first so that we get the desired # behavior that extra service data attributes overwrite # profile values profile = profiles.get(dat.get(ATTR_PROFILE)) if profile: *color, bright = profile else: color, bright = None, None if ATTR_BRIGHTNESS in dat: bright = util.convert(dat.get(ATTR_BRIGHTNESS), int) if ATTR_XY_COLOR in dat: try: # xy_color should be a list containing 2 floats xy_color = dat.get(ATTR_XY_COLOR) if len(xy_color) == 2: color = [float(val) for val in xy_color] except (TypeError, ValueError): # TypeError if xy_color is not iterable # ValueError if value could not be converted to float pass if ATTR_RGB_COLOR in dat: try: # rgb_color should be a list containing 3 ints rgb_color = dat.get(ATTR_RGB_COLOR) if len(rgb_color) == 3: color = util.color_RGB_to_xy(int(rgb_color[0]), int(rgb_color[1]), int(rgb_color[2])) except (TypeError, ValueError): # TypeError if rgb_color is not iterable # ValueError if not all values can be converted to int pass light_control.turn_light_on(light_ids, transition, bright, color) # Update state of lights touched. If there was only 1 light selected # then just update that light else update all if len(light_ids) == 1: update_light_state(light_ids[0]) else: update_lights_state(None, True)
def test_services(self): """ Test the provided services. """ platform = loader.get_component('light.test') platform.init() self.assertTrue( light.setup(self.hass, {light.DOMAIN: {CONF_PLATFORM: 'test'}})) dev1, dev2, dev3 = platform.DEVICES # Test init self.assertTrue(light.is_on(self.hass, dev1.entity_id)) self.assertFalse(light.is_on(self.hass, dev2.entity_id)) self.assertFalse(light.is_on(self.hass, dev3.entity_id)) # Test basic turn_on, turn_off services light.turn_off(self.hass, entity_id=dev1.entity_id) light.turn_on(self.hass, entity_id=dev2.entity_id) self.hass.pool.block_till_done() self.assertFalse(light.is_on(self.hass, dev1.entity_id)) self.assertTrue(light.is_on(self.hass, dev2.entity_id)) # turn on all lights light.turn_on(self.hass) self.hass.pool.block_till_done() self.assertTrue(light.is_on(self.hass, dev1.entity_id)) self.assertTrue(light.is_on(self.hass, dev2.entity_id)) self.assertTrue(light.is_on(self.hass, dev3.entity_id)) # turn off all lights light.turn_off(self.hass) self.hass.pool.block_till_done() self.assertFalse(light.is_on(self.hass, dev1.entity_id)) self.assertFalse(light.is_on(self.hass, dev2.entity_id)) self.assertFalse(light.is_on(self.hass, dev3.entity_id)) # Ensure all attributes process correctly light.turn_on(self.hass, dev1.entity_id, transition=10, brightness=20) light.turn_on( self.hass, dev2.entity_id, rgb_color=[255, 255, 255]) light.turn_on(self.hass, dev3.entity_id, xy_color=[.4, .6]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual( {light.ATTR_TRANSITION: 10, light.ATTR_BRIGHTNESS: 20}, data) method, data = dev2.last_call('turn_on') self.assertEqual( {light.ATTR_XY_COLOR: util.color_RGB_to_xy(255, 255, 255)}, data) method, data = dev3.last_call('turn_on') self.assertEqual({light.ATTR_XY_COLOR: [.4, .6]}, data) # One of the light profiles prof_name, prof_x, prof_y, prof_bri = 'relax', 0.5119, 0.4147, 144 # Test light profiles light.turn_on(self.hass, dev1.entity_id, profile=prof_name) # Specify a profile and attributes to overwrite it light.turn_on( self.hass, dev2.entity_id, profile=prof_name, brightness=100, xy_color=[.4, .6]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual( {light.ATTR_BRIGHTNESS: prof_bri, light.ATTR_XY_COLOR: [prof_x, prof_y]}, data) method, data = dev2.last_call('turn_on') self.assertEqual( {light.ATTR_BRIGHTNESS: 100, light.ATTR_XY_COLOR: [.4, .6]}, data) # Test shitty data light.turn_on(self.hass, dev1.entity_id, profile="nonexisting") light.turn_on(self.hass, dev2.entity_id, xy_color=["bla-di-bla", 5]) light.turn_on(self.hass, dev3.entity_id, rgb_color=[255, None, 2]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual({}, data) method, data = dev2.last_call('turn_on') self.assertEqual({}, data) method, data = dev3.last_call('turn_on') self.assertEqual({}, data) # faulty attributes should not overwrite profile data light.turn_on( self.hass, dev1.entity_id, profile=prof_name, brightness='bright', rgb_color='yellowish') self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual( {light.ATTR_BRIGHTNESS: prof_bri, light.ATTR_XY_COLOR: [prof_x, prof_y]}, data)
def handle_light_service(service): """ Hande a turn light on or off service call. """ # Get and validate data dat = service.data # Convert the entity ids to valid light ids lights = [ent_to_light[entity_id] for entity_id in extract_entity_ids(hass, service) if entity_id in ent_to_light] if not lights: lights = list(ent_to_light.values()) params = {} transition = util.convert(dat.get(ATTR_TRANSITION), int) if transition is not None: params[ATTR_TRANSITION] = transition if service.service == SERVICE_TURN_OFF: for light in lights: # pylint: disable=star-args light.turn_off(**params) else: # Processing extra data for turn light on request # We process the profile first so that we get the desired # behavior that extra service data attributes overwrite # profile values profile = profiles.get(dat.get(ATTR_PROFILE)) if profile: *params[ATTR_XY_COLOR], params[ATTR_BRIGHTNESS] = profile if ATTR_BRIGHTNESS in dat: # We pass in the old value as the default parameter if parsing # of the new one goes wrong. params[ATTR_BRIGHTNESS] = util.convert( dat.get(ATTR_BRIGHTNESS), int, params.get(ATTR_BRIGHTNESS)) if ATTR_XY_COLOR in dat: try: # xy_color should be a list containing 2 floats xycolor = dat.get(ATTR_XY_COLOR) # Without this check, a xycolor with value '99' would work if not isinstance(xycolor, str): params[ATTR_XY_COLOR] = [float(val) for val in xycolor] except (TypeError, ValueError): # TypeError if xy_color is not iterable # ValueError if value could not be converted to float pass if ATTR_RGB_COLOR in dat: try: # rgb_color should be a list containing 3 ints rgb_color = dat.get(ATTR_RGB_COLOR) if len(rgb_color) == 3: params[ATTR_XY_COLOR] = \ util.color_RGB_to_xy(int(rgb_color[0]), int(rgb_color[1]), int(rgb_color[2])) except (TypeError, ValueError): # TypeError if rgb_color is not iterable # ValueError if not all values can be converted to int pass for light in lights: # pylint: disable=star-args light.turn_on(**params) for light in lights: light.update_ha_state(hass, True)
def test_services(self): """ Test the provided services. """ platform = loader.get_component('light.test') platform.init() self.assertTrue( light.setup(self.hass, {light.DOMAIN: { CONF_TYPE: 'test' }})) dev1, dev2, dev3 = platform.DEVICES # Test init self.assertTrue(light.is_on(self.hass, dev1.entity_id)) self.assertFalse(light.is_on(self.hass, dev2.entity_id)) self.assertFalse(light.is_on(self.hass, dev3.entity_id)) # Test basic turn_on, turn_off services light.turn_off(self.hass, entity_id=dev1.entity_id) light.turn_on(self.hass, entity_id=dev2.entity_id) self.hass.pool.block_till_done() self.assertFalse(light.is_on(self.hass, dev1.entity_id)) self.assertTrue(light.is_on(self.hass, dev2.entity_id)) # turn on all lights light.turn_on(self.hass) self.hass.pool.block_till_done() self.assertTrue(light.is_on(self.hass, dev1.entity_id)) self.assertTrue(light.is_on(self.hass, dev2.entity_id)) self.assertTrue(light.is_on(self.hass, dev3.entity_id)) # turn off all lights light.turn_off(self.hass) self.hass.pool.block_till_done() self.assertFalse(light.is_on(self.hass, dev1.entity_id)) self.assertFalse(light.is_on(self.hass, dev2.entity_id)) self.assertFalse(light.is_on(self.hass, dev3.entity_id)) # Ensure all attributes process correctly light.turn_on(self.hass, dev1.entity_id, transition=10, brightness=20) light.turn_on(self.hass, dev2.entity_id, rgb_color=[255, 255, 255]) light.turn_on(self.hass, dev3.entity_id, xy_color=[.4, .6]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual({ light.ATTR_TRANSITION: 10, light.ATTR_BRIGHTNESS: 20 }, data) method, data = dev2.last_call('turn_on') self.assertEqual( {light.ATTR_XY_COLOR: util.color_RGB_to_xy(255, 255, 255)}, data) method, data = dev3.last_call('turn_on') self.assertEqual({light.ATTR_XY_COLOR: [.4, .6]}, data) # One of the light profiles prof_name, prof_x, prof_y, prof_bri = 'relax', 0.5119, 0.4147, 144 # Test light profiles light.turn_on(self.hass, dev1.entity_id, profile=prof_name) # Specify a profile and attributes to overwrite it light.turn_on(self.hass, dev2.entity_id, profile=prof_name, brightness=100, xy_color=[.4, .6]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual( { light.ATTR_BRIGHTNESS: prof_bri, light.ATTR_XY_COLOR: [prof_x, prof_y] }, data) method, data = dev2.last_call('turn_on') self.assertEqual( { light.ATTR_BRIGHTNESS: 100, light.ATTR_XY_COLOR: [.4, .6] }, data) # Test shitty data light.turn_on(self.hass, dev1.entity_id, profile="nonexisting") light.turn_on(self.hass, dev2.entity_id, xy_color=["bla-di-bla", 5]) light.turn_on(self.hass, dev3.entity_id, rgb_color=[255, None, 2]) self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual({}, data) method, data = dev2.last_call('turn_on') self.assertEqual({}, data) method, data = dev3.last_call('turn_on') self.assertEqual({}, data) # faulty attributes should not overwrite profile data light.turn_on(self.hass, dev1.entity_id, profile=prof_name, brightness='bright', rgb_color='yellowish') self.hass.pool.block_till_done() method, data = dev1.last_call('turn_on') self.assertEqual( { light.ATTR_BRIGHTNESS: prof_bri, light.ATTR_XY_COLOR: [prof_x, prof_y] }, data)
def handle_light_service(service): """ Hande a turn light on or off service call. """ # Get and validate data dat = service.data # Convert the entity ids to valid light ids target_lights = component.extract_from_service(service) params = {} transition = util.convert(dat.get(ATTR_TRANSITION), int) if transition is not None: params[ATTR_TRANSITION] = transition if service.service == SERVICE_TURN_OFF: for light in target_lights: light.turn_off(**params) else: # Processing extra data for turn light on request # We process the profile first so that we get the desired # behavior that extra service data attributes overwrite # profile values profile = profiles.get(dat.get(ATTR_PROFILE)) if profile: *params[ATTR_XY_COLOR], params[ATTR_BRIGHTNESS] = profile if ATTR_BRIGHTNESS in dat: # We pass in the old value as the default parameter if parsing # of the new one goes wrong. params[ATTR_BRIGHTNESS] = util.convert( dat.get(ATTR_BRIGHTNESS), int, params.get(ATTR_BRIGHTNESS)) if ATTR_XY_COLOR in dat: try: # xy_color should be a list containing 2 floats xycolor = dat.get(ATTR_XY_COLOR) # Without this check, a xycolor with value '99' would work if not isinstance(xycolor, str): params[ATTR_XY_COLOR] = [float(val) for val in xycolor] except (TypeError, ValueError): # TypeError if xy_color is not iterable # ValueError if value could not be converted to float pass if ATTR_RGB_COLOR in dat: try: # rgb_color should be a list containing 3 ints rgb_color = dat.get(ATTR_RGB_COLOR) if len(rgb_color) == 3: params[ATTR_XY_COLOR] = \ util.color_RGB_to_xy(int(rgb_color[0]), int(rgb_color[1]), int(rgb_color[2])) except (TypeError, ValueError): # TypeError if rgb_color is not iterable # ValueError if not all values can be converted to int pass if ATTR_FLASH in dat: if dat[ATTR_FLASH] == FLASH_SHORT: params[ATTR_FLASH] = FLASH_SHORT elif dat[ATTR_FLASH] == FLASH_LONG: params[ATTR_FLASH] = FLASH_LONG for light in target_lights: light.turn_on(**params) for light in target_lights: light.update_ha_state(True)
def handle_light_service(service): """ Hande a turn light on or off service call. """ # Get and validate data dat = service.data # Convert the entity ids to valid light ids lights = [ ent_to_light[entity_id] for entity_id in extract_entity_ids(hass, service) if entity_id in ent_to_light ] if not lights: lights = list(ent_to_light.values()) transition = util.convert(dat.get(ATTR_TRANSITION), int) if service.service == SERVICE_TURN_OFF: for light in lights: light.turn_off(transition=transition) else: # Processing extra data for turn light on request # We process the profile first so that we get the desired # behavior that extra service data attributes overwrite # profile values profile = profiles.get(dat.get(ATTR_PROFILE)) if profile: *color, bright = profile else: color, bright = None, None if ATTR_BRIGHTNESS in dat: bright = util.convert(dat.get(ATTR_BRIGHTNESS), int) if ATTR_XY_COLOR in dat: try: # xy_color should be a list containing 2 floats xy_color = dat.get(ATTR_XY_COLOR) if len(xy_color) == 2: color = [float(val) for val in xy_color] except (TypeError, ValueError): # TypeError if xy_color is not iterable # ValueError if value could not be converted to float pass if ATTR_RGB_COLOR in dat: try: # rgb_color should be a list containing 3 ints rgb_color = dat.get(ATTR_RGB_COLOR) if len(rgb_color) == 3: color = util.color_RGB_to_xy(int(rgb_color[0]), int(rgb_color[1]), int(rgb_color[2])) except (TypeError, ValueError): # TypeError if rgb_color is not iterable # ValueError if not all values can be converted to int pass for light in lights: light.turn_on(transition=transition, brightness=bright, xy_color=color) for light in lights: light.update_ha_state(hass, True)