From 0646d01152f14248d3ddb353f30fcb3b92ff6bf3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Per=20Osb=C3=A4ck?= Date: Mon, 5 Jun 2017 07:46:18 +0200 Subject: [PATCH] Add support for the expirationTime parameter. (#7895) Enabled by default in Chrome 60. Only accepts the param, doesn't act on the actual expiration date. Chrome will always pass NULL for now. https://github.com/w3c/push-api/pull/248 https://www.chromestatus.com/feature/4929396687241216 https://bugs.chromium.org/p/chromium/issues/detail?id=718837 --- homeassistant/components/notify/html5.py | 5 ++- tests/components/notify/test_html5.py | 46 ++++++++++++++++++++++++ 2 files changed, 50 insertions(+), 1 deletion(-) diff --git a/homeassistant/components/notify/html5.py b/homeassistant/components/notify/html5.py index 495fc8a3c6f..c8ff6c7aa2f 100644 --- a/homeassistant/components/notify/html5.py +++ b/homeassistant/components/notify/html5.py @@ -48,6 +48,7 @@ ATTR_ENDPOINT = 'endpoint' ATTR_KEYS = 'keys' ATTR_AUTH = 'auth' ATTR_P256DH = 'p256dh' +ATTR_EXPIRATIONTIME = 'expirationTime' ATTR_TAG = 'tag' ATTR_ACTION = 'action' @@ -71,7 +72,9 @@ SUBSCRIPTION_SCHEMA = vol.All(dict, vol.Schema({ # pylint: disable=no-value-for-parameter vol.Required(ATTR_ENDPOINT): vol.Url(), - vol.Required(ATTR_KEYS): KEYS_SCHEMA + vol.Required(ATTR_KEYS): KEYS_SCHEMA, + vol.Optional(ATTR_EXPIRATIONTIME): + vol.Any(None, cv.positive_int) })) REGISTER_SCHEMA = vol.Schema({ diff --git a/tests/components/notify/test_html5.py b/tests/components/notify/test_html5.py index ff1076d1eed..5aa8afb4f7d 100644 --- a/tests/components/notify/test_html5.py +++ b/tests/components/notify/test_html5.py @@ -34,6 +34,14 @@ SUBSCRIPTION_3 = { }, }, } +SUBSCRIPTION_4 = { + 'browser': 'chrome', + 'subscription': { + 'endpoint': 'https://google.com', + 'expirationTime': None, + 'keys': {'auth': 'auth', 'p256dh': 'p256dh'} + }, +} REGISTER_URL = '/api/notify.html5' PUBLISH_URL = '/api/notify.html5/callback' @@ -139,6 +147,44 @@ class TestHtml5Notify(object): handle = m() assert json.loads(handle.write.call_args[0][0]) == expected + @asyncio.coroutine + def test_registering_new_device_expiration_view(self, loop, test_client): + """Test that the HTML view works.""" + hass = MagicMock() + expected = { + 'unnamed device': SUBSCRIPTION_4, + } + + m = mock_open() + with patch( + 'homeassistant.components.notify.html5.open', m, create=True + ): + hass.config.path.return_value = 'file.conf' + service = html5.get_service(hass, {}) + + assert service is not None + + # assert hass.called + assert len(hass.mock_calls) == 3 + + view = hass.mock_calls[1][1][0] + assert view.json_path == hass.config.path.return_value + assert view.registrations == {} + + hass.loop = loop + app = mock_http_component_app(hass) + view.register(app.router) + client = yield from test_client(app) + hass.http.is_banned_ip.return_value = False + resp = yield from client.post(REGISTER_URL, + data=json.dumps(SUBSCRIPTION_4)) + + content = yield from resp.text() + assert resp.status == 200, content + assert view.registrations == expected + handle = m() + assert json.loads(handle.write.call_args[0][0]) == expected + @asyncio.coroutine def test_registering_new_device_validation(self, loop, test_client): """Test various errors when registering a new device."""