def set_resource_value_async(self, device_id, resource_path, resource_value=None, fix_path=True): """Set resource value for given resource path, on device. Will not block. Returns immediately. Usage: .. code-block:: python a = api.set_resource_value_async(device, path, value) while not a.is_done: time.sleep(0.1) if a.error: print("Error", a.error) print("Success, new value:", a.value) :param str device_id: The name/id of the device (Required) :param str resource_path: The resource path to update (Required) :param str resource_value: The new value to set for given path :param fix_path: if True then the leading /, if found, will be stripped before doing request to backend. This is a requirement for the API to work properly :returns: An async consumer object holding reference to request :rtype: AsyncConsumer """ # When path starts with / we remove the slash, as the API can't handle //. if fix_path and resource_path.startswith("/"): resource_path = resource_path[1:] api = self._get_api(mds.ResourcesApi) resp = api.update_resource_value(device_id, resource_path, resource_value) return AsyncConsumer(resp.async_response_id, self._db)
def _mds_rpc_post(self, device_id, _wrap_with_consumer=True, async_id=None, **params): """Helper for using RPC endpoint""" self.ensure_notifications_thread() api = self._get_api(mds.DeviceRequestsApi) async_id = async_id or utils.new_async_id() device_request = mds.DeviceRequest(**params) api.create_async_request( device_id, async_id=async_id, body=device_request, ) return AsyncConsumer(async_id, self._db) if _wrap_with_consumer else async_id
def execute_resource(self, device_id, resource_path, fix_path=True, timeout=None, **kwargs): """Execute a function on a resource. Will block and wait for response to come through. Usage: .. code-block:: python try: v = api.execute_resource(device, path, function_name) print("Success, returned value:", v) except AsyncError, e: print("Error", e) :param str device_id: The name/id of the device (Required) :param str resource_path: The resource path to update (Required) :param str resource_function: The function to trigger :param fix_path: if True then the leading /, if found, will be stripped before doing request to backend. This is a requirement for the API to work properly :raises: AsyncError :returns: The value returned from the function executed on the resource :rtype: str """ # Ensure we're listening to notifications first self.ensure_notifications_thread() # When path starts with / we remove the slash, as the API can't handle //. if fix_path and resource_path.startswith("/"): resource_path = resource_path[1:] api = self._get_api(mds.ResourcesApi) resp = api.execute_or_create_resource(device_id, resource_path, **kwargs) consumer = AsyncConsumer(resp.async_response_id, self._db) return consumer.wait(timeout)
def test_async_response(self): asyncid = 'w349yw4ti7y34ti7eghiey54t' # make a fake listener result = AsyncConsumer(asyncid, self.api._db) self.assertFalse(result.is_done) # fake a response coming from a webhook receiver json_payload = json.dumps({ 'async-responses': [{ 'id': asyncid, 'status': 1, 'ct': 'tlv', 'payload': "Q2hhbmdlIG1lIQ==" }] }) self.api.notify_webhook_received(payload=json_payload) self.assertTrue(result.is_done) self.assertEqual(result.value, {'104': 'ang', '8301': 'e!'}) self.assertEqual(result.async_id, asyncid)
def execute_resource_async(self, device_id, resource_path, fix_path=True, **kwargs): """Execute a function on a resource. Will not block. Returns immediatly. Usage: .. code-block:: python a = api.execute_resource_async(device, path, function_name) while not a.is_done: time.sleep(0.1) if a.error: print("Error", a.error) print("Success, returned value:", a.value) :param str device_id: The name/id of the device (Required) :param str resource_path: The resource path to update (Required) :param str resource_function: The function to trigger :param fix_path: if True then the leading /, if found, will be stripped before doing request to backend. This is a requirement for the API to work properly :returns: An async consumer object holding reference to request :rtype: AsyncConsumer """ # When path starts with / we remove the slash, as the API can't handle //. if fix_path and resource_path.startswith("/"): resource_path = resource_path[1:] api = self._get_api(mds.ResourcesApi) resp = api.v2_endpoints_device_id_resource_path_post( device_id, resource_path, **kwargs) return AsyncConsumer(resp.async_response_id, self._db)