@@ -48,7 +48,7 @@ use crate::utils::log_plan;
48
48
use datafusion_common:: alias:: AliasGenerator ;
49
49
use datafusion_common:: config:: ConfigOptions ;
50
50
use datafusion_common:: instant:: Instant ;
51
- use datafusion_common:: { DFSchema , DataFusionError , Result } ;
51
+ use datafusion_common:: { internal_err , DFSchema , DataFusionError , Result } ;
52
52
use datafusion_expr:: logical_plan:: LogicalPlan ;
53
53
54
54
use chrono:: { DateTime , Utc } ;
@@ -80,12 +80,28 @@ pub trait OptimizerRule {
80
80
/// A human readable name for this optimizer rule
81
81
fn name ( & self ) -> & str ;
82
82
83
- /// How should the rule be applied by the optimizer? See comments on [`ApplyOrder`] for details.
83
+ /// How should the rule be applied by the optimizer? See comments on
84
+ /// [`ApplyOrder`] for details.
84
85
///
85
- /// If a rule use default None, it should traverse recursively plan inside itself
86
+ /// If returns `None`, the default, the rule must handle recursion itself
86
87
fn apply_order ( & self ) -> Option < ApplyOrder > {
87
88
None
88
89
}
90
+
91
+ /// Does this rule support rewriting owned plans (rather than by reference)?
92
+ fn supports_owned ( & self ) -> bool {
93
+ false
94
+ }
95
+
96
+ /// if supports_owned returns true, the Optimizer calls
97
+ /// [`Self::try_optimize_owned`] instead of [`Self::try_optimize`]
98
+ fn try_optimize_owned (
99
+ & self ,
100
+ _plan : LogicalPlan ,
101
+ _config : & dyn OptimizerConfig ,
102
+ ) -> Result < Transformed < LogicalPlan > , DataFusionError > {
103
+ internal_err ! ( "try_optimized_owned is not implemented for {}" , self . name( ) )
104
+ }
89
105
}
90
106
91
107
/// Options to control the DataFusion Optimizer.
@@ -297,7 +313,10 @@ fn optimize_plan_node(
297
313
rule : & dyn OptimizerRule ,
298
314
config : & dyn OptimizerConfig ,
299
315
) -> Result < Transformed < LogicalPlan > > {
300
- // TODO: introduce a better API to OptimizerRule to allow rewriting by ownership
316
+ if rule. supports_owned ( ) {
317
+ return rule. try_optimize_owned ( plan, config) ;
318
+ }
319
+
301
320
rule. try_optimize ( & plan, config) . map ( |maybe_plan| {
302
321
match maybe_plan {
303
322
Some ( new_plan) => {
0 commit comments