@@ -7,8 +7,10 @@ use serde_yaml::Value as YamlValue;
77use std:: path:: Path ;
88
99pub use config:: input:: ControllerConfig ;
10+ pub use config:: input:: SQLControllerConfig ;
1011pub use error:: ControllerError ;
1112pub use output:: generator:: { GeneratorOutput , PuntedQuery } ;
13+ pub use output:: sql_generator:: SQLRuntimeOptions ;
1214
1315#[ derive( Debug , Clone , Copy , PartialEq , Eq ) ]
1416pub enum StreamingEngine {
@@ -162,6 +164,117 @@ impl PlannerOutput {
162164 pub fn to_inference_yaml_string ( & self ) -> Result < String , anyhow:: Error > {
163165 Ok ( serde_yaml:: to_string ( & self . inference_yaml ) ?)
164166 }
167+
168+ /// Returns the table_name field of the first aggregation matching agg_type.
169+ pub fn aggregation_table_name ( & self , agg_type : & str ) -> Option < String > {
170+ if let YamlValue :: Mapping ( root) = & self . streaming_yaml {
171+ if let Some ( YamlValue :: Sequence ( aggs) ) = root. get ( "aggregations" ) {
172+ for agg in aggs {
173+ if let YamlValue :: Mapping ( m) = agg {
174+ if let Some ( YamlValue :: String ( t) ) = m. get ( "aggregationType" ) {
175+ if t == agg_type {
176+ if let Some ( YamlValue :: String ( name) ) = m. get ( "table_name" ) {
177+ return Some ( name. clone ( ) ) ;
178+ }
179+ }
180+ }
181+ }
182+ }
183+ }
184+ }
185+ None
186+ }
187+
188+ /// Returns the value_column field of the first aggregation matching agg_type.
189+ pub fn aggregation_value_column ( & self , agg_type : & str ) -> Option < String > {
190+ if let YamlValue :: Mapping ( root) = & self . streaming_yaml {
191+ if let Some ( YamlValue :: Sequence ( aggs) ) = root. get ( "aggregations" ) {
192+ for agg in aggs {
193+ if let YamlValue :: Mapping ( m) = agg {
194+ if let Some ( YamlValue :: String ( t) ) = m. get ( "aggregationType" ) {
195+ if t == agg_type {
196+ if let Some ( YamlValue :: String ( col) ) = m. get ( "value_column" ) {
197+ return Some ( col. clone ( ) ) ;
198+ }
199+ }
200+ }
201+ }
202+ }
203+ }
204+ }
205+ None
206+ }
207+
208+ /// Returns true if any aggregation has the matching type AND sub_type.
209+ pub fn has_aggregation_type_and_sub_type ( & self , agg_type : & str , sub_type : & str ) -> bool {
210+ if let YamlValue :: Mapping ( root) = & self . streaming_yaml {
211+ if let Some ( YamlValue :: Sequence ( aggs) ) = root. get ( "aggregations" ) {
212+ return aggs. iter ( ) . any ( |agg| {
213+ if let YamlValue :: Mapping ( m) = agg {
214+ let type_matches = m. get ( "aggregationType" ) . and_then ( |v| {
215+ if let YamlValue :: String ( s) = v {
216+ Some ( s. as_str ( ) )
217+ } else {
218+ None
219+ }
220+ } ) == Some ( agg_type) ;
221+ let sub_matches = m. get ( "aggregationSubType" ) . and_then ( |v| {
222+ if let YamlValue :: String ( s) = v {
223+ Some ( s. as_str ( ) )
224+ } else {
225+ None
226+ }
227+ } ) == Some ( sub_type) ;
228+ type_matches && sub_matches
229+ } else {
230+ false
231+ }
232+ } ) ;
233+ }
234+ }
235+ false
236+ }
237+ }
238+
239+ pub struct SQLController {
240+ config : SQLControllerConfig ,
241+ options : SQLRuntimeOptions ,
242+ }
243+
244+ impl SQLController {
245+ pub fn from_file ( path : & Path , opts : SQLRuntimeOptions ) -> Result < Self , ControllerError > {
246+ let yaml_str = std:: fs:: read_to_string ( path) ?;
247+ Self :: from_yaml ( & yaml_str, opts)
248+ }
249+
250+ pub fn from_yaml ( yaml : & str , opts : SQLRuntimeOptions ) -> Result < Self , ControllerError > {
251+ let config: SQLControllerConfig = serde_yaml:: from_str ( yaml) ?;
252+ Ok ( Self {
253+ config,
254+ options : opts,
255+ } )
256+ }
257+
258+ pub fn generate ( & self ) -> Result < PlannerOutput , ControllerError > {
259+ let output = output:: sql_generator:: generate_sql_plan ( & self . config , & self . options ) ?;
260+ Ok ( PlannerOutput {
261+ punted_queries : output. punted_queries ,
262+ streaming_yaml : output. streaming_yaml ,
263+ inference_yaml : output. inference_yaml ,
264+ aggregation_count : output. aggregation_count ,
265+ query_count : output. query_count ,
266+ } )
267+ }
268+
269+ pub fn generate_to_dir ( & self , dir : & Path ) -> Result < PlannerOutput , ControllerError > {
270+ let output = self . generate ( ) ?;
271+ std:: fs:: create_dir_all ( dir) ?;
272+ let streaming_str = serde_yaml:: to_string ( & output. streaming_yaml ) ?;
273+ let inference_str = serde_yaml:: to_string ( & output. inference_yaml ) ?;
274+ std:: fs:: write ( dir. join ( "streaming_config.yaml" ) , streaming_str) ?;
275+ std:: fs:: write ( dir. join ( "inference_config.yaml" ) , inference_str) ?;
276+ Ok ( output)
277+ }
165278}
166279
167280impl Controller {
0 commit comments