From 7d158e8cb44b602ab76a3660b9f5f5c5c5992a1f Mon Sep 17 00:00:00 2001 From: Alvaro Herrera Date: Fri, 22 Jul 2022 12:57:01 +0200 Subject: [PATCH] parser: centralize common auxiliary productions Things like "opt_name" can well be shared by various commands rather than there being multiple definitions of the same thing. Rename these productions and move them to appear together in gram.y, which may improve chances of reuse in the future. Discussion: https://postgr.es/m/20220721174212.cmitjpuimx6ssyyj@alvherre.pgsql --- src/backend/parser/gram.y | 89 +++++++++++++++++++-------------------- 1 file changed, 44 insertions(+), 45 deletions(-) diff --git a/src/backend/parser/gram.y b/src/backend/parser/gram.y index 0a874a04aa1..b761a5b5d2d 100644 --- a/src/backend/parser/gram.y +++ b/src/backend/parser/gram.y @@ -334,6 +334,11 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); simple_select values_clause PLpgSQL_Expr PLAssignStmt +%type opt_single_name +%type opt_qualified_name +%type opt_concurrently +%type opt_drop_behavior + %type alter_column_default opclass_item opclass_drop alter_using %type add_drop opt_asc_desc opt_nulls_order @@ -343,8 +348,6 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); %type alter_identity_column_option_list %type alter_identity_column_option -%type opt_drop_behavior - %type createdb_opt_list createdb_opt_items copy_opt_list transaction_mode_list create_extension_opt_list alter_extension_opt_list @@ -371,7 +374,7 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); %type foreign_server_version opt_foreign_server_version %type opt_in_database -%type OptSchemaName parameter_name +%type parameter_name %type OptSchemaEltList parameter_name_list %type am_type @@ -392,10 +395,10 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); %type copy_file_name access_method_clause attr_name table_access_method_clause name cursor_name file_name - opt_index_name cluster_index_specification + cluster_index_specification %type func_name handler_name qual_Op qual_all_Op subquery_Op - opt_class opt_inline_handler opt_validator validator_clause + opt_inline_handler opt_validator validator_clause opt_collate %type qualified_name insert_target OptConstrFromTable @@ -435,7 +438,7 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); oper_argtypes RuleActionList RuleActionMulti opt_column_list columnList opt_name_list sort_clause opt_sort_clause sortby_list index_params - opt_stats_name stats_params + stats_params opt_include opt_c_include index_including_params name_list role_list from_clause from_list opt_array_bounds qualified_name_list any_name any_name_list type_name_list @@ -495,7 +498,7 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query); %type unicode_normal_form %type opt_instead -%type opt_unique opt_concurrently opt_verbose opt_full +%type opt_unique opt_verbose opt_full %type opt_freeze opt_analyze opt_default opt_recheck %type opt_binary copy_delimiter @@ -1180,6 +1183,30 @@ stmt: { $$ = NULL; } ; +/* + * Generic supporting productions for DDL + */ +opt_single_name: + ColId { $$ = $1; } + | /* EMPTY */ { $$ = NULL; } + ; + +opt_qualified_name: + any_name { $$ = $1; } + | /*EMPTY*/ { $$ = NIL; } + ; + +opt_concurrently: + CONCURRENTLY { $$ = true; } + | /*EMPTY*/ { $$ = false; } + ; + +opt_drop_behavior: + CASCADE { $$ = DROP_CASCADE; } + | RESTRICT { $$ = DROP_RESTRICT; } + | /* EMPTY */ { $$ = DROP_RESTRICT; /* default */ } + ; + /***************************************************************************** * * CALL statement @@ -1554,7 +1581,7 @@ add_drop: ADD_P { $$ = +1; } *****************************************************************************/ CreateSchemaStmt: - CREATE SCHEMA OptSchemaName AUTHORIZATION RoleSpec OptSchemaEltList + CREATE SCHEMA opt_single_name AUTHORIZATION RoleSpec OptSchemaEltList { CreateSchemaStmt *n = makeNode(CreateSchemaStmt); @@ -1576,7 +1603,7 @@ CreateSchemaStmt: n->if_not_exists = false; $$ = (Node *) n; } - | CREATE SCHEMA IF_P NOT EXISTS OptSchemaName AUTHORIZATION RoleSpec OptSchemaEltList + | CREATE SCHEMA IF_P NOT EXISTS opt_single_name AUTHORIZATION RoleSpec OptSchemaEltList { CreateSchemaStmt *n = makeNode(CreateSchemaStmt); @@ -1610,11 +1637,6 @@ CreateSchemaStmt: } ; -OptSchemaName: - ColId { $$ = $1; } - | /* EMPTY */ { $$ = NULL; } - ; - OptSchemaEltList: OptSchemaEltList schema_stmt { @@ -2995,12 +3017,6 @@ alter_column_default: | DROP DEFAULT { $$ = NULL; } ; -opt_drop_behavior: - CASCADE { $$ = DROP_CASCADE; } - | RESTRICT { $$ = DROP_RESTRICT; } - | /* EMPTY */ { $$ = DROP_RESTRICT; /* default */ } - ; - opt_collate_clause: COLLATE any_name { @@ -4467,7 +4483,7 @@ part_params: part_elem { $$ = list_make1($1); } | part_params ',' part_elem { $$ = lappend($1, $3); } ; -part_elem: ColId opt_collate opt_class +part_elem: ColId opt_collate opt_qualified_name { PartitionElem *n = makeNode(PartitionElem); @@ -4478,7 +4494,7 @@ part_elem: ColId opt_collate opt_class n->location = @1; $$ = n; } - | func_expr_windowless opt_collate opt_class + | func_expr_windowless opt_collate opt_qualified_name { PartitionElem *n = makeNode(PartitionElem); @@ -4489,7 +4505,7 @@ part_elem: ColId opt_collate opt_class n->location = @1; $$ = n; } - | '(' a_expr ')' opt_collate opt_class + | '(' a_expr ')' opt_collate opt_qualified_name { PartitionElem *n = makeNode(PartitionElem); @@ -4543,10 +4559,12 @@ ExistingIndex: USING INDEX name { $$ = $3; } * but the grammar accepts it and then we'll throw FEATURE_NOT_SUPPORTED * errors as necessary at execution. * + * Statistics name is optional unless IF NOT EXISTS is specified. + * *****************************************************************************/ CreateStatsStmt: - CREATE STATISTICS opt_stats_name + CREATE STATISTICS opt_qualified_name opt_name_list ON stats_params FROM from_list { CreateStatsStmt *n = makeNode(CreateStatsStmt); @@ -4574,12 +4592,6 @@ CreateStatsStmt: } ; -/* Statistics name is optional unless IF NOT EXISTS is specified */ -opt_stats_name: - any_name { $$ = $1; } - | /*EMPTY*/ { $$ = NULL; } - ; - /* * Statistics attributes can be either simple column references, or arbitrary * expressions in parens. For compatibility with index attributes permitted @@ -7987,7 +7999,7 @@ defacl_privilege_target: * willing to make TABLESPACE a fully reserved word. *****************************************************************************/ -IndexStmt: CREATE opt_unique INDEX opt_concurrently opt_index_name +IndexStmt: CREATE opt_unique INDEX opt_concurrently opt_single_name ON relation_expr access_method_clause '(' index_params ')' opt_include opt_unique_null_treatment opt_reloptions OptTableSpace where_clause { @@ -8058,16 +8070,6 @@ opt_unique: | /*EMPTY*/ { $$ = false; } ; -opt_concurrently: - CONCURRENTLY { $$ = true; } - | /*EMPTY*/ { $$ = false; } - ; - -opt_index_name: - name { $$ = $1; } - | /*EMPTY*/ { $$ = NULL; } - ; - access_method_clause: USING name { $$ = $2; } | /*EMPTY*/ { $$ = DEFAULT_INDEX_TYPE; } @@ -8079,7 +8081,7 @@ index_params: index_elem { $$ = list_make1($1); } index_elem_options: - opt_collate opt_class opt_asc_desc opt_nulls_order + opt_collate opt_qualified_name opt_asc_desc opt_nulls_order { $$ = makeNode(IndexElem); $$->name = NULL; @@ -8139,9 +8141,6 @@ opt_collate: COLLATE any_name { $$ = $2; } | /*EMPTY*/ { $$ = NIL; } ; -opt_class: any_name { $$ = $1; } - | /*EMPTY*/ { $$ = NIL; } - ; opt_asc_desc: ASC { $$ = SORTBY_ASC; } | DESC { $$ = SORTBY_DESC; }