PostgreSQL的prepare 和 execute 动作背后
我给PostgreSQL的源代码加入了调试信息以后,会有如下表现:
我执行Prepare:
postgres=# prepare s(int) as select * from tst01 t where id < $1; PREPARE postgres=#
背后的反应:
** In PostgresMain In exec_simple_query loop for parsetree_list++++++++++++++++++++++++++Before pg_plan_queries ***************In pg_plan_queries -------start ................In pg_plan_queries...query->commandType == CMD_UTILITY ***************In pg_plan_queries -------end In exec_simple_query loop for parsetree_list++++++++++++++++++++++++++After pg_plan_queries ...In exec_simple_query....Before PortalRun .....In PortalRun ------------start .......In PortalRunUtility ---------------start .........In ProcessUtility----Start .........In ProcessUtility----End .......In PortalRunUtility ---------------end .....In PortalRun ------------end ...In exec_simple_query....After PortalRun
接着执行 Execute:
postgres=# execute s(2); id ---- 1 (1 row) postgres=#
背后的反应:
In exec_simple_query loop for parsetree_list++++++++++++++++++++++++++Before pg_plan_queries ***************In pg_plan_queries -------start ................In pg_plan_queries...query->commandType == CMD_UTILITY ***************In pg_plan_queries -------end In exec_simple_query loop for parsetree_list++++++++++++++++++++++++++After pg_plan_queries ...In exec_simple_query....Before PortalRun .....In PortalRun ------------start xxxxxxIn FillPortalStore ...........start .......In PortalRunUtility ---------------start .........In ProcessUtility----Start ..........In standard_ProcessUtility ... Before ExecuteQuery xxxxxxxxxxxIn ExecuteQuery--------start ++++++++++++In GetCachedPlan ........start .............In BuildCachedPlan, Before pg_plan_queries ***************In pg_plan_queries -------start ................In pg_plan_queries...query->commandType != CMD_UTILITY ..................In pg_plan_query........start *******************In planner ........start ___________________In standard_planner........start ********************In subquery_planner........start ++++++++++++++++++++++In grouping_planner......start ************************In query_planner......start ........................In make_one_rel......start ...........................In set_base_rel_pathlists......start -----------------------------In set_rel_pathlist......start ******************************In set_plain_rel_pathlist......start -------------------------------Before add_path of seqscan -------------------------------After add_path of seqscan -------------------------------Before create_index_paths -------------------------------After create_index_path -------------------------------Before create_tidscan_paths -------------------------------After create_tidscan_paths -------------------------------Before set_cheapest -------------------------------After set_cheapest ******************************In set_plain_rel_pathlist......end -----------------------------In set_rel_pathlist......end ...........................In set_base_rel_pathlists......end ........................In make_one_rel......end ************************In query_planner......end ++++++++++++++++++++++In grouping_planner......end ********************In subquery_planner........end ___________________In standard_planner........end *******************In planner ........end ..................In pg_plan_query........end ***************In pg_plan_queries -------end .............In BuildCachedPlan, After pg_plan_queries ++++++++++++In GetCachedPlan ........end .....In PortalRun ------------start .....In PortalRun ------------end xxxxxxxxxxxIn ExecuteQuery--------end ..........In standard_ProcessUtility ... After ExecuteQuery .........In ProcessUtility----End .......In PortalRunUtility ---------------end xxxxxxIn FillPortalStore ...........end .....In PortalRun ------------end ...In exec_simple_query....After PortalRun
按照对过去版本的认识,应当是PortalRun的时候单纯执行计划。
但是preapre....execute 方式,把它破坏了。
可以看到,prepare时候,不进行path的生成。
execute 的时候,在PortalRun的阶段,通过 ExecuteQuery->GetCachedPlan->BuildCachedPlan,
来生成path和确定plan。
不过要注意到一点是,我所执行的上述的例子中,并没有导致 param_info 非空。
可以说,这种针对单一表的preapre execute,是把执行计划的生成推后了,但是并不等于它就是 Parameterized Path。