From 1fda362ca392ebb205208cd84ddbd387b37c5be0 Mon Sep 17 00:00:00 2001 From: Paulus Schoutsen Date: Thu, 16 Jul 2015 21:12:18 -0700 Subject: [PATCH] Take elevation into consideration --- homeassistant/components/sun.py | 36 ++++++++++++------- ...test_component_device_sun_light_trigger.py | 2 +- tests/test_component_sun.py | 4 +-- 3 files changed, 26 insertions(+), 16 deletions(-) diff --git a/homeassistant/components/sun.py b/homeassistant/components/sun.py index a3286ebc9ee..fd2cfa46b72 100644 --- a/homeassistant/components/sun.py +++ b/homeassistant/components/sun.py @@ -32,6 +32,8 @@ REQUIREMENTS = ['astral>=0.8.1'] DOMAIN = "sun" ENTITY_ID = "sun.sun" +CONF_ELEVATION = 'elevation' + STATE_ABOVE_HORIZON = "above_horizon" STATE_BELOW_HORIZON = "below_horizon" @@ -116,7 +118,21 @@ def setup(hass, config): _LOGGER.error('Invalid configuration received: %s', ", ".join(errors)) return False - sun = Sun(hass, latitude, longitude) + platform_config = config.get(DOMAIN, {}) + + elevation = platform_config.get(CONF_ELEVATION) + + from astral import Location, GoogleGeocoder + + location = Location(('', '', latitude, longitude, hass.config.time_zone, + elevation or 0)) + + if elevation is None: + google = GoogleGeocoder() + google._get_elevation(location) # pylint: disable=protected-access + _LOGGER.info('Retrieved elevation from Google: %s', location.elevation) + + sun = Sun(hass, location) sun.point_in_time_listener(dt_util.utcnow()) return True @@ -127,13 +143,9 @@ class Sun(Entity): entity_id = ENTITY_ID - def __init__(self, hass, latitude, longitude): - from astral import Astral - + def __init__(self, hass, location): self.hass = hass - self.latitude = latitude - self.longitude = longitude - self.astral = Astral() + self.location = location self._state = self.next_rising = self.next_setting = None @property @@ -168,18 +180,16 @@ class Sun(Entity): """ Calculate sun state at a point in UTC time. """ mod = -1 while True: - next_rising_dt = self.astral.sunrise_utc( - utc_point_in_time + - timedelta(days=mod), self.latitude, self.longitude) + next_rising_dt = self.location.sunrise( + utc_point_in_time + timedelta(days=mod), local=False) if next_rising_dt > utc_point_in_time: break mod += 1 mod = -1 while True: - next_setting_dt = (self.astral.sunset_utc( - utc_point_in_time + - timedelta(days=mod), self.latitude, self.longitude)) + next_setting_dt = (self.location.sunset( + utc_point_in_time + timedelta(days=mod), local=False)) if next_setting_dt > utc_point_in_time: break mod += 1 diff --git a/tests/test_component_device_sun_light_trigger.py b/tests/test_component_device_sun_light_trigger.py index 7a05f63099f..05452a830ec 100644 --- a/tests/test_component_device_sun_light_trigger.py +++ b/tests/test_component_device_sun_light_trigger.py @@ -67,7 +67,7 @@ class TestDeviceSunLightTrigger(unittest.TestCase): light.DOMAIN: {CONF_PLATFORM: 'test'} }) - sun.setup(self.hass, {}) + sun.setup(self.hass, {sun.DOMAIN: {sun.CONF_ELEVATION: 0}}) def tearDown(self): # pylint: disable=invalid-name """ Stop down stuff we started. """ diff --git a/tests/test_component_sun.py b/tests/test_component_sun.py index d102622be8c..705caadcd3a 100644 --- a/tests/test_component_sun.py +++ b/tests/test_component_sun.py @@ -40,7 +40,7 @@ class TestSun(unittest.TestCase): # Compare it with the real data self.hass.config.latitude = latitude self.hass.config.longitude = longitude - sun.setup(self.hass, None) + sun.setup(self.hass, {sun.DOMAIN: {sun.CONF_ELEVATION: 0}}) astral = Astral() utc_now = dt_util.utcnow() @@ -77,7 +77,7 @@ class TestSun(unittest.TestCase): """ Test if the state changes at next setting/rising. """ self.hass.config.latitude = '32.87336' self.hass.config.longitude = '117.22743' - sun.setup(self.hass, None) + sun.setup(self.hass, {}) if sun.is_on(self.hass): test_state = sun.STATE_BELOW_HORIZON