diff --git a/homeassistant/components/binary_sensor/blink.py b/homeassistant/components/binary_sensor/blink.py index 1e95d4d466b9b2..35d8375e6eb970 100644 --- a/homeassistant/components/binary_sensor/blink.py +++ b/homeassistant/components/binary_sensor/blink.py @@ -15,9 +15,9 @@ def setup_platform(hass, config, add_devices, discovery_info=None): if discovery_info is None: return - data = hass.data[DOMAIN].blink + data = hass.data[DOMAIN] devs = list() - for name in data.cameras: + for name in data.blink.cameras: devs.append(BlinkCameraMotionSensor(name, data)) devs.append(BlinkSystemSensor(data)) add_devices(devs, True) @@ -31,7 +31,7 @@ def __init__(self, name, data): self._name = 'blink_' + name + '_motion_enabled' self._camera_name = name self.data = data - self._state = self.data.cameras[self._camera_name].armed + self._state = self.data.blink.cameras[self._camera_name].armed @property def name(self): @@ -45,8 +45,7 @@ def is_on(self): def update(self): """Update sensor state.""" - self.data.refresh() - self._state = self.data.cameras[self._camera_name].armed + self._state = self.data.blink.cameras[self._camera_name].armed class BlinkSystemSensor(BinarySensorDevice): @@ -56,7 +55,7 @@ def __init__(self, data): """Initialize the sensor.""" self._name = 'blink armed status' self.data = data - self._state = self.data.arm + self._state = self.data.blink.arm @property def name(self): @@ -70,5 +69,4 @@ def is_on(self): def update(self): """Update sensor state.""" - self.data.refresh() - self._state = self.data.arm + self._state = self.data.blink.arm diff --git a/homeassistant/components/blink.py b/homeassistant/components/blink.py index 4ae5007d665c4e..ae259d65e0edee 100644 --- a/homeassistant/components/blink.py +++ b/homeassistant/components/blink.py @@ -5,6 +5,8 @@ https://home-assistant.io/components/blink/ """ import logging +from datetime import timedelta +import requests import voluptuous as vol @@ -12,6 +14,7 @@ from homeassistant.const import ( CONF_USERNAME, CONF_PASSWORD, ATTR_FRIENDLY_NAME, ATTR_ARMED) from homeassistant.helpers import discovery +from homeassistant.util import Throttle REQUIREMENTS = ['blinkpy==0.5.2'] @@ -19,6 +22,9 @@ DOMAIN = 'blink' +MIN_TIME_BETWEEN_UPDATES = timedelta(seconds=180) +MIN_TIME_BETWEEN_FORCED_UPDATES = timedelta(seconds=5) + CONFIG_SCHEMA = vol.Schema({ DOMAIN: vol.Schema({ vol.Required(CONF_USERNAME): cv.string, @@ -49,6 +55,43 @@ def __init__(self, config_info): self.blink = blinkpy.Blink(username=config_info[DOMAIN][CONF_USERNAME], password=config_info[DOMAIN][CONF_PASSWORD]) self.blink.setup_system() + self._header = {} + self.ignore_throttle = False + + @Throttle(MIN_TIME_BETWEEN_UPDATES, MIN_TIME_BETWEEN_FORCED_UPDATES) + def image_request(self, image_url, **kwargs): + """Request an image from Blink servers.""" + _LOGGER.info("Requesting image from Blink servers.") + response = requests.get(image_url, headers=self._header, stream=True) + if self.ignore_throttle: + self.ignore_throttle = False + return response + + @Throttle(MIN_TIME_BETWEEN_UPDATES, MIN_TIME_BETWEEN_FORCED_UPDATES) + def update(self, **kwargs): + """Check auth token and update system.""" + # Grab random camera header, doesn't matter which one + if not self._header: + camera_name = list(self.blink.cameras.keys())[0] + self._header = self.blink.cameras[camera_name].header + _LOGGER.info("Retrieving header from %s.", camera_name) + + resp = requests.get(self.blink.urls.networks_url, + headers=self._header) + if resp.status_code is not 200: + # Can't get device data, need to get new auth token + _LOGGER.info("Received status code %d, getting new token.", + resp.status_code) + self.blink.get_auth_token() + self.blink.set_links() + self._header = {} + + self.blink.refresh() + + def force_update(self): + """Force a system update.""" + self.ignore_throttle = True + self.update(no_throttle=True) def setup(hass, config): @@ -77,7 +120,11 @@ def arm_system(call): """Arm the system.""" value = call.data.get(ATTR_ARMED, True) hass.data[DOMAIN].blink.arm = value - hass.data[DOMAIN].blink.refresh() + hass.data[DOMAIN].update() + + def force_update(call): + """Force an update.""" + hass.data[DOMAIN].force_update() hass.services.register( DOMAIN, 'snap_picture', snap_picture, schema=SNAP_PICTURE_SCHEMA) @@ -85,5 +132,7 @@ def arm_system(call): DOMAIN, 'arm_camera', arm_camera, schema=ARM_CAMERA_SCHEMA) hass.services.register( DOMAIN, 'arm_system', arm_system, schema=ARM_SYSTEM_SCHEMA) + hass.services.register( + DOMAIN, 'force_update', force_update) return True diff --git a/homeassistant/components/camera/blink.py b/homeassistant/components/camera/blink.py index 59616b0ded2900..81de6d34a8137a 100644 --- a/homeassistant/components/camera/blink.py +++ b/homeassistant/components/camera/blink.py @@ -6,17 +6,11 @@ """ import logging -from datetime import timedelta -import requests - from homeassistant.components.blink import DOMAIN from homeassistant.components.camera import Camera -from homeassistant.util import Throttle DEPENDENCIES = ['blink'] -MIN_TIME_BETWEEN_UPDATES = timedelta(seconds=90) - _LOGGER = logging.getLogger(__name__) @@ -25,9 +19,9 @@ def setup_platform(hass, config, add_devices, discovery_info=None): if discovery_info is None: return - data = hass.data[DOMAIN].blink + data = hass.data[DOMAIN] devs = list() - for name in data.cameras: + for name in data.blink.cameras: devs.append(BlinkCamera(hass, config, data, name)) add_devices(devs) @@ -42,7 +36,7 @@ def __init__(self, hass, config, data, name): self.data = data self.hass = hass self._name = name - self.notifications = self.data.cameras[self._name].notifications + self.notifications = self.data.blink.cameras[self._name].notifications self.response = None _LOGGER.info("Initialized blink camera %s", self._name) @@ -52,28 +46,28 @@ def name(self): """A camera name.""" return self._name - @Throttle(MIN_TIME_BETWEEN_UPDATES) def request_image(self): """An image request from Blink servers.""" - _LOGGER.info("Requesting new image from blink servers") image_url = self.check_for_motion() - header = self.data.cameras[self._name].header - self.response = requests.get(image_url, headers=header, stream=True) + resp = self.data.image_request(image_url, + no_throttle=self.data.ignore_throttle) + if resp is not None: + self.response = resp def check_for_motion(self): """A method to check if motion has been detected since last update.""" - self.data.refresh() - notifs = self.data.cameras[self._name].notifications + self.data.update() + notifs = self.data.blink.cameras[self._name].notifications if notifs > self.notifications: # We detected motion at some point - self.data.last_motion() + self.data.blink.last_motion() self.notifications = notifs # returning motion image currently not working # return self.data.cameras[self._name].motion['image'] elif notifs < self.notifications: self.notifications = notifs - return self.data.camera_thumbs[self._name] + return self.data.blink.camera_thumbs[self._name] def camera_image(self): """Return a still image reponse from the camera.""" diff --git a/homeassistant/components/sensor/blink.py b/homeassistant/components/sensor/blink.py index e069dfa00f7d10..50e5b8f84e721a 100644 --- a/homeassistant/components/sensor/blink.py +++ b/homeassistant/components/sensor/blink.py @@ -26,10 +26,10 @@ def setup_platform(hass, config, add_devices, discovery_info=None): if discovery_info is None: return - data = hass.data[DOMAIN].blink + data = hass.data[DOMAIN] devs = list() index = 0 - for name in data.cameras: + for name in data.blink.cameras: devs.append(BlinkSensor(name, 'temperature', index, data)) devs.append(BlinkSensor(name, 'battery', index, data)) devs.append(BlinkSensor(name, 'notifications', index, data)) @@ -73,7 +73,7 @@ def unit_of_measurement(self): def update(self): """A method to retrieve sensor data from the camera.""" - camera = self.data.cameras[self._camera_name] + camera = self.data.blink.cameras[self._camera_name] if self._type == 'temperature': self._state = camera.temperature elif self._type == 'battery':