Fix bug when IQVIA API fails to return data (#23916)

* Fix bug when IQVIA API fails to return data

* Updated requirements

* Fixed tests

* Linting

* Removed impossible case

* Removed extraneous comment
This commit is contained in:
Aaron Bach 2019-05-16 15:19:53 -06:00 committed by GitHub
parent c8cf06b8b7
commit 297d24c5b0
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
7 changed files with 13 additions and 33 deletions

View File

@ -82,8 +82,9 @@ async def async_setup_entry(hass, config_entry):
Client(config_entry.data[CONF_ZIP_CODE], websession), Client(config_entry.data[CONF_ZIP_CODE], websession),
config_entry.data.get(CONF_MONITORED_CONDITIONS, list(SENSORS))) config_entry.data.get(CONF_MONITORED_CONDITIONS, list(SENSORS)))
await iqvia.async_update() await iqvia.async_update()
except IQVIAError as err: except InvalidZipError:
_LOGGER.error('Unable to set up IQVIA: %s', err) _LOGGER.error(
'Invalid ZIP code provided: %s', config_entry.data[CONF_ZIP_CODE])
return False return False
hass.data[DOMAIN][DATA_CLIENT][config_entry.entry_id] = iqvia hass.data[DOMAIN][DATA_CLIENT][config_entry.entry_id] = iqvia
@ -157,16 +158,7 @@ class IQVIAData:
results = await asyncio.gather(*tasks.values(), return_exceptions=True) results = await asyncio.gather(*tasks.values(), return_exceptions=True)
# IQVIA sites require a bit more complicated error handling, given that
# they sometimes have parts (but not the whole thing) go down:
# 1. If `InvalidZipError` is thrown, quit everything immediately.
# 2. If a single request throws any other error, try the others.
for key, result in zip(tasks, results): for key, result in zip(tasks, results):
if isinstance(result, InvalidZipError):
_LOGGER.error("No data for ZIP: %s", self._client.zip_code)
self.data = {}
return
if isinstance(result, IQVIAError): if isinstance(result, IQVIAError):
_LOGGER.error('Unable to get %s data: %s', key, result) _LOGGER.error('Unable to get %s data: %s', key, result)
self.data[key] = {} self.data[key] = {}

View File

@ -4,7 +4,7 @@ from collections import OrderedDict
import voluptuous as vol import voluptuous as vol
from pyiqvia import Client from pyiqvia import Client
from pyiqvia.errors import IQVIAError from pyiqvia.errors import InvalidZipError
from homeassistant import config_entries from homeassistant import config_entries
from homeassistant.core import callback from homeassistant.core import callback
@ -54,11 +54,10 @@ class IQVIAFlowHandler(config_entries.ConfigFlow):
return await self._show_form({CONF_ZIP_CODE: 'identifier_exists'}) return await self._show_form({CONF_ZIP_CODE: 'identifier_exists'})
websession = aiohttp_client.async_get_clientsession(self.hass) websession = aiohttp_client.async_get_clientsession(self.hass)
client = Client(user_input[CONF_ZIP_CODE], websession)
try: try:
await client.allergens.current() Client(user_input[CONF_ZIP_CODE], websession)
except IQVIAError: except InvalidZipError:
return await self._show_form({CONF_ZIP_CODE: 'invalid_zip_code'}) return await self._show_form({CONF_ZIP_CODE: 'invalid_zip_code'})
return self.async_create_entry( return self.async_create_entry(

View File

@ -5,7 +5,7 @@
"documentation": "https://www.home-assistant.io/components/iqvia", "documentation": "https://www.home-assistant.io/components/iqvia",
"requirements": [ "requirements": [
"numpy==1.16.3", "numpy==1.16.3",
"pyiqvia==0.2.0" "pyiqvia==0.2.1"
], ],
"dependencies": [], "dependencies": [],
"codeowners": [ "codeowners": [

View File

@ -106,8 +106,8 @@ class ForecastSensor(IQVIAEntity):
if not self._iqvia.data: if not self._iqvia.data:
return return
data = self._iqvia.data[self._type].get('Location') data = self._iqvia.data[self._type]['Location']
if not data: if not data.get('periods'):
return return
indices = [p['Index'] for p in data['periods']] indices = [p['Index'] for p in data['periods']]

View File

@ -1130,7 +1130,7 @@ pyicloud==0.9.1
pyipma==1.2.1 pyipma==1.2.1
# homeassistant.components.iqvia # homeassistant.components.iqvia
pyiqvia==0.2.0 pyiqvia==0.2.1
# homeassistant.components.irish_rail_transport # homeassistant.components.irish_rail_transport
pyirishrail==0.0.2 pyirishrail==0.0.2

View File

@ -235,7 +235,7 @@ pyheos==0.5.2
pyhomematic==0.1.58 pyhomematic==0.1.58
# homeassistant.components.iqvia # homeassistant.components.iqvia
pyiqvia==0.2.0 pyiqvia==0.2.1
# homeassistant.components.litejet # homeassistant.components.litejet
pylitejet==0.1 pylitejet==0.1

View File

@ -1,25 +1,16 @@
"""Define tests for the IQVIA config flow.""" """Define tests for the IQVIA config flow."""
from pyiqvia.errors import IQVIAError
import pytest import pytest
from homeassistant import data_entry_flow from homeassistant import data_entry_flow
from homeassistant.components.iqvia import CONF_ZIP_CODE, DOMAIN, config_flow from homeassistant.components.iqvia import CONF_ZIP_CODE, DOMAIN, config_flow
from tests.common import MockConfigEntry, MockDependency, mock_coro from tests.common import MockConfigEntry, MockDependency
@pytest.fixture @pytest.fixture
def allergens_current_response(): def mock_pyiqvia():
"""Define a fixture for a successful allergens.current response."""
return mock_coro()
@pytest.fixture
def mock_pyiqvia(allergens_current_response):
"""Mock the pyiqvia library.""" """Mock the pyiqvia library."""
with MockDependency('pyiqvia') as mock_pyiqvia_: with MockDependency('pyiqvia') as mock_pyiqvia_:
mock_pyiqvia_.Client().allergens.current.return_value = (
allergens_current_response)
yield mock_pyiqvia_ yield mock_pyiqvia_
@ -37,8 +28,6 @@ async def test_duplicate_error(hass):
assert result['errors'] == {CONF_ZIP_CODE: 'identifier_exists'} assert result['errors'] == {CONF_ZIP_CODE: 'identifier_exists'}
@pytest.mark.parametrize(
'allergens_current_response', [mock_coro(exception=IQVIAError)])
async def test_invalid_zip_code(hass, mock_pyiqvia): async def test_invalid_zip_code(hass, mock_pyiqvia):
"""Test that an invalid ZIP code key throws an error.""" """Test that an invalid ZIP code key throws an error."""
conf = { conf = {