| // Copyright 2020 The Fuchsia Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| use { |
| crate::expect::{expect_call, Status}, |
| anyhow::Error, |
| fidl_fuchsia_bluetooth::Uuid as FidlUuid, |
| fidl_fuchsia_bluetooth_gatt::{ |
| self as gatt, ReadByTypeResult, RemoteServiceMarker, RemoteServiceProxy, |
| RemoteServiceRequest, RemoteServiceRequestStream, |
| }, |
| fuchsia_bluetooth::types::Uuid, |
| fuchsia_zircon::Duration, |
| }; |
| |
| /// Provides a simple mock implementation of `fuchsia.bluetooth.gatt.RemoteService`. |
| pub struct RemoteServiceMock { |
| stream: RemoteServiceRequestStream, |
| timeout: Duration, |
| } |
| |
| impl RemoteServiceMock { |
| pub fn new(timeout: Duration) -> Result<(RemoteServiceProxy, RemoteServiceMock), Error> { |
| let (proxy, stream) = fidl::endpoints::create_proxy_and_stream::<RemoteServiceMarker>()?; |
| Ok((proxy, RemoteServiceMock { stream, timeout })) |
| } |
| |
| /// Wait until a Read By Type message is received with the given `uuid`. `result` will be sent |
| /// in response to the matching FIDL request. |
| pub async fn expect_read_by_type( |
| &mut self, |
| expected_uuid: Uuid, |
| result: Result<&[ReadByTypeResult], gatt::Error>, |
| ) -> Result<(), Error> { |
| let expected_uuid: FidlUuid = expected_uuid.into(); |
| expect_call(&mut self.stream, self.timeout, move |req| { |
| if let RemoteServiceRequest::ReadByType { uuid, responder } = req { |
| if uuid == expected_uuid { |
| responder.send(result)?; |
| Ok(Status::Satisfied(())) |
| } else { |
| // Send error to unexpected request. |
| responder.send(Err(fidl_fuchsia_bluetooth_gatt::Error::Failure))?; |
| Ok(Status::Pending) |
| } |
| } else { |
| Ok(Status::Pending) |
| } |
| }) |
| .await |
| } |
| } |
| |
| #[cfg(test)] |
| mod tests { |
| use super::*; |
| use {crate::timeout_duration, futures::join}; |
| |
| #[fuchsia_async::run_until_stalled(test)] |
| async fn test_expect_read_by_type() { |
| let (proxy, mut mock) = |
| RemoteServiceMock::new(timeout_duration()).expect("failed to create mock"); |
| let uuid = Uuid::new16(0x180d); |
| let result = Ok(&[][..]); |
| |
| let fidl_uuid: FidlUuid = uuid.clone().into(); |
| let read_by_type = proxy.read_by_type(&fidl_uuid); |
| let expect = mock.expect_read_by_type(uuid, result); |
| |
| let (read_by_type_result, expect_result) = join!(read_by_type, expect); |
| let _ = read_by_type_result.expect("read by type request failed"); |
| let _ = expect_result.expect("expectation not satisfied"); |
| } |
| } |