@@ -43,7 +43,6 @@ compareNumeric(Numeric a, Numeric b)
4343 );
4444}
4545
46- #define jbvScalar jbvBinary
4746static int
4847JsonbType (JsonbValue * jb )
4948{
@@ -52,15 +51,9 @@ JsonbType(JsonbValue *jb)
5251 if (jb -> type == jbvBinary )
5352 {
5453 JsonbContainer * jbc = jb -> val .binary .data ;
55-
56- if (jbc -> header & JB_FSCALAR )
54+ type = jbc -> type ;
55+ if (type == ( jbvArray | jbvScalar ) )
5756 type = jbvScalar ;
58- else if (jbc -> header & JB_FOBJECT )
59- type = jbvObject ;
60- else if (jbc -> header & JB_FARRAY )
61- type = jbvArray ;
62- else
63- elog (ERROR , "Unknown container type: 0x%08x" , jbc -> header );
6457 }
6558
6659 return type ;
@@ -174,18 +167,22 @@ checkArrayEquality(JsQueryItem *jsq, JsonbValue *jb)
174167 JsonbIterator * it ;
175168 JsonbValue v ;
176169 JsQueryItem elem ;
170+ int nelems ;
177171
178172 if (!(jsq -> type == jqiArray && JsonbType (jb ) == jbvArray ))
179173 return false;
180174
175+ nelems = JsonContainerSize (jb -> val .binary .data );
176+ if (nelems < 0 )
177+ nelems = JsonGetArraySize (jb -> val .binary .data );
178+
179+ if (nelems != jsq -> array .nelems )
180+ return false;
181181
182182 it = JsonbIteratorInit (jb -> val .binary .data );
183183 r = JsonbIteratorNext (& it , & v , true);
184184 Assert (r == WJB_BEGIN_ARRAY );
185185
186- if (v .val .array .nElems != jsq -> array .nelems )
187- return false;
188-
189186 while ((r = JsonbIteratorNext (& it , & v , true)) != WJB_DONE )
190187 {
191188 if (r != WJB_ELEM )
@@ -338,7 +335,28 @@ executeExpr(JsQueryItem *jsq, int32 op, JsonbValue *jb, JsQueryItem *jsqLeftArg)
338335 r = JsonbIteratorNext (& it , & v , true);
339336 Assert (r == WJB_BEGIN_ARRAY || r == WJB_BEGIN_OBJECT );
340337
341- length = (r == WJB_BEGIN_ARRAY ) ? v .val .array .nElems : v .val .object .nPairs ;
338+ if (r == WJB_BEGIN_ARRAY )
339+ {
340+ length = v .val .array .nElems ;
341+
342+ if (length < 0 )
343+ length = JsonGetArraySize (jb -> val .binary .data );
344+ }
345+ else
346+ {
347+ length = v .val .object .nPairs ;
348+
349+ if (length < 0 )
350+ {
351+ length = 0 ;
352+
353+ while ((r = JsonbIteratorNext (& it , & v , true)) != WJB_DONE )
354+ {
355+ if (r == WJB_KEY )
356+ length ++ ;
357+ }
358+ }
359+ }
342360
343361 v .type = jbvNumeric ;
344362 v .val .numeric = DatumGetNumeric (DirectFunctionCall1 (int4_numeric , Int32GetDatum (length )));
@@ -609,16 +627,14 @@ jsquery_json_exec(PG_FUNCTION_ARGS)
609627 JsonbValue jbv ;
610628 JsQueryItem jsq ;
611629
612- jbv .type = jbvBinary ;
613- jbv .val .binary .data = & jb -> root ;
614- jbv .val .binary .len = VARSIZE_ANY_EXHDR (jb );
630+ JsonValueInitBinary (& jbv , & jb -> root );
615631
616632 jsqInit (& jsq , jq );
617633
618634 res = recursiveExecute (& jsq , & jbv , NULL );
619635
620636 PG_FREE_IF_COPY (jq , 0 );
621- PG_FREE_IF_COPY (jb , 1 );
637+ PG_FREE_IF_COPY_JSONB (jb , 1 );
622638
623639 PG_RETURN_BOOL (res );
624640}
@@ -633,15 +649,13 @@ json_jsquery_exec(PG_FUNCTION_ARGS)
633649 JsonbValue jbv ;
634650 JsQueryItem jsq ;
635651
636- jbv .type = jbvBinary ;
637- jbv .val .binary .data = & jb -> root ;
638- jbv .val .binary .len = VARSIZE_ANY_EXHDR (jb );
652+ JsonValueInitBinary (& jbv , & jb -> root );
639653
640654 jsqInit (& jsq , jq );
641655
642656 res = recursiveExecute (& jsq , & jbv , NULL );
643657
644- PG_FREE_IF_COPY (jb , 0 );
658+ PG_FREE_IF_COPY_JSONB (jb , 0 );
645659 PG_FREE_IF_COPY (jq , 1 );
646660
647661 PG_RETURN_BOOL (res );
0 commit comments