Make EntityComponent update process more robust. (#5943)

* Make EntityComponent update process more robust.

* address paulus comments

* Add platform to log message.
pull/5995/head
Pascal Vizeli 2017-02-14 18:32:40 +01:00 committed by Paulus Schoutsen
parent cd9f3fa215
commit 4b8e6e36b6
1 changed files with 18 additions and 11 deletions

View File

@ -41,7 +41,7 @@ class EntityComponent(object):
self.config = None
self._platforms = {
'core': EntityPlatform(self, self.scan_interval, None),
'core': EntityPlatform(self, domain, self.scan_interval, None),
}
self.async_add_entities = self._platforms['core'].async_add_entities
self.add_entities = self._platforms['core'].add_entities
@ -134,8 +134,8 @@ class EntityComponent(object):
key = (platform_type, scan_interval, entity_namespace)
if key not in self._platforms:
self._platforms[key] = EntityPlatform(self, scan_interval,
entity_namespace)
self._platforms[key] = EntityPlatform(
self, platform_type, scan_interval, entity_namespace)
entity_platform = self._platforms[key]
try:
@ -284,14 +284,15 @@ class EntityComponent(object):
class EntityPlatform(object):
"""Keep track of entities for a single platform and stay in loop."""
def __init__(self, component, scan_interval, entity_namespace):
def __init__(self, component, platform, scan_interval, entity_namespace):
"""Initalize the entity platform."""
self.component = component
self.platform = platform
self.scan_interval = scan_interval
self.entity_namespace = entity_namespace
self.platform_entities = []
self._async_unsub_polling = None
self._process_updates = False
self._process_updates = asyncio.Lock(loop=component.hass.loop)
def add_entities(self, new_entities, update_before_add=False):
"""Add entities for a single platform."""
@ -364,11 +365,14 @@ class EntityPlatform(object):
This method must be run in the event loop.
"""
if self._process_updates:
if self._process_updates.locked():
self.component.logger.warning(
"Updating %s %s took longer than the scheduled update "
"interval %s", self.platform, self.component.domain,
self.scan_interval)
return
self._process_updates = True
try:
with (yield from self._process_updates):
tasks = []
to_update = []
@ -384,9 +388,12 @@ class EntityPlatform(object):
to_update.append(update_coro)
for update_coro in to_update:
yield from update_coro
try:
yield from update_coro
except Exception: # pylint: disable=broad-except
self.component.logger.exception(
'Error while update entity from %s in %s',
self.platform, self.component.domain)
if tasks:
yield from asyncio.wait(tasks, loop=self.component.hass.loop)
finally:
self._process_updates = False