LCOV - code coverage report
Current view: top level - dashql-native-proxy/src/test - hyper_service_mock.rs Coverage Total Hit
Test: DashQL 6e74948 Lines: 92.0 % 25 23
Test Date: 2026-11-06 17:46:50

            Line data    Source code
       1              : use crate::proto::salesforce_hyperdb_grpc_v1::{
       2              :     hyper_service_server::{HyperService, HyperServiceServer},
       3              :     QueryParam, QueryResult,
       4              : };
       5              : use std::{net::SocketAddr, pin::Pin};
       6              : use tokio::sync::oneshot;
       7              : use tokio_stream::{wrappers::ReceiverStream, Stream};
       8              : use tonic::Status;
       9              : 
      10              : pub type QueryResultSender = tokio::sync::mpsc::Sender<Result<QueryResult, tonic::Status>>;
      11              : 
      12              : /// A Hyper gRPC service that hands every query to the test for its results
      13              : pub struct HyperServiceMock {
      14              :     /// Receives the parameters of a query together with the sender of its results
      15              :     pub setup_execute_query: tokio::sync::mpsc::Sender<(QueryParam, QueryResultSender)>,
      16              : }
      17              : 
      18              : impl HyperServiceMock {
      19            2 :     pub fn new() -> (
      20            2 :         Self,
      21            2 :         tokio::sync::mpsc::Receiver<(QueryParam, QueryResultSender)>,
      22            2 :     ) {
      23            2 :         let (send, recv) = tokio::sync::mpsc::channel(1);
      24            2 :         (Self { setup_execute_query: send }, recv)
      25            2 :     }
      26              : }
      27              : 
      28              : type ExecuteQueryResponseStream = Pin<Box<dyn Stream<Item = Result<QueryResult, Status>> + Send>>;
      29              : 
      30              : #[tonic::async_trait]
      31              : impl HyperService for HyperServiceMock {
      32              :     type ExecuteQueryStream = ExecuteQueryResponseStream;
      33              : 
      34              :     async fn execute_query(
      35              :         &self,
      36              :         request: tonic::Request<QueryParam>,
      37            2 :     ) -> Result<tonic::Response<Self::ExecuteQueryStream>, tonic::Status> {
      38              :         // Setup a channel for sending results
      39              :         let (result_sender, receive) = tokio::sync::mpsc::channel(10);
      40              :         let test_setup = self.setup_execute_query.clone();
      41              : 
      42              :         // Pass the result_sender back to the test, together with the request params
      43              :         let params = request.into_inner();
      44              :         test_setup.send((params, result_sender)).await.unwrap();
      45              : 
      46              :         // Wire up a receiver stream to the gRPC output
      47              :         let out = ReceiverStream::new(receive);
      48              :         Ok(tonic::Response::new(
      49              :             Box::pin(out) as Self::ExecuteQueryStream
      50              :         ))
      51            2 :     }
      52              : }
      53              : 
      54            2 : pub async fn spawn_hyper_service_mock(mock: HyperServiceMock) -> (SocketAddr, oneshot::Sender<()>) {
      55            2 :     let service = HyperServiceServer::new(mock);
      56              : 
      57              :     // Bind to port `0` so the OS finds a free port
      58            2 :     let listener = tokio::net::TcpListener::bind("127.0.0.1:0").await.unwrap();
      59            2 :     let addr = listener.local_addr().unwrap();
      60              : 
      61            2 :     let (shutdown_tx, shutdown_rx) = oneshot::channel::<()>();
      62              : 
      63            2 :     tokio::spawn(async move {
      64            2 :         tonic::transport::Server::builder()
      65            2 :             .add_service(service)
      66            2 :             .serve_with_incoming_shutdown(
      67            2 :                 tokio_stream::wrappers::TcpListenerStream::new(listener),
      68            2 :                 async { drop(shutdown_rx.await) },
      69              :             )
      70            2 :             .await
      71            0 :             .unwrap();
      72            0 :     });
      73            2 :     (addr, shutdown_tx)
      74            2 : }
        

Generated by: LCOV version 2.0-1