use google_cloud_spanner::client::Spanner;
use google_cloud_spanner::statement::Statement;
use google_cloud_test_macros::tokio_test_no_panics;
use spanner_grpc_mock::MockSpanner;
use spanner_grpc_mock::google::spanner::v1 as mock_v1;
use spanner_grpc_mock::start;
#[tokio_test_no_panics]
async fn test_execute_query() -> anyhow::Result<()> {
let mut mock = MockSpanner::new();
mock.expect_create_session().once().returning(|_| {
Ok(gaxi::grpc::tonic::Response::new(mock_v1::Session {
name: "projects/p/instances/i/databases/d/sessions/123".to_string(),
..Default::default()
}))
});
mock.expect_execute_streaming_sql().once().returning(|req| {
let req = req.into_inner();
assert_eq!(
req.session,
"projects/p/instances/i/databases/d/sessions/123"
);
assert_eq!(req.sql, "SELECT 1");
let result_set = mock_v1::PartialResultSet {
metadata: Some(mock_v1::ResultSetMetadata {
row_type: Some(mock_v1::StructType {
fields: vec![spanner_grpc_mock::google::spanner::v1::struct_type::Field {
name: "column1".to_string(),
r#type: Some(spanner_grpc_mock::google::spanner::v1::Type {
code: spanner_grpc_mock::google::spanner::v1::TypeCode::String as i32,
array_element_type: None,
struct_type: None,
type_annotation: 0,
proto_type_fqn: "".to_string(),
}),
}],
}),
transaction: None,
undeclared_parameters: None,
}),
values: vec![prost_types::Value {
kind: Some(prost_types::value::Kind::StringValue("1".to_string())),
}],
chunked_value: false,
resume_token: vec![],
stats: None,
precommit_token: None,
cache_update: None,
last: true,
};
let (tx, rx) = tokio::sync::mpsc::channel(1);
tx.try_send(Ok(result_set)).expect("always succeeds");
Ok(gaxi::grpc::tonic::Response::from(rx))
});
let (address, _server) = start("0.0.0.0:0", mock)
.await
.expect("Failed to start mock server");
let spanner = Spanner::builder()
.with_endpoint(address)
.with_credentials(google_cloud_auth::credentials::anonymous::Builder::new().build())
.build()
.await
.expect("Failed to build client");
let db_client = spanner
.database_client("projects/p/instances/i/databases/d")
.build()
.await
.expect("Failed to create DatabaseClient");
let tx = db_client.single_use().build();
let stmt = Statement::builder("SELECT 1").build();
let mut rs = tx.execute_query(stmt).await?;
let row = rs.next().await.expect("has row").expect("has valid row");
let val: &str = row.raw_values()[0].as_string();
assert_eq!(val, "1");
assert!(rs.next().await.is_none());
Ok(())
}