@@ -39,12 +39,14 @@ use mz_sql::catalog::{EnvironmentId, SessionCatalog};
3939use mz_sql:: session:: hint:: ApplicationNameHint ;
4040use mz_sql:: session:: metadata:: SessionMetadata ;
4141use mz_sql:: session:: user:: SUPPORT_USER ;
42- use mz_sql:: session:: vars:: { CLUSTER , OwnedVarInput , SystemVars , Var } ;
42+ use mz_sql:: session:: vars:: {
43+ CLUSTER , ENABLE_FRONTEND_PEEK_SEQUENCING , OwnedVarInput , SystemVars , Var ,
44+ } ;
4345use mz_sql_parser:: parser:: { ParserStatementError , StatementParseResult } ;
4446use prometheus:: Histogram ;
4547use serde_json:: json;
4648use tokio:: sync:: { mpsc, oneshot} ;
47- use tracing:: error;
49+ use tracing:: { debug , error} ;
4850use uuid:: Uuid ;
4951
5052use crate :: catalog:: Catalog ;
@@ -63,7 +65,7 @@ use crate::session::{
6365use crate :: statement_logging:: { StatementEndedExecutionReason , StatementExecutionStrategy } ;
6466use crate :: telemetry:: { self , EventDetails , SegmentClientExt , StatementFailureType } ;
6567use crate :: webhook:: AppendWebhookResponse ;
66- use crate :: { AdapterNotice , AppendWebhookError , PeekResponseUnary , StartupResponse } ;
68+ use crate :: { AdapterNotice , AppendWebhookError , PeekClient , PeekResponseUnary , StartupResponse } ;
6769
6870/// A handle to a running coordinator.
6971///
@@ -252,21 +254,36 @@ impl Client {
252254
253255 // Create the client as soon as startup succeeds (before any await points) so its `Drop` can
254256 // handle termination.
257+ // Build the PeekClient with controller handles returned from startup.
258+ let StartupResponse {
259+ role_id,
260+ write_notify,
261+ session_defaults,
262+ catalog,
263+ storage_collections,
264+ transient_id_gen,
265+ optimizer_metrics,
266+ persist_client,
267+ } = response;
268+
269+ let peek_client = PeekClient :: new (
270+ self . clone ( ) ,
271+ storage_collections,
272+ transient_id_gen,
273+ optimizer_metrics,
274+ persist_client,
275+ ) ;
276+
255277 let mut client = SessionClient {
256278 inner : Some ( self . clone ( ) ) ,
257279 session : Some ( session) ,
258280 timeouts : Timeout :: new ( ) ,
259281 environment_id : self . environment_id . clone ( ) ,
260282 segment_client : self . segment_client . clone ( ) ,
283+ peek_client,
284+ enable_frontend_peek_sequencing : false , // initialized below, once we have a ConnCatalog
261285 } ;
262286
263- let StartupResponse {
264- role_id,
265- write_notify,
266- session_defaults,
267- catalog,
268- } = response;
269-
270287 let session = client. session ( ) ;
271288 session. initialize_role_metadata ( role_id) ;
272289 let vars_mut = session. vars_mut ( ) ;
@@ -396,6 +413,10 @@ Issue a SQL query to get started. Need help?
396413 }
397414 }
398415
416+ client. enable_frontend_peek_sequencing = ENABLE_FRONTEND_PEEK_SEQUENCING
417+ . require ( catalog. system_vars ( ) )
418+ . is_ok ( ) ;
419+
399420 Ok ( client)
400421 }
401422
@@ -412,7 +433,7 @@ Issue a SQL query to get started. Need help?
412433 pub async fn support_execute_one (
413434 & self ,
414435 sql : & str ,
415- ) -> Result < Pin < Box < dyn Stream < Item = PeekResponseUnary > + Send + Sync > > , anyhow:: Error > {
436+ ) -> Result < Pin < Box < dyn Stream < Item = PeekResponseUnary > + Send > > , anyhow:: Error > {
416437 // Connect to the coordinator.
417438 let conn_id = self . new_conn_id ( ) ?;
418439 let session = self . new_session ( SessionConfig {
@@ -503,7 +524,7 @@ Issue a SQL query to get started. Need help?
503524 }
504525
505526 #[ instrument( level = "debug" ) ]
506- fn send ( & self , cmd : Command ) {
527+ pub ( crate ) fn send ( & self , cmd : Command ) {
507528 self . inner_cmd_tx
508529 . send ( ( OpenTelemetryContext :: obtain ( ) , cmd) )
509530 . expect ( "coordinator unexpectedly gone" ) ;
@@ -524,6 +545,13 @@ pub struct SessionClient {
524545 timeouts : Timeout ,
525546 segment_client : Option < mz_segment:: Client > ,
526547 environment_id : EnvironmentId ,
548+ /// Client for frontend peek sequencing; populated at connection startup.
549+ peek_client : PeekClient ,
550+ /// Whether frontend peek sequencing is enabled; initialized at connection startup.
551+ // TODO(peek-seq): Currently, this is initialized only at session startup. We'll be able to
552+ // check the actual feature flag value at every peek (without a Coordinator call) once we'll
553+ // always have a catalog snapshot at hand.
554+ pub enable_frontend_peek_sequencing : bool ,
527555}
528556
529557impl SessionClient {
@@ -672,6 +700,17 @@ impl SessionClient {
672700 outer_ctx_extra : Option < ExecuteContextExtra > ,
673701 ) -> Result < ( ExecuteResponse , Instant ) , AdapterError > {
674702 let execute_started = Instant :: now ( ) ;
703+
704+ // Attempt peek sequencing in the session task.
705+ // If unsupported, fall back to the Coordinator path.
706+ // TODO(peek-seq): wire up cancel_future
707+ if let Some ( resp) = self . try_frontend_peek ( & portal_name) . await ? {
708+ debug ! ( "frontend peek succeeded" ) ;
709+ return Ok ( ( resp, execute_started) ) ;
710+ } else {
711+ debug ! ( "frontend peek did not happen" ) ;
712+ }
713+
675714 let response = self
676715 . send_with_cancel (
677716 |tx, session| Command :: Execute {
@@ -973,7 +1012,9 @@ impl SessionClient {
9731012 | Command :: Terminate { .. }
9741013 | Command :: RetireExecute { .. }
9751014 | Command :: CheckConsistency { .. }
976- | Command :: Dump { .. } => { }
1015+ | Command :: Dump { .. }
1016+ | Command :: GetComputeInstanceClient { .. }
1017+ | Command :: GetOracle { .. } => { }
9771018 } ;
9781019 cmd
9791020 } ) ;
@@ -1045,6 +1086,34 @@ impl SessionClient {
10451086 pub async fn recv_timeout ( & mut self ) -> Option < TimeoutType > {
10461087 self . timeouts . recv ( ) . await
10471088 }
1089+
1090+ /// Returns a reference to the PeekClient used for frontend peek sequencing.
1091+ pub fn peek_client ( & self ) -> & PeekClient {
1092+ & self . peek_client
1093+ }
1094+
1095+ /// Returns a reference to the PeekClient used for frontend peek sequencing.
1096+ pub fn peek_client_mut ( & mut self ) -> & mut PeekClient {
1097+ & mut self . peek_client
1098+ }
1099+
1100+ /// Attempt to sequence a peek from the session task.
1101+ ///
1102+ /// Returns Some(response) if we handled the peek, or None to fall back to the Coordinator's
1103+ /// peek sequencing.
1104+ pub ( crate ) async fn try_frontend_peek (
1105+ & mut self ,
1106+ portal_name : & str ,
1107+ ) -> Result < Option < ExecuteResponse > , AdapterError > {
1108+ if self . enable_frontend_peek_sequencing {
1109+ let session = self . session . as_mut ( ) . expect ( "SessionClient invariant" ) ;
1110+ self . peek_client
1111+ . try_frontend_peek_inner ( portal_name, session)
1112+ . await
1113+ } else {
1114+ Ok ( None )
1115+ }
1116+ }
10481117}
10491118
10501119impl Drop for SessionClient {
0 commit comments