Skip to content

Commit 8f8bc84

Browse files
author
Commitfest Bot
committed
[CF 5478] v20 - SQL/JSON json_table PLAN clause
This branch was automatically generated by a robot using patches from an email thread registered at: https://commitfest.postgresql.org/patch/5478 The branch will be overwritten each time a new patch version is posted to the thread, and also periodically to check for bitrot caused by changes on the master branch. Patch(es): https://www.postgresql.org/message-id/CAN-LCVPSYfLZHcmvct-_nGZ7peTat-Bo--04K9VXGU8p_TcbWg@mail.gmail.com Author(s): Fedor Sigaev, Alexander Korotkov, Andrew Dunstan, Amit Langote, Nikita Glukhov, Oleg Bartunov, Anton Melnikov, Nikita Malakhov
2 parents e29df42 + 5012608 commit 8f8bc84

File tree

11 files changed

+2308
-168
lines changed

11 files changed

+2308
-168
lines changed

src/backend/nodes/makefuncs.c

+54
Original file line numberDiff line numberDiff line change
@@ -963,6 +963,60 @@ makeJsonBehavior(JsonBehaviorType btype, Node *expr, int location)
963963
return behavior;
964964
}
965965

966+
/*
967+
* makeJsonTableDefaultPlan -
968+
* creates a JsonTablePlanSpec node to represent a "default" JSON_TABLE plan
969+
* with given join strategy
970+
*/
971+
Node *
972+
makeJsonTableDefaultPlan(JsonTablePlanJoinType join_type, int location)
973+
{
974+
JsonTablePlanSpec *n = makeNode(JsonTablePlanSpec);
975+
976+
n->plan_type = JSTP_DEFAULT;
977+
n->join_type = join_type;
978+
n->location = location;
979+
980+
return (Node *) n;
981+
}
982+
983+
/*
984+
* makeJsonTableSimplePlan -
985+
* creates a JsonTablePlanSpec node to represent a "simple" JSON_TABLE plan
986+
* for given PATH
987+
*/
988+
Node *
989+
makeJsonTableSimplePlan(char *pathname, int location)
990+
{
991+
JsonTablePlanSpec *n = makeNode(JsonTablePlanSpec);
992+
993+
n->plan_type = JSTP_SIMPLE;
994+
n->pathname = pathname;
995+
n->location = location;
996+
997+
return (Node *) n;
998+
}
999+
1000+
/*
1001+
* makeJsonTableJoinedPlan -
1002+
* creates a JsonTablePlanSpec node to represent join between the given
1003+
* pair of plans
1004+
*/
1005+
Node *
1006+
makeJsonTableJoinedPlan(JsonTablePlanJoinType type, Node *plan1, Node *plan2,
1007+
int location)
1008+
{
1009+
JsonTablePlanSpec *n = makeNode(JsonTablePlanSpec);
1010+
1011+
n->plan_type = JSTP_JOINED;
1012+
n->join_type = type;
1013+
n->plan1 = castNode(JsonTablePlanSpec, plan1);
1014+
n->plan2 = castNode(JsonTablePlanSpec, plan2);
1015+
n->location = location;
1016+
1017+
return (Node *) n;
1018+
}
1019+
9661020
/*
9671021
* makeJsonKeyValue -
9681022
* creates a JsonKeyValue node

src/backend/parser/gram.y

+95-6
Original file line numberDiff line numberDiff line change
@@ -656,6 +656,14 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query);
656656
json_table
657657
json_table_column_definition
658658
json_table_column_path_clause_opt
659+
json_table_plan_clause_opt
660+
json_table_plan
661+
json_table_plan_simple
662+
json_table_plan_outer
663+
json_table_plan_inner
664+
json_table_plan_union
665+
json_table_plan_cross
666+
json_table_plan_primary
659667
%type <list> json_name_and_value_list
660668
json_value_expr_list
661669
json_array_aggregate_order_by_clause_opt
@@ -667,6 +675,9 @@ static Node *makeRecursiveViewSelect(char *relname, List *aliases, Node *query);
667675
%type <ival> json_behavior_type
668676
json_predicate_type_constraint
669677
json_quotes_clause_opt
678+
json_table_default_plan_choices
679+
json_table_default_plan_inner_outer
680+
json_table_default_plan_union_cross
670681
json_wrapper_behavior
671682
%type <boolean> json_key_uniqueness_constraint_opt
672683
json_object_constructor_null_clause_opt
@@ -14315,6 +14326,7 @@ json_table:
1431514326
json_value_expr ',' a_expr json_table_path_name_opt
1431614327
json_passing_clause_opt
1431714328
COLUMNS '(' json_table_column_definition_list ')'
14329+
json_table_plan_clause_opt
1431814330
json_on_error_clause_opt
1431914331
')'
1432014332
{
@@ -14326,13 +14338,15 @@ json_table:
1432614338
castNode(A_Const, $5)->val.node.type != T_String)
1432714339
ereport(ERROR,
1432814340
errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
14329-
errmsg("only string constants are supported in JSON_TABLE path specification"),
14341+
errmsg("only string constants are supported in"
14342+
" JSON_TABLE path specification"),
1433014343
parser_errposition(@5));
1433114344
pathstring = castNode(A_Const, $5)->val.sval.sval;
1433214345
n->pathspec = makeJsonTablePathSpec(pathstring, $6, @5, @6);
1433314346
n->passing = $7;
1433414347
n->columns = $10;
14335-
n->on_error = (JsonBehavior *) $12;
14348+
n->planspec = (JsonTablePlanSpec *) $12;
14349+
n->on_error = (JsonBehavior *) $13;
1433614350
n->location = @1;
1433714351
$$ = (Node *) n;
1433814352
}
@@ -14424,8 +14438,7 @@ json_table_column_definition:
1442414438
JsonTableColumn *n = makeNode(JsonTableColumn);
1442514439

1442614440
n->coltype = JTC_NESTED;
14427-
n->pathspec = (JsonTablePathSpec *)
14428-
makeJsonTablePathSpec($3, NULL, @3, -1);
14441+
n->pathspec = makeJsonTablePathSpec($3, NULL, @3, -1);
1442914442
n->columns = $6;
1443014443
n->location = @1;
1443114444
$$ = (Node *) n;
@@ -14436,8 +14449,7 @@ json_table_column_definition:
1443614449
JsonTableColumn *n = makeNode(JsonTableColumn);
1443714450

1443814451
n->coltype = JTC_NESTED;
14439-
n->pathspec = (JsonTablePathSpec *)
14440-
makeJsonTablePathSpec($3, $5, @3, @5);
14452+
n->pathspec = makeJsonTablePathSpec($3, $5, @3, @5);
1444114453
n->columns = $8;
1444214454
n->location = @1;
1444314455
$$ = (Node *) n;
@@ -14456,6 +14468,83 @@ json_table_column_path_clause_opt:
1445614468
{ $$ = NULL; }
1445714469
;
1445814470

14471+
json_table_plan_clause_opt:
14472+
PLAN '(' json_table_plan ')'
14473+
{ $$ = $3; }
14474+
| PLAN DEFAULT '(' json_table_default_plan_choices ')'
14475+
{ $$ = makeJsonTableDefaultPlan($4, @1); }
14476+
| /* EMPTY */
14477+
{ $$ = NULL; }
14478+
;
14479+
14480+
json_table_plan:
14481+
json_table_plan_simple
14482+
| json_table_plan_outer
14483+
| json_table_plan_inner
14484+
| json_table_plan_union
14485+
| json_table_plan_cross
14486+
;
14487+
14488+
json_table_plan_simple:
14489+
name
14490+
{ $$ = makeJsonTableSimplePlan($1, @1); }
14491+
;
14492+
14493+
json_table_plan_outer:
14494+
json_table_plan_simple OUTER_P json_table_plan_primary
14495+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_OUTER, $1, $3, @1); }
14496+
;
14497+
14498+
json_table_plan_inner:
14499+
json_table_plan_simple INNER_P json_table_plan_primary
14500+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_INNER, $1, $3, @1); }
14501+
;
14502+
14503+
json_table_plan_union:
14504+
json_table_plan_primary UNION json_table_plan_primary
14505+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_UNION, $1, $3, @1); }
14506+
| json_table_plan_union UNION json_table_plan_primary
14507+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_UNION, $1, $3, @1); }
14508+
;
14509+
14510+
json_table_plan_cross:
14511+
json_table_plan_primary CROSS json_table_plan_primary
14512+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_CROSS, $1, $3, @1); }
14513+
| json_table_plan_cross CROSS json_table_plan_primary
14514+
{ $$ = makeJsonTableJoinedPlan(JSTP_JOIN_CROSS, $1, $3, @1); }
14515+
;
14516+
14517+
json_table_plan_primary:
14518+
json_table_plan_simple
14519+
{ $$ = $1; }
14520+
| '(' json_table_plan ')'
14521+
{
14522+
castNode(JsonTablePlanSpec, $2)->location = @1;
14523+
$$ = $2;
14524+
}
14525+
;
14526+
14527+
json_table_default_plan_choices:
14528+
json_table_default_plan_inner_outer
14529+
{ $$ = $1 | JSTP_JOIN_UNION; }
14530+
| json_table_default_plan_union_cross
14531+
{ $$ = $1 | JSTP_JOIN_OUTER; }
14532+
| json_table_default_plan_inner_outer ',' json_table_default_plan_union_cross
14533+
{ $$ = $1 | $3; }
14534+
| json_table_default_plan_union_cross ',' json_table_default_plan_inner_outer
14535+
{ $$ = $1 | $3; }
14536+
;
14537+
14538+
json_table_default_plan_inner_outer:
14539+
INNER_P { $$ = JSTP_JOIN_INNER; }
14540+
| OUTER_P { $$ = JSTP_JOIN_OUTER; }
14541+
;
14542+
14543+
json_table_default_plan_union_cross:
14544+
UNION { $$ = JSTP_JOIN_UNION; }
14545+
| CROSS { $$ = JSTP_JOIN_CROSS; }
14546+
;
14547+
1445914548
/*****************************************************************************
1446014549
*
1446114550
* Type syntax

0 commit comments

Comments
 (0)