24
24
#include "utils/jsonpath.h"
25
25
#include "utils/varlena.h"
26
26
27
+ /* Special pseudo-ErrorData with zero sqlerrcode for existence queries. */
28
+ ErrorData jperNotFound [1 ];
29
+
30
+
27
31
typedef struct JsonPathExecContext
28
32
{
29
33
List * vars ;
@@ -755,12 +759,12 @@ executeComparison(JsonPathExecContext *cxt, JsonPathItem *jsp, JsonbValue *jb)
755
759
jspGetLeftArg (jsp , & elem );
756
760
res = recursiveExecuteAndUnwrap (cxt , & elem , jb , & lseq );
757
761
if (jperIsError (res ))
758
- return jpbUnknown ;
762
+ return jperReplace ( res , jpbUnknown ) ;
759
763
760
764
jspGetRightArg (jsp , & elem );
761
765
res = recursiveExecuteAndUnwrap (cxt , & elem , jb , & rseq );
762
766
if (jperIsError (res ))
763
- return jpbUnknown ;
767
+ return jperReplace ( res , jpbUnknown ) ;
764
768
765
769
while ((lval = JsonValueListNext (& lseq , & lseqit )))
766
770
{
@@ -906,14 +910,16 @@ executeBinaryArithmExpr(JsonPathExecContext *cxt, JsonPathItem *jsp,
906
910
PG_CATCH ();
907
911
{
908
912
int errcode = geterrcode ();
913
+ ErrorData * edata ;
909
914
910
915
if (ERRCODE_TO_CATEGORY (errcode ) != ERRCODE_DATA_EXCEPTION )
911
916
PG_RE_THROW ();
912
917
913
- FlushErrorState ();
914
918
MemoryContextSwitchTo (mcxt );
919
+ edata = CopyErrorData ();
920
+ FlushErrorState ();
915
921
916
- return jperMakeError ( errcode );
922
+ return jperMakeErrorData ( edata );
917
923
}
918
924
PG_END_TRY ();
919
925
@@ -940,7 +946,7 @@ executeUnaryArithmExpr(JsonPathExecContext *cxt, JsonPathItem *jsp,
940
946
jper = recursiveExecuteAndUnwrap (cxt , & elem , jb , & seq );
941
947
942
948
if (jperIsError (jper ))
943
- return jperMakeError (ERRCODE_JSON_NUMBER_NOT_FOUND );
949
+ return jperReplace ( jper , jperMakeError (ERRCODE_JSON_NUMBER_NOT_FOUND ) );
944
950
945
951
jper = jperNotFound ;
946
952
@@ -1107,7 +1113,7 @@ executeStartsWithPredicate(JsonPathExecContext *cxt, JsonPathItem *jsp,
1107
1113
jspGetRightArg (jsp , & elem );
1108
1114
res = recursiveExecute (cxt , & elem , jb , & rseq );
1109
1115
if (jperIsError (res ))
1110
- return jpbUnknown ;
1116
+ return jperReplace ( res , jpbUnknown ) ;
1111
1117
1112
1118
if (JsonValueListLength (& rseq ) != 1 )
1113
1119
return jpbUnknown ;
@@ -1123,7 +1129,7 @@ executeStartsWithPredicate(JsonPathExecContext *cxt, JsonPathItem *jsp,
1123
1129
jspGetLeftArg (jsp , & elem );
1124
1130
res = recursiveExecuteAndUnwrap (cxt , & elem , jb , & lseq );
1125
1131
if (jperIsError (res ))
1126
- return jpbUnknown ;
1132
+ return jperReplace ( res , jpbUnknown ) ;
1127
1133
1128
1134
while ((whole = JsonValueListNext (& lseq , & lit )))
1129
1135
{
@@ -1190,7 +1196,7 @@ executeLikeRegexPredicate(JsonPathExecContext *cxt, JsonPathItem *jsp,
1190
1196
jspInitByBuffer (& elem , jsp -> base , jsp -> content .like_regex .expr );
1191
1197
res = recursiveExecuteAndUnwrap (cxt , & elem , jb , & seq );
1192
1198
if (jperIsError (res ))
1193
- return jpbUnknown ;
1199
+ return jperReplace ( res , jpbUnknown ) ;
1194
1200
1195
1201
while ((str = JsonValueListNext (& seq , & it )))
1196
1202
{
@@ -1371,7 +1377,7 @@ recursiveExecuteBool(JsonPathExecContext *cxt, JsonPathItem *jsp,
1371
1377
recursiveExecute (cxt , & arg , jb , & vals );
1372
1378
1373
1379
if (jperIsError (res ))
1374
- return jpbUnknown ;
1380
+ return jperReplace ( res , jpbUnknown ) ;
1375
1381
1376
1382
return JsonValueListIsEmpty (& vals ) ? jpbFalse : jpbTrue ;
1377
1383
}
@@ -1380,7 +1386,7 @@ recursiveExecuteBool(JsonPathExecContext *cxt, JsonPathItem *jsp,
1380
1386
JsonPathExecResult res = recursiveExecute (cxt , & arg , jb , NULL );
1381
1387
1382
1388
if (jperIsError (res ))
1383
- return jpbUnknown ;
1389
+ return jperReplace ( res , jpbUnknown ) ;
1384
1390
1385
1391
return res == jperOk ? jpbTrue : jpbFalse ;
1386
1392
}
@@ -2353,59 +2359,65 @@ makePassingVars(Jsonb *jb)
2353
2359
static void
2354
2360
throwJsonPathError (JsonPathExecResult res )
2355
2361
{
2362
+ int err ;
2356
2363
if (!jperIsError (res ))
2357
2364
return ;
2358
2365
2359
- switch (jperGetError (res ))
2366
+ if (jperIsErrorData (res ))
2367
+ ThrowErrorData (jperGetErrorData (res ));
2368
+
2369
+ err = jperGetError (res );
2370
+
2371
+ switch (err )
2360
2372
{
2361
2373
case ERRCODE_JSON_ARRAY_NOT_FOUND :
2362
2374
ereport (ERROR ,
2363
- (errcode (jperGetError ( res ) ),
2375
+ (errcode (err ),
2364
2376
errmsg ("SQL/JSON array not found" )));
2365
2377
break ;
2366
2378
case ERRCODE_JSON_OBJECT_NOT_FOUND :
2367
2379
ereport (ERROR ,
2368
- (errcode (jperGetError ( res ) ),
2380
+ (errcode (err ),
2369
2381
errmsg ("SQL/JSON object not found" )));
2370
2382
break ;
2371
2383
case ERRCODE_JSON_MEMBER_NOT_FOUND :
2372
2384
ereport (ERROR ,
2373
- (errcode (jperGetError ( res ) ),
2385
+ (errcode (err ),
2374
2386
errmsg ("SQL/JSON member not found" )));
2375
2387
break ;
2376
2388
case ERRCODE_JSON_NUMBER_NOT_FOUND :
2377
2389
ereport (ERROR ,
2378
- (errcode (jperGetError ( res ) ),
2390
+ (errcode (err ),
2379
2391
errmsg ("SQL/JSON number not found" )));
2380
2392
break ;
2381
2393
case ERRCODE_JSON_SCALAR_REQUIRED :
2382
2394
ereport (ERROR ,
2383
- (errcode (jperGetError ( res ) ),
2395
+ (errcode (err ),
2384
2396
errmsg ("SQL/JSON scalar required" )));
2385
2397
break ;
2386
2398
case ERRCODE_SINGLETON_JSON_ITEM_REQUIRED :
2387
2399
ereport (ERROR ,
2388
- (errcode (jperGetError ( res ) ),
2400
+ (errcode (err ),
2389
2401
errmsg ("Singleton SQL/JSON item required" )));
2390
2402
break ;
2391
2403
case ERRCODE_NON_NUMERIC_JSON_ITEM :
2392
2404
ereport (ERROR ,
2393
- (errcode (jperGetError ( res ) ),
2405
+ (errcode (err ),
2394
2406
errmsg ("Non-numeric SQL/JSON item" )));
2395
2407
break ;
2396
2408
case ERRCODE_INVALID_JSON_SUBSCRIPT :
2397
2409
ereport (ERROR ,
2398
- (errcode (jperGetError ( res ) ),
2410
+ (errcode (err ),
2399
2411
errmsg ("Invalid SQL/JSON subscript" )));
2400
2412
break ;
2401
2413
case ERRCODE_INVALID_ARGUMENT_FOR_JSON_DATETIME_FUNCTION :
2402
2414
ereport (ERROR ,
2403
- (errcode (jperGetError ( res ) ),
2415
+ (errcode (err ),
2404
2416
errmsg ("Invalid argument for SQL/JSON datetime function" )));
2405
2417
break ;
2406
2418
default :
2407
2419
ereport (ERROR ,
2408
- (errcode (jperGetError ( res ) ),
2420
+ (errcode (err ),
2409
2421
errmsg ("Unknown SQL/JSON error" )));
2410
2422
break ;
2411
2423
}
@@ -2428,7 +2440,10 @@ jsonb_jsonpath_exists(PG_FUNCTION_ARGS)
2428
2440
PG_FREE_IF_COPY (jp , 1 );
2429
2441
2430
2442
if (jperIsError (res ))
2443
+ {
2444
+ jperFree (res );
2431
2445
PG_RETURN_NULL ();
2446
+ }
2432
2447
2433
2448
PG_RETURN_BOOL (res == jperOk );
2434
2449
}
0 commit comments