Component setup error messages with markdown (#3919)

* Remove_dev_link_async

* callback
pull/4184/head
Johann Kellerman 2016-11-03 04:31:09 +02:00 committed by Paulus Schoutsen
parent 2940fb72fb
commit 0d14920758
1 changed files with 33 additions and 15 deletions

View File

@ -31,8 +31,8 @@ _LOGGER = logging.getLogger(__name__)
ATTR_COMPONENT = 'component'
ERROR_LOG_FILENAME = 'home-assistant.log'
_PERSISTENT_PLATFORMS = set()
_PERSISTENT_VALIDATION = set()
_PERSISTENT_ERRORS = {}
HA_COMPONENT_URL = '[{}](https://home-assistant.io/components/{}/)'
def setup_component(hass: core.HomeAssistant, domain: str,
@ -63,12 +63,14 @@ def async_setup_component(hass: core.HomeAssistant, domain: str,
# OrderedSet is empty if component or dependencies could not be resolved
if not components:
_async_persistent_notification(hass, domain, True)
return False
for component in components:
res = yield from _async_setup_component(hass, component, config)
if not res:
_LOGGER.error('Component %s failed to setup', component)
_async_persistent_notification(hass, component, True)
return False
return True
@ -87,6 +89,7 @@ def _handle_requirements(hass: core.HomeAssistant, component,
if not pkg_util.install_package(req, target=hass.config.path('deps')):
_LOGGER.error('Not initializing %s because could not install '
'dependency %s', name, req)
_async_persistent_notification(hass, name)
return False
return True
@ -114,6 +117,7 @@ def _async_setup_component(hass: core.HomeAssistant,
if domain in setup_progress:
_LOGGER.error('Attempt made to setup %s during setup of %s',
domain, domain)
_async_persistent_notification(hass, domain, True)
return False
try:
@ -131,6 +135,10 @@ def _async_setup_component(hass: core.HomeAssistant,
return False
component = loader.get_component(domain)
if component is None:
_async_persistent_notification(hass, domain)
return False
async_comp = hasattr(component, 'async_setup')
try:
@ -141,14 +149,17 @@ def _async_setup_component(hass: core.HomeAssistant,
None, component.setup, hass, config)
except Exception: # pylint: disable=broad-except
_LOGGER.exception('Error during setup of component %s', domain)
_async_persistent_notification(hass, domain, True)
return False
if result is False:
_LOGGER.error('component %s failed to initialize', domain)
_async_persistent_notification(hass, domain, True)
return False
elif result is not True:
_LOGGER.error('component %s did not return boolean if setup '
'was successful. Disabling component.', domain)
_async_persistent_notification(hass, domain, True)
loader.set_component(domain, None)
return False
@ -284,13 +295,7 @@ def async_prepare_setup_platform(hass: core.HomeAssistant, config, domain: str,
# Not found
if platform is None:
_LOGGER.error('Unable to find platform %s', platform_path)
_PERSISTENT_PLATFORMS.add(platform_path)
message = ('Unable to find the following platforms: ' +
', '.join(list(_PERSISTENT_PLATFORMS)) +
'(please check your configuration)')
persistent_notification.async_create(
hass, message, 'Invalid platforms', 'platform_errors')
_async_persistent_notification(hass, platform_path)
return None
# Already loaded
@ -305,6 +310,7 @@ def async_prepare_setup_platform(hass: core.HomeAssistant, config, domain: str,
'Unable to prepare setup for platform %s because '
'dependency %s could not be initialized', platform_path,
component)
_async_persistent_notification(hass, platform_path, True)
return None
res = yield from hass.loop.run_in_executor(
@ -552,6 +558,22 @@ def log_exception(ex, domain, config, hass):
hass.loop, async_log_exception, ex, domain, config, hass).result()
@core.callback
def _async_persistent_notification(hass: core.HomeAssistant, component: str,
link: Optional[bool]=False):
"""Print a persistent notification.
This method must be run in the event loop.
"""
_PERSISTENT_ERRORS[component] = _PERSISTENT_ERRORS.get(component) or link
_lst = [HA_COMPONENT_URL.format(name.replace('_', '-'), name)
if link else name for name, link in _PERSISTENT_ERRORS.items()]
message = ('The following components and platforms could not be set up:\n'
'* ' + '\n* '.join(list(_lst)) + '\nPlease check your config')
persistent_notification.async_create(
hass, message, 'Invalid config', 'invalid_config')
@core.callback
def async_log_exception(ex, domain, config, hass):
"""Generate log exception for config validation.
@ -559,12 +581,8 @@ def async_log_exception(ex, domain, config, hass):
This method must be run in the event loop.
"""
message = 'Invalid config for [{}]: '.format(domain)
_PERSISTENT_VALIDATION.add(domain)
message = ('The following platforms contain invalid configuration: ' +
', '.join(list(_PERSISTENT_VALIDATION)) +
' (please check your configuration). ')
persistent_notification.async_create(
hass, message, 'Invalid config', 'invalid_config')
if hass is not None:
_async_persistent_notification(hass, domain, True)
if 'extra keys not allowed' in ex.error_message:
message += '[{}] is an invalid option for [{}]. Check: {}->{}.'\