blob: 3636d36655cfdf5aaf7073a5bb2a48fe5f4df9d6 [file] [log] [blame]
drh5fa5c102015-08-12 16:49:40 +00001/*
2** 2015-08-12
3**
4** The author disclaims copyright to this source code. In place of
5** a legal notice, here is a blessing:
6**
7** May you do good and not evil.
8** May you find forgiveness for yourself and forgive others.
9** May you share freely, never taking more than you give.
10**
11******************************************************************************
12**
drh9dbf96b2022-01-06 01:40:09 +000013** This SQLite JSON functions.
drh5fa5c102015-08-12 16:49:40 +000014**
drh9dbf96b2022-01-06 01:40:09 +000015** This file began as an extension in ext/misc/json1.c in 2015. That
16** extension proved so useful that it has now been moved into the core.
drh5fa5c102015-08-12 16:49:40 +000017**
drh5634cc02015-08-17 11:28:03 +000018** For the time being, all JSON is stored as pure text. (We might add
19** a JSONB type in the future which stores a binary encoding of JSON in
drhcb6c6c62015-08-19 22:47:17 +000020** a BLOB, but there is no support for JSONB in the current implementation.
21** This implementation parses JSON text at 250 MB/s, so it is hard to see
22** how JSONB might improve on that.)
drh5fa5c102015-08-12 16:49:40 +000023*/
drh9dbf96b2022-01-06 01:40:09 +000024#ifndef SQLITE_OMIT_JSON
25#include "sqliteInt.h"
dan2e8f5512015-09-17 17:21:09 +000026
drh95677942015-09-24 01:06:37 +000027/*
28** Growing our own isspace() routine this way is twice as fast as
29** the library isspace() function, resulting in a 7% overall performance
30** increase for the parser. (Ubuntu14.10 gcc 4.8.4 x64 with -Os).
31*/
32static const char jsonIsSpace[] = {
drhb9e8f592015-10-16 15:16:06 +000033 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 0,
drh95677942015-09-24 01:06:37 +000034 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
35 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
36 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
37 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
38 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
39 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
40 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
41 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
42 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
43 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
44 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
45 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
46 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
47 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
48 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
49};
drh9dbf96b2022-01-06 01:40:09 +000050#define fast_isspace(x) (jsonIsSpace[(unsigned char)x])
drh95677942015-09-24 01:06:37 +000051
drh16fc5e62021-11-01 12:53:01 +000052#if !defined(SQLITE_DEBUG) && !defined(SQLITE_COVERAGE_TEST)
drh285f2ef2021-10-15 16:15:04 +000053# define VVA(X)
54#else
55# define VVA(X) X
56#endif
57
drh52216ad2015-08-18 02:28:03 +000058/* Objects */
drh505ad2c2015-08-21 17:33:11 +000059typedef struct JsonString JsonString;
drh52216ad2015-08-18 02:28:03 +000060typedef struct JsonNode JsonNode;
61typedef struct JsonParse JsonParse;
62
drh5634cc02015-08-17 11:28:03 +000063/* An instance of this object represents a JSON string
64** under construction. Really, this is a generic string accumulator
65** that can be and is used to create strings other than JSON.
drh5fa5c102015-08-12 16:49:40 +000066*/
drh505ad2c2015-08-21 17:33:11 +000067struct JsonString {
drh5fa5c102015-08-12 16:49:40 +000068 sqlite3_context *pCtx; /* Function context - put error messages here */
drh5634cc02015-08-17 11:28:03 +000069 char *zBuf; /* Append JSON content here */
drh5fa5c102015-08-12 16:49:40 +000070 u64 nAlloc; /* Bytes of storage available in zBuf[] */
71 u64 nUsed; /* Bytes of zBuf[] currently used */
72 u8 bStatic; /* True if zBuf is static space */
drhd0960592015-08-17 21:22:32 +000073 u8 bErr; /* True if an error has been encountered */
drh5fa5c102015-08-12 16:49:40 +000074 char zSpace[100]; /* Initial static space */
75};
76
drhe9c37f32015-08-15 21:25:36 +000077/* JSON type values
drhbd0621b2015-08-13 13:54:59 +000078*/
drhe9c37f32015-08-15 21:25:36 +000079#define JSON_NULL 0
80#define JSON_TRUE 1
81#define JSON_FALSE 2
82#define JSON_INT 3
83#define JSON_REAL 4
84#define JSON_STRING 5
85#define JSON_ARRAY 6
86#define JSON_OBJECT 7
87
drhf5ddb9c2015-09-11 00:06:41 +000088/* The "subtype" set for JSON values */
89#define JSON_SUBTYPE 74 /* Ascii for "J" */
90
drh987eb1f2015-08-17 15:17:37 +000091/*
92** Names of the various JSON types:
93*/
94static const char * const jsonType[] = {
95 "null", "true", "false", "integer", "real", "text", "array", "object"
96};
97
drh301eecc2015-08-17 20:14:19 +000098/* Bit values for the JsonNode.jnFlag field
99*/
100#define JNODE_RAW 0x01 /* Content is raw, not JSON encoded */
101#define JNODE_ESCAPE 0x02 /* Content is text with \ escapes */
102#define JNODE_REMOVE 0x04 /* Do not output */
drh633647a2017-03-22 21:24:31 +0000103#define JNODE_REPLACE 0x08 /* Replace with JsonNode.u.iReplace */
104#define JNODE_PATCH 0x10 /* Patch with JsonNode.u.pPatch */
105#define JNODE_APPEND 0x20 /* More ARRAY/OBJECT entries at u.iAppend */
106#define JNODE_LABEL 0x40 /* Is a label of an object */
drh301eecc2015-08-17 20:14:19 +0000107
drh987eb1f2015-08-17 15:17:37 +0000108
drhe9c37f32015-08-15 21:25:36 +0000109/* A single node of parsed JSON
110*/
drhe9c37f32015-08-15 21:25:36 +0000111struct JsonNode {
drh5634cc02015-08-17 11:28:03 +0000112 u8 eType; /* One of the JSON_ type values */
drh301eecc2015-08-17 20:14:19 +0000113 u8 jnFlags; /* JNODE flags */
drh285f2ef2021-10-15 16:15:04 +0000114 u8 eU; /* Which union element to use */
drhe9c37f32015-08-15 21:25:36 +0000115 u32 n; /* Bytes of content, or number of sub-nodes */
drh52216ad2015-08-18 02:28:03 +0000116 union {
drh285f2ef2021-10-15 16:15:04 +0000117 const char *zJContent; /* 1: Content for INT, REAL, and STRING */
118 u32 iAppend; /* 2: More terms for ARRAY and OBJECT */
119 u32 iKey; /* 3: Key for ARRAY objects in json_tree() */
120 u32 iReplace; /* 4: Replacement content for JNODE_REPLACE */
121 JsonNode *pPatch; /* 5: Node chain of patch for JNODE_PATCH */
drh52216ad2015-08-18 02:28:03 +0000122 } u;
drhe9c37f32015-08-15 21:25:36 +0000123};
124
125/* A completely parsed JSON string
126*/
drhe9c37f32015-08-15 21:25:36 +0000127struct JsonParse {
128 u32 nNode; /* Number of slots of aNode[] used */
129 u32 nAlloc; /* Number of slots of aNode[] allocated */
130 JsonNode *aNode; /* Array of nodes containing the parse */
131 const char *zJson; /* Original JSON string */
drh505ad2c2015-08-21 17:33:11 +0000132 u32 *aUp; /* Index of parent of each node */
drhe9c37f32015-08-15 21:25:36 +0000133 u8 oom; /* Set to true if out of memory */
drha7714022015-08-29 00:54:49 +0000134 u8 nErr; /* Number of errors seen */
drhff6d50e2017-04-11 18:55:05 +0000135 u16 iDepth; /* Nesting depth */
drh3fb153c2017-05-11 16:49:59 +0000136 int nJson; /* Length of the zJson string in bytes */
drhe35fc302018-08-30 01:52:10 +0000137 u32 iHold; /* Replace cache line with the lowest iHold value */
drhe9c37f32015-08-15 21:25:36 +0000138};
139
drhff6d50e2017-04-11 18:55:05 +0000140/*
141** Maximum nesting depth of JSON for this implementation.
142**
143** This limit is needed to avoid a stack overflow in the recursive
144** descent parser. A depth of 2000 is far deeper than any sane JSON
145** should go.
146*/
147#define JSON_MAX_DEPTH 2000
148
drh505ad2c2015-08-21 17:33:11 +0000149/**************************************************************************
150** Utility routines for dealing with JsonString objects
151**************************************************************************/
drh301eecc2015-08-17 20:14:19 +0000152
drh505ad2c2015-08-21 17:33:11 +0000153/* Set the JsonString object to an empty string
drh5fa5c102015-08-12 16:49:40 +0000154*/
drh505ad2c2015-08-21 17:33:11 +0000155static void jsonZero(JsonString *p){
drh5fa5c102015-08-12 16:49:40 +0000156 p->zBuf = p->zSpace;
157 p->nAlloc = sizeof(p->zSpace);
158 p->nUsed = 0;
159 p->bStatic = 1;
160}
161
drh505ad2c2015-08-21 17:33:11 +0000162/* Initialize the JsonString object
drh5fa5c102015-08-12 16:49:40 +0000163*/
drh505ad2c2015-08-21 17:33:11 +0000164static void jsonInit(JsonString *p, sqlite3_context *pCtx){
drh5fa5c102015-08-12 16:49:40 +0000165 p->pCtx = pCtx;
drhd0960592015-08-17 21:22:32 +0000166 p->bErr = 0;
drh5fa5c102015-08-12 16:49:40 +0000167 jsonZero(p);
168}
169
170
drh505ad2c2015-08-21 17:33:11 +0000171/* Free all allocated memory and reset the JsonString object back to its
drh5fa5c102015-08-12 16:49:40 +0000172** initial state.
173*/
drh505ad2c2015-08-21 17:33:11 +0000174static void jsonReset(JsonString *p){
drh5fa5c102015-08-12 16:49:40 +0000175 if( !p->bStatic ) sqlite3_free(p->zBuf);
176 jsonZero(p);
177}
178
179
180/* Report an out-of-memory (OOM) condition
181*/
drh505ad2c2015-08-21 17:33:11 +0000182static void jsonOom(JsonString *p){
drh3d1d2a92015-09-22 01:15:49 +0000183 p->bErr = 1;
184 sqlite3_result_error_nomem(p->pCtx);
185 jsonReset(p);
drh5fa5c102015-08-12 16:49:40 +0000186}
187
188/* Enlarge pJson->zBuf so that it can hold at least N more bytes.
189** Return zero on success. Return non-zero on an OOM error
190*/
drh505ad2c2015-08-21 17:33:11 +0000191static int jsonGrow(JsonString *p, u32 N){
drh301eecc2015-08-17 20:14:19 +0000192 u64 nTotal = N<p->nAlloc ? p->nAlloc*2 : p->nAlloc+N+10;
drh5fa5c102015-08-12 16:49:40 +0000193 char *zNew;
194 if( p->bStatic ){
drhd0960592015-08-17 21:22:32 +0000195 if( p->bErr ) return 1;
drh5fa5c102015-08-12 16:49:40 +0000196 zNew = sqlite3_malloc64(nTotal);
197 if( zNew==0 ){
198 jsonOom(p);
199 return SQLITE_NOMEM;
200 }
drh6fd5c1e2015-08-21 20:37:12 +0000201 memcpy(zNew, p->zBuf, (size_t)p->nUsed);
drh5fa5c102015-08-12 16:49:40 +0000202 p->zBuf = zNew;
203 p->bStatic = 0;
204 }else{
205 zNew = sqlite3_realloc64(p->zBuf, nTotal);
206 if( zNew==0 ){
207 jsonOom(p);
208 return SQLITE_NOMEM;
209 }
210 p->zBuf = zNew;
211 }
212 p->nAlloc = nTotal;
213 return SQLITE_OK;
214}
215
drh505ad2c2015-08-21 17:33:11 +0000216/* Append N bytes from zIn onto the end of the JsonString string.
drh5fa5c102015-08-12 16:49:40 +0000217*/
drh505ad2c2015-08-21 17:33:11 +0000218static void jsonAppendRaw(JsonString *p, const char *zIn, u32 N){
drhc795e3d2020-05-17 13:47:28 +0000219 if( N==0 ) return;
drh5fa5c102015-08-12 16:49:40 +0000220 if( (N+p->nUsed >= p->nAlloc) && jsonGrow(p,N)!=0 ) return;
221 memcpy(p->zBuf+p->nUsed, zIn, N);
222 p->nUsed += N;
223}
224
drh4af352d2015-08-21 20:02:48 +0000225/* Append formatted text (not to exceed N bytes) to the JsonString.
226*/
227static void jsonPrintf(int N, JsonString *p, const char *zFormat, ...){
228 va_list ap;
229 if( (p->nUsed + N >= p->nAlloc) && jsonGrow(p, N) ) return;
230 va_start(ap, zFormat);
231 sqlite3_vsnprintf(N, p->zBuf+p->nUsed, zFormat, ap);
232 va_end(ap);
233 p->nUsed += (int)strlen(p->zBuf+p->nUsed);
234}
235
drh5634cc02015-08-17 11:28:03 +0000236/* Append a single character
237*/
drh505ad2c2015-08-21 17:33:11 +0000238static void jsonAppendChar(JsonString *p, char c){
drh5634cc02015-08-17 11:28:03 +0000239 if( p->nUsed>=p->nAlloc && jsonGrow(p,1)!=0 ) return;
240 p->zBuf[p->nUsed++] = c;
241}
242
drh301eecc2015-08-17 20:14:19 +0000243/* Append a comma separator to the output buffer, if the previous
244** character is not '[' or '{'.
245*/
drh505ad2c2015-08-21 17:33:11 +0000246static void jsonAppendSeparator(JsonString *p){
drh301eecc2015-08-17 20:14:19 +0000247 char c;
248 if( p->nUsed==0 ) return;
249 c = p->zBuf[p->nUsed-1];
250 if( c!='[' && c!='{' ) jsonAppendChar(p, ',');
251}
252
drh505ad2c2015-08-21 17:33:11 +0000253/* Append the N-byte string in zIn to the end of the JsonString string
drh5fa5c102015-08-12 16:49:40 +0000254** under construction. Enclose the string in "..." and escape
255** any double-quotes or backslash characters contained within the
256** string.
257*/
drh505ad2c2015-08-21 17:33:11 +0000258static void jsonAppendString(JsonString *p, const char *zIn, u32 N){
drh5fa5c102015-08-12 16:49:40 +0000259 u32 i;
drh76baad92021-04-30 16:12:40 +0000260 if( zIn==0 || ((N+p->nUsed+2 >= p->nAlloc) && jsonGrow(p,N+2)!=0) ) return;
drh5fa5c102015-08-12 16:49:40 +0000261 p->zBuf[p->nUsed++] = '"';
262 for(i=0; i<N; i++){
drh3b7f9a62016-02-04 10:28:57 +0000263 unsigned char c = ((unsigned const char*)zIn)[i];
drh5fa5c102015-08-12 16:49:40 +0000264 if( c=='"' || c=='\\' ){
drh3b7f9a62016-02-04 10:28:57 +0000265 json_simple_escape:
drh4977ccf2015-09-19 11:57:26 +0000266 if( (p->nUsed+N+3-i > p->nAlloc) && jsonGrow(p,N+3-i)!=0 ) return;
drh5fa5c102015-08-12 16:49:40 +0000267 p->zBuf[p->nUsed++] = '\\';
drh3b7f9a62016-02-04 10:28:57 +0000268 }else if( c<=0x1f ){
269 static const char aSpecial[] = {
270 0, 0, 0, 0, 0, 0, 0, 0, 'b', 't', 'n', 0, 'f', 'r', 0, 0,
271 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0
272 };
273 assert( sizeof(aSpecial)==32 );
274 assert( aSpecial['\b']=='b' );
275 assert( aSpecial['\f']=='f' );
276 assert( aSpecial['\n']=='n' );
277 assert( aSpecial['\r']=='r' );
278 assert( aSpecial['\t']=='t' );
279 if( aSpecial[c] ){
280 c = aSpecial[c];
281 goto json_simple_escape;
282 }
283 if( (p->nUsed+N+7+i > p->nAlloc) && jsonGrow(p,N+7-i)!=0 ) return;
284 p->zBuf[p->nUsed++] = '\\';
285 p->zBuf[p->nUsed++] = 'u';
286 p->zBuf[p->nUsed++] = '0';
287 p->zBuf[p->nUsed++] = '0';
288 p->zBuf[p->nUsed++] = '0' + (c>>4);
289 c = "0123456789abcdef"[c&0xf];
drh5fa5c102015-08-12 16:49:40 +0000290 }
291 p->zBuf[p->nUsed++] = c;
292 }
293 p->zBuf[p->nUsed++] = '"';
drh4977ccf2015-09-19 11:57:26 +0000294 assert( p->nUsed<p->nAlloc );
drh5fa5c102015-08-12 16:49:40 +0000295}
296
drhd0960592015-08-17 21:22:32 +0000297/*
298** Append a function parameter value to the JSON string under
299** construction.
300*/
301static void jsonAppendValue(
drh505ad2c2015-08-21 17:33:11 +0000302 JsonString *p, /* Append to this JSON string */
drhf5ddb9c2015-09-11 00:06:41 +0000303 sqlite3_value *pValue /* Value to append */
drhd0960592015-08-17 21:22:32 +0000304){
305 switch( sqlite3_value_type(pValue) ){
306 case SQLITE_NULL: {
307 jsonAppendRaw(p, "null", 4);
308 break;
309 }
310 case SQLITE_INTEGER:
311 case SQLITE_FLOAT: {
312 const char *z = (const char*)sqlite3_value_text(pValue);
313 u32 n = (u32)sqlite3_value_bytes(pValue);
314 jsonAppendRaw(p, z, n);
315 break;
316 }
317 case SQLITE_TEXT: {
318 const char *z = (const char*)sqlite3_value_text(pValue);
319 u32 n = (u32)sqlite3_value_bytes(pValue);
drhf5ddb9c2015-09-11 00:06:41 +0000320 if( sqlite3_value_subtype(pValue)==JSON_SUBTYPE ){
drhecb5fed2015-08-28 03:33:50 +0000321 jsonAppendRaw(p, z, n);
322 }else{
323 jsonAppendString(p, z, n);
324 }
drhd0960592015-08-17 21:22:32 +0000325 break;
326 }
327 default: {
328 if( p->bErr==0 ){
329 sqlite3_result_error(p->pCtx, "JSON cannot hold BLOB values", -1);
drh4a642b62016-02-05 01:55:27 +0000330 p->bErr = 2;
drhd0960592015-08-17 21:22:32 +0000331 jsonReset(p);
332 }
333 break;
334 }
335 }
336}
337
338
drhbd0621b2015-08-13 13:54:59 +0000339/* Make the JSON in p the result of the SQL function.
drh5fa5c102015-08-12 16:49:40 +0000340*/
drh505ad2c2015-08-21 17:33:11 +0000341static void jsonResult(JsonString *p){
drhd0960592015-08-17 21:22:32 +0000342 if( p->bErr==0 ){
drh5fa5c102015-08-12 16:49:40 +0000343 sqlite3_result_text64(p->pCtx, p->zBuf, p->nUsed,
344 p->bStatic ? SQLITE_TRANSIENT : sqlite3_free,
345 SQLITE_UTF8);
346 jsonZero(p);
347 }
348 assert( p->bStatic );
349}
350
drh505ad2c2015-08-21 17:33:11 +0000351/**************************************************************************
352** Utility routines for dealing with JsonNode and JsonParse objects
353**************************************************************************/
354
355/*
356** Return the number of consecutive JsonNode slots need to represent
357** the parsed JSON at pNode. The minimum answer is 1. For ARRAY and
358** OBJECT types, the number might be larger.
359**
360** Appended elements are not counted. The value returned is the number
361** by which the JsonNode counter should increment in order to go to the
362** next peer value.
363*/
364static u32 jsonNodeSize(JsonNode *pNode){
365 return pNode->eType>=JSON_ARRAY ? pNode->n+1 : 1;
366}
367
368/*
369** Reclaim all memory allocated by a JsonParse object. But do not
370** delete the JsonParse object itself.
371*/
372static void jsonParseReset(JsonParse *pParse){
373 sqlite3_free(pParse->aNode);
374 pParse->aNode = 0;
375 pParse->nNode = 0;
376 pParse->nAlloc = 0;
377 sqlite3_free(pParse->aUp);
378 pParse->aUp = 0;
379}
380
drh5634cc02015-08-17 11:28:03 +0000381/*
drh3fb153c2017-05-11 16:49:59 +0000382** Free a JsonParse object that was obtained from sqlite3_malloc().
383*/
384static void jsonParseFree(JsonParse *pParse){
385 jsonParseReset(pParse);
386 sqlite3_free(pParse);
387}
388
389/*
drh5634cc02015-08-17 11:28:03 +0000390** Convert the JsonNode pNode into a pure JSON string and
391** append to pOut. Subsubstructure is also included. Return
392** the number of JsonNode objects that are encoded.
drhbd0621b2015-08-13 13:54:59 +0000393*/
drh52216ad2015-08-18 02:28:03 +0000394static void jsonRenderNode(
drhd0960592015-08-17 21:22:32 +0000395 JsonNode *pNode, /* The node to render */
drh505ad2c2015-08-21 17:33:11 +0000396 JsonString *pOut, /* Write JSON here */
drhd0960592015-08-17 21:22:32 +0000397 sqlite3_value **aReplace /* Replacement values */
398){
drh7d4c94b2021-10-04 22:34:38 +0000399 assert( pNode!=0 );
drh633647a2017-03-22 21:24:31 +0000400 if( pNode->jnFlags & (JNODE_REPLACE|JNODE_PATCH) ){
drh7d4c94b2021-10-04 22:34:38 +0000401 if( (pNode->jnFlags & JNODE_REPLACE)!=0 && ALWAYS(aReplace!=0) ){
drh285f2ef2021-10-15 16:15:04 +0000402 assert( pNode->eU==4 );
drh633647a2017-03-22 21:24:31 +0000403 jsonAppendValue(pOut, aReplace[pNode->u.iReplace]);
404 return;
405 }
drh285f2ef2021-10-15 16:15:04 +0000406 assert( pNode->eU==5 );
drh633647a2017-03-22 21:24:31 +0000407 pNode = pNode->u.pPatch;
408 }
drh5634cc02015-08-17 11:28:03 +0000409 switch( pNode->eType ){
drha8f39a92015-09-21 22:53:16 +0000410 default: {
411 assert( pNode->eType==JSON_NULL );
drh5634cc02015-08-17 11:28:03 +0000412 jsonAppendRaw(pOut, "null", 4);
413 break;
414 }
415 case JSON_TRUE: {
416 jsonAppendRaw(pOut, "true", 4);
417 break;
418 }
419 case JSON_FALSE: {
420 jsonAppendRaw(pOut, "false", 5);
421 break;
422 }
423 case JSON_STRING: {
drh301eecc2015-08-17 20:14:19 +0000424 if( pNode->jnFlags & JNODE_RAW ){
drh285f2ef2021-10-15 16:15:04 +0000425 assert( pNode->eU==1 );
drh52216ad2015-08-18 02:28:03 +0000426 jsonAppendString(pOut, pNode->u.zJContent, pNode->n);
drh5634cc02015-08-17 11:28:03 +0000427 break;
428 }
drh08b92082020-08-10 14:18:00 +0000429 /* no break */ deliberate_fall_through
drh5634cc02015-08-17 11:28:03 +0000430 }
431 case JSON_REAL:
432 case JSON_INT: {
drh285f2ef2021-10-15 16:15:04 +0000433 assert( pNode->eU==1 );
drh52216ad2015-08-18 02:28:03 +0000434 jsonAppendRaw(pOut, pNode->u.zJContent, pNode->n);
drh5634cc02015-08-17 11:28:03 +0000435 break;
436 }
437 case JSON_ARRAY: {
drh52216ad2015-08-18 02:28:03 +0000438 u32 j = 1;
drh5634cc02015-08-17 11:28:03 +0000439 jsonAppendChar(pOut, '[');
drh52216ad2015-08-18 02:28:03 +0000440 for(;;){
441 while( j<=pNode->n ){
drh633647a2017-03-22 21:24:31 +0000442 if( (pNode[j].jnFlags & JNODE_REMOVE)==0 ){
drhd0960592015-08-17 21:22:32 +0000443 jsonAppendSeparator(pOut);
drh52216ad2015-08-18 02:28:03 +0000444 jsonRenderNode(&pNode[j], pOut, aReplace);
drhd0960592015-08-17 21:22:32 +0000445 }
drh505ad2c2015-08-21 17:33:11 +0000446 j += jsonNodeSize(&pNode[j]);
drh301eecc2015-08-17 20:14:19 +0000447 }
drh52216ad2015-08-18 02:28:03 +0000448 if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;
drh285f2ef2021-10-15 16:15:04 +0000449 assert( pNode->eU==2 );
drh52216ad2015-08-18 02:28:03 +0000450 pNode = &pNode[pNode->u.iAppend];
451 j = 1;
drh5634cc02015-08-17 11:28:03 +0000452 }
453 jsonAppendChar(pOut, ']');
454 break;
455 }
456 case JSON_OBJECT: {
drh52216ad2015-08-18 02:28:03 +0000457 u32 j = 1;
drh5634cc02015-08-17 11:28:03 +0000458 jsonAppendChar(pOut, '{');
drh52216ad2015-08-18 02:28:03 +0000459 for(;;){
460 while( j<=pNode->n ){
461 if( (pNode[j+1].jnFlags & JNODE_REMOVE)==0 ){
462 jsonAppendSeparator(pOut);
463 jsonRenderNode(&pNode[j], pOut, aReplace);
464 jsonAppendChar(pOut, ':');
drh633647a2017-03-22 21:24:31 +0000465 jsonRenderNode(&pNode[j+1], pOut, aReplace);
drhd0960592015-08-17 21:22:32 +0000466 }
drh505ad2c2015-08-21 17:33:11 +0000467 j += 1 + jsonNodeSize(&pNode[j+1]);
drh301eecc2015-08-17 20:14:19 +0000468 }
drh52216ad2015-08-18 02:28:03 +0000469 if( (pNode->jnFlags & JNODE_APPEND)==0 ) break;
drh285f2ef2021-10-15 16:15:04 +0000470 assert( pNode->eU==2 );
drh52216ad2015-08-18 02:28:03 +0000471 pNode = &pNode[pNode->u.iAppend];
472 j = 1;
drh5634cc02015-08-17 11:28:03 +0000473 }
474 jsonAppendChar(pOut, '}');
475 break;
476 }
drhbd0621b2015-08-13 13:54:59 +0000477 }
drh5634cc02015-08-17 11:28:03 +0000478}
479
480/*
drhf2df7e72015-08-28 20:07:40 +0000481** Return a JsonNode and all its descendents as a JSON string.
482*/
483static void jsonReturnJson(
484 JsonNode *pNode, /* Node to return */
485 sqlite3_context *pCtx, /* Return value for this function */
486 sqlite3_value **aReplace /* Array of replacement values */
487){
488 JsonString s;
489 jsonInit(&s, pCtx);
490 jsonRenderNode(pNode, &s, aReplace);
491 jsonResult(&s);
drhf5ddb9c2015-09-11 00:06:41 +0000492 sqlite3_result_subtype(pCtx, JSON_SUBTYPE);
drhf2df7e72015-08-28 20:07:40 +0000493}
494
495/*
drh48eb03b2019-11-10 11:09:06 +0000496** Translate a single byte of Hex into an integer.
497** This routine only works if h really is a valid hexadecimal
498** character: 0..9a..fA..F
499*/
500static u8 jsonHexToInt(int h){
501 assert( (h>='0' && h<='9') || (h>='a' && h<='f') || (h>='A' && h<='F') );
502#ifdef SQLITE_EBCDIC
503 h += 9*(1&~(h>>4));
504#else
505 h += 9*(1&(h>>6));
506#endif
507 return (u8)(h & 0xf);
508}
509
510/*
511** Convert a 4-byte hex string into an integer
512*/
513static u32 jsonHexToInt4(const char *z){
514 u32 v;
drh9dbf96b2022-01-06 01:40:09 +0000515 assert( sqlite3Isxdigit(z[0]) );
516 assert( sqlite3Isxdigit(z[1]) );
517 assert( sqlite3Isxdigit(z[2]) );
518 assert( sqlite3Isxdigit(z[3]) );
drh48eb03b2019-11-10 11:09:06 +0000519 v = (jsonHexToInt(z[0])<<12)
520 + (jsonHexToInt(z[1])<<8)
521 + (jsonHexToInt(z[2])<<4)
522 + jsonHexToInt(z[3]);
523 return v;
524}
525
526/*
drh5634cc02015-08-17 11:28:03 +0000527** Make the JsonNode the return value of the function.
528*/
drhd0960592015-08-17 21:22:32 +0000529static void jsonReturn(
530 JsonNode *pNode, /* Node to return */
531 sqlite3_context *pCtx, /* Return value for this function */
532 sqlite3_value **aReplace /* Array of replacement values */
533){
drh5634cc02015-08-17 11:28:03 +0000534 switch( pNode->eType ){
drha8f39a92015-09-21 22:53:16 +0000535 default: {
536 assert( pNode->eType==JSON_NULL );
drh5634cc02015-08-17 11:28:03 +0000537 sqlite3_result_null(pCtx);
538 break;
539 }
540 case JSON_TRUE: {
541 sqlite3_result_int(pCtx, 1);
542 break;
543 }
544 case JSON_FALSE: {
545 sqlite3_result_int(pCtx, 0);
546 break;
547 }
drh987eb1f2015-08-17 15:17:37 +0000548 case JSON_INT: {
549 sqlite3_int64 i = 0;
drh285f2ef2021-10-15 16:15:04 +0000550 const char *z;
551 assert( pNode->eU==1 );
552 z = pNode->u.zJContent;
drh987eb1f2015-08-17 15:17:37 +0000553 if( z[0]=='-' ){ z++; }
drh8deb4b82015-10-09 18:21:43 +0000554 while( z[0]>='0' && z[0]<='9' ){
555 unsigned v = *(z++) - '0';
556 if( i>=LARGEST_INT64/10 ){
drha0882fa2015-10-09 20:40:44 +0000557 if( i>LARGEST_INT64/10 ) goto int_as_real;
drh8deb4b82015-10-09 18:21:43 +0000558 if( z[0]>='0' && z[0]<='9' ) goto int_as_real;
559 if( v==9 ) goto int_as_real;
560 if( v==8 ){
561 if( pNode->u.zJContent[0]=='-' ){
562 sqlite3_result_int64(pCtx, SMALLEST_INT64);
563 goto int_done;
564 }else{
565 goto int_as_real;
566 }
567 }
568 }
569 i = i*10 + v;
570 }
drh52216ad2015-08-18 02:28:03 +0000571 if( pNode->u.zJContent[0]=='-' ){ i = -i; }
drh987eb1f2015-08-17 15:17:37 +0000572 sqlite3_result_int64(pCtx, i);
drh8deb4b82015-10-09 18:21:43 +0000573 int_done:
574 break;
drhe85e1da2021-10-01 21:01:07 +0000575 int_as_real: ; /* no break */ deliberate_fall_through
drh8deb4b82015-10-09 18:21:43 +0000576 }
577 case JSON_REAL: {
drh49472652015-10-16 15:35:39 +0000578 double r;
579#ifdef SQLITE_AMALGAMATION
drh285f2ef2021-10-15 16:15:04 +0000580 const char *z;
581 assert( pNode->eU==1 );
582 z = pNode->u.zJContent;
drh49472652015-10-16 15:35:39 +0000583 sqlite3AtoF(z, &r, sqlite3Strlen30(z), SQLITE_UTF8);
584#else
drh285f2ef2021-10-15 16:15:04 +0000585 assert( pNode->eU==1 );
drh49472652015-10-16 15:35:39 +0000586 r = strtod(pNode->u.zJContent, 0);
587#endif
drh8deb4b82015-10-09 18:21:43 +0000588 sqlite3_result_double(pCtx, r);
drh987eb1f2015-08-17 15:17:37 +0000589 break;
590 }
drh5634cc02015-08-17 11:28:03 +0000591 case JSON_STRING: {
drha8f39a92015-09-21 22:53:16 +0000592#if 0 /* Never happens because JNODE_RAW is only set by json_set(),
593 ** json_insert() and json_replace() and those routines do not
594 ** call jsonReturn() */
drh301eecc2015-08-17 20:14:19 +0000595 if( pNode->jnFlags & JNODE_RAW ){
drh285f2ef2021-10-15 16:15:04 +0000596 assert( pNode->eU==1 );
drh52216ad2015-08-18 02:28:03 +0000597 sqlite3_result_text(pCtx, pNode->u.zJContent, pNode->n,
598 SQLITE_TRANSIENT);
drha8f39a92015-09-21 22:53:16 +0000599 }else
600#endif
601 assert( (pNode->jnFlags & JNODE_RAW)==0 );
602 if( (pNode->jnFlags & JNODE_ESCAPE)==0 ){
drh987eb1f2015-08-17 15:17:37 +0000603 /* JSON formatted without any backslash-escapes */
drh285f2ef2021-10-15 16:15:04 +0000604 assert( pNode->eU==1 );
drh52216ad2015-08-18 02:28:03 +0000605 sqlite3_result_text(pCtx, pNode->u.zJContent+1, pNode->n-2,
drh987eb1f2015-08-17 15:17:37 +0000606 SQLITE_TRANSIENT);
drh5634cc02015-08-17 11:28:03 +0000607 }else{
608 /* Translate JSON formatted string into raw text */
drh987eb1f2015-08-17 15:17:37 +0000609 u32 i;
610 u32 n = pNode->n;
drh285f2ef2021-10-15 16:15:04 +0000611 const char *z;
drh987eb1f2015-08-17 15:17:37 +0000612 char *zOut;
613 u32 j;
drh285f2ef2021-10-15 16:15:04 +0000614 assert( pNode->eU==1 );
615 z = pNode->u.zJContent;
drh987eb1f2015-08-17 15:17:37 +0000616 zOut = sqlite3_malloc( n+1 );
617 if( zOut==0 ){
618 sqlite3_result_error_nomem(pCtx);
619 break;
620 }
621 for(i=1, j=0; i<n-1; i++){
622 char c = z[i];
drh80d87402015-08-24 12:42:41 +0000623 if( c!='\\' ){
drh987eb1f2015-08-17 15:17:37 +0000624 zOut[j++] = c;
625 }else{
626 c = z[++i];
drh80d87402015-08-24 12:42:41 +0000627 if( c=='u' ){
drh48eb03b2019-11-10 11:09:06 +0000628 u32 v = jsonHexToInt4(z+i+1);
629 i += 4;
drh80d87402015-08-24 12:42:41 +0000630 if( v==0 ) break;
drh987eb1f2015-08-17 15:17:37 +0000631 if( v<=0x7f ){
mistachkin16a93122015-09-11 18:05:01 +0000632 zOut[j++] = (char)v;
drh987eb1f2015-08-17 15:17:37 +0000633 }else if( v<=0x7ff ){
mistachkin16a93122015-09-11 18:05:01 +0000634 zOut[j++] = (char)(0xc0 | (v>>6));
drh987eb1f2015-08-17 15:17:37 +0000635 zOut[j++] = 0x80 | (v&0x3f);
drh80d87402015-08-24 12:42:41 +0000636 }else{
drh48eb03b2019-11-10 11:09:06 +0000637 u32 vlo;
638 if( (v&0xfc00)==0xd800
639 && i<n-6
640 && z[i+1]=='\\'
641 && z[i+2]=='u'
642 && ((vlo = jsonHexToInt4(z+i+3))&0xfc00)==0xdc00
643 ){
644 /* We have a surrogate pair */
645 v = ((v&0x3ff)<<10) + (vlo&0x3ff) + 0x10000;
646 i += 6;
647 zOut[j++] = 0xf0 | (v>>18);
648 zOut[j++] = 0x80 | ((v>>12)&0x3f);
649 zOut[j++] = 0x80 | ((v>>6)&0x3f);
650 zOut[j++] = 0x80 | (v&0x3f);
651 }else{
652 zOut[j++] = 0xe0 | (v>>12);
653 zOut[j++] = 0x80 | ((v>>6)&0x3f);
654 zOut[j++] = 0x80 | (v&0x3f);
655 }
drh987eb1f2015-08-17 15:17:37 +0000656 }
657 }else{
658 if( c=='b' ){
659 c = '\b';
660 }else if( c=='f' ){
661 c = '\f';
662 }else if( c=='n' ){
663 c = '\n';
664 }else if( c=='r' ){
665 c = '\r';
666 }else if( c=='t' ){
667 c = '\t';
668 }
669 zOut[j++] = c;
670 }
671 }
672 }
673 zOut[j] = 0;
674 sqlite3_result_text(pCtx, zOut, j, sqlite3_free);
drh5634cc02015-08-17 11:28:03 +0000675 }
676 break;
677 }
678 case JSON_ARRAY:
679 case JSON_OBJECT: {
drhf2df7e72015-08-28 20:07:40 +0000680 jsonReturnJson(pNode, pCtx, aReplace);
drh5634cc02015-08-17 11:28:03 +0000681 break;
682 }
683 }
drhbd0621b2015-08-13 13:54:59 +0000684}
685
drh95677942015-09-24 01:06:37 +0000686/* Forward reference */
687static int jsonParseAddNode(JsonParse*,u32,u32,const char*);
688
689/*
690** A macro to hint to the compiler that a function should not be
691** inlined.
692*/
693#if defined(__GNUC__)
694# define JSON_NOINLINE __attribute__((noinline))
695#elif defined(_MSC_VER) && _MSC_VER>=1310
696# define JSON_NOINLINE __declspec(noinline)
697#else
698# define JSON_NOINLINE
699#endif
700
701
702static JSON_NOINLINE int jsonParseAddNodeExpand(
703 JsonParse *pParse, /* Append the node to this object */
704 u32 eType, /* Node type */
705 u32 n, /* Content size or sub-node count */
706 const char *zContent /* Content */
707){
708 u32 nNew;
709 JsonNode *pNew;
710 assert( pParse->nNode>=pParse->nAlloc );
711 if( pParse->oom ) return -1;
712 nNew = pParse->nAlloc*2 + 10;
drh2d77d802019-01-08 20:02:48 +0000713 pNew = sqlite3_realloc64(pParse->aNode, sizeof(JsonNode)*nNew);
drh95677942015-09-24 01:06:37 +0000714 if( pNew==0 ){
715 pParse->oom = 1;
716 return -1;
717 }
718 pParse->nAlloc = nNew;
719 pParse->aNode = pNew;
720 assert( pParse->nNode<pParse->nAlloc );
721 return jsonParseAddNode(pParse, eType, n, zContent);
722}
723
drh5fa5c102015-08-12 16:49:40 +0000724/*
drhe9c37f32015-08-15 21:25:36 +0000725** Create a new JsonNode instance based on the arguments and append that
726** instance to the JsonParse. Return the index in pParse->aNode[] of the
727** new node, or -1 if a memory allocation fails.
728*/
729static int jsonParseAddNode(
730 JsonParse *pParse, /* Append the node to this object */
731 u32 eType, /* Node type */
732 u32 n, /* Content size or sub-node count */
733 const char *zContent /* Content */
734){
735 JsonNode *p;
drhaa6fe5b2021-10-04 13:18:44 +0000736 if( pParse->aNode==0 || pParse->nNode>=pParse->nAlloc ){
drh95677942015-09-24 01:06:37 +0000737 return jsonParseAddNodeExpand(pParse, eType, n, zContent);
drhe9c37f32015-08-15 21:25:36 +0000738 }
739 p = &pParse->aNode[pParse->nNode];
drh5634cc02015-08-17 11:28:03 +0000740 p->eType = (u8)eType;
drh301eecc2015-08-17 20:14:19 +0000741 p->jnFlags = 0;
drh285f2ef2021-10-15 16:15:04 +0000742 VVA( p->eU = zContent ? 1 : 0 );
drhe9c37f32015-08-15 21:25:36 +0000743 p->n = n;
drh52216ad2015-08-18 02:28:03 +0000744 p->u.zJContent = zContent;
drhe9c37f32015-08-15 21:25:36 +0000745 return pParse->nNode++;
746}
747
748/*
drhad875e72016-11-07 13:37:28 +0000749** Return true if z[] begins with 4 (or more) hexadecimal digits
750*/
751static int jsonIs4Hex(const char *z){
752 int i;
drh9dbf96b2022-01-06 01:40:09 +0000753 for(i=0; i<4; i++) if( !sqlite3Isxdigit(z[i]) ) return 0;
drhad875e72016-11-07 13:37:28 +0000754 return 1;
755}
756
757/*
drhe9c37f32015-08-15 21:25:36 +0000758** Parse a single JSON value which begins at pParse->zJson[i]. Return the
759** index of the first character past the end of the value parsed.
760**
761** Return negative for a syntax error. Special cases: return -2 if the
762** first non-whitespace character is '}' and return -3 if the first
763** non-whitespace character is ']'.
764*/
765static int jsonParseValue(JsonParse *pParse, u32 i){
766 char c;
767 u32 j;
drhbc8f0922015-08-22 19:39:04 +0000768 int iThis;
drhe9c37f32015-08-15 21:25:36 +0000769 int x;
drh852944e2015-09-10 03:29:11 +0000770 JsonNode *pNode;
drh9fa866a2017-04-08 18:18:22 +0000771 const char *z = pParse->zJson;
drh9dbf96b2022-01-06 01:40:09 +0000772 while( fast_isspace(z[i]) ){ i++; }
drh9fa866a2017-04-08 18:18:22 +0000773 if( (c = z[i])=='{' ){
drhe9c37f32015-08-15 21:25:36 +0000774 /* Parse object */
775 iThis = jsonParseAddNode(pParse, JSON_OBJECT, 0, 0);
drhbc8f0922015-08-22 19:39:04 +0000776 if( iThis<0 ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000777 for(j=i+1;;j++){
drh9dbf96b2022-01-06 01:40:09 +0000778 while( fast_isspace(z[j]) ){ j++; }
drhff6d50e2017-04-11 18:55:05 +0000779 if( ++pParse->iDepth > JSON_MAX_DEPTH ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000780 x = jsonParseValue(pParse, j);
781 if( x<0 ){
drhff6d50e2017-04-11 18:55:05 +0000782 pParse->iDepth--;
drhf27cd1f2015-09-23 01:10:29 +0000783 if( x==(-2) && pParse->nNode==(u32)iThis+1 ) return j+1;
drhe9c37f32015-08-15 21:25:36 +0000784 return -1;
785 }
drhbe9474e2015-08-22 03:05:54 +0000786 if( pParse->oom ) return -1;
drh852944e2015-09-10 03:29:11 +0000787 pNode = &pParse->aNode[pParse->nNode-1];
788 if( pNode->eType!=JSON_STRING ) return -1;
789 pNode->jnFlags |= JNODE_LABEL;
drhe9c37f32015-08-15 21:25:36 +0000790 j = x;
drh9dbf96b2022-01-06 01:40:09 +0000791 while( fast_isspace(z[j]) ){ j++; }
drh9fa866a2017-04-08 18:18:22 +0000792 if( z[j]!=':' ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000793 j++;
794 x = jsonParseValue(pParse, j);
drhff6d50e2017-04-11 18:55:05 +0000795 pParse->iDepth--;
drhe9c37f32015-08-15 21:25:36 +0000796 if( x<0 ) return -1;
797 j = x;
drh9dbf96b2022-01-06 01:40:09 +0000798 while( fast_isspace(z[j]) ){ j++; }
drh9fa866a2017-04-08 18:18:22 +0000799 c = z[j];
drhe9c37f32015-08-15 21:25:36 +0000800 if( c==',' ) continue;
801 if( c!='}' ) return -1;
802 break;
803 }
drhbc8f0922015-08-22 19:39:04 +0000804 pParse->aNode[iThis].n = pParse->nNode - (u32)iThis - 1;
drhe9c37f32015-08-15 21:25:36 +0000805 return j+1;
806 }else if( c=='[' ){
807 /* Parse array */
808 iThis = jsonParseAddNode(pParse, JSON_ARRAY, 0, 0);
drhbc8f0922015-08-22 19:39:04 +0000809 if( iThis<0 ) return -1;
drh285f2ef2021-10-15 16:15:04 +0000810 memset(&pParse->aNode[iThis].u, 0, sizeof(pParse->aNode[iThis].u));
drhe9c37f32015-08-15 21:25:36 +0000811 for(j=i+1;;j++){
drh9dbf96b2022-01-06 01:40:09 +0000812 while( fast_isspace(z[j]) ){ j++; }
drhff6d50e2017-04-11 18:55:05 +0000813 if( ++pParse->iDepth > JSON_MAX_DEPTH ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000814 x = jsonParseValue(pParse, j);
drhff6d50e2017-04-11 18:55:05 +0000815 pParse->iDepth--;
drhe9c37f32015-08-15 21:25:36 +0000816 if( x<0 ){
drhf27cd1f2015-09-23 01:10:29 +0000817 if( x==(-3) && pParse->nNode==(u32)iThis+1 ) return j+1;
drhe9c37f32015-08-15 21:25:36 +0000818 return -1;
819 }
820 j = x;
drh9dbf96b2022-01-06 01:40:09 +0000821 while( fast_isspace(z[j]) ){ j++; }
drh9fa866a2017-04-08 18:18:22 +0000822 c = z[j];
drhe9c37f32015-08-15 21:25:36 +0000823 if( c==',' ) continue;
824 if( c!=']' ) return -1;
825 break;
826 }
drhbc8f0922015-08-22 19:39:04 +0000827 pParse->aNode[iThis].n = pParse->nNode - (u32)iThis - 1;
drhe9c37f32015-08-15 21:25:36 +0000828 return j+1;
829 }else if( c=='"' ){
830 /* Parse string */
drh301eecc2015-08-17 20:14:19 +0000831 u8 jnFlags = 0;
drhe9c37f32015-08-15 21:25:36 +0000832 j = i+1;
833 for(;;){
drh9fa866a2017-04-08 18:18:22 +0000834 c = z[j];
drh86715382017-04-13 00:12:32 +0000835 if( (c & ~0x1f)==0 ){
836 /* Control characters are not allowed in strings */
837 return -1;
838 }
drhe9c37f32015-08-15 21:25:36 +0000839 if( c=='\\' ){
drh9fa866a2017-04-08 18:18:22 +0000840 c = z[++j];
drhad875e72016-11-07 13:37:28 +0000841 if( c=='"' || c=='\\' || c=='/' || c=='b' || c=='f'
842 || c=='n' || c=='r' || c=='t'
drh9fa866a2017-04-08 18:18:22 +0000843 || (c=='u' && jsonIs4Hex(z+j+1)) ){
drhad875e72016-11-07 13:37:28 +0000844 jnFlags = JNODE_ESCAPE;
845 }else{
846 return -1;
847 }
drhe9c37f32015-08-15 21:25:36 +0000848 }else if( c=='"' ){
849 break;
850 }
851 j++;
852 }
drh9fa866a2017-04-08 18:18:22 +0000853 jsonParseAddNode(pParse, JSON_STRING, j+1-i, &z[i]);
drhbe9474e2015-08-22 03:05:54 +0000854 if( !pParse->oom ) pParse->aNode[pParse->nNode-1].jnFlags = jnFlags;
drhe9c37f32015-08-15 21:25:36 +0000855 return j+1;
856 }else if( c=='n'
drh9fa866a2017-04-08 18:18:22 +0000857 && strncmp(z+i,"null",4)==0
drh9dbf96b2022-01-06 01:40:09 +0000858 && !sqlite3Isalnum(z[i+4]) ){
drhe9c37f32015-08-15 21:25:36 +0000859 jsonParseAddNode(pParse, JSON_NULL, 0, 0);
860 return i+4;
861 }else if( c=='t'
drh9fa866a2017-04-08 18:18:22 +0000862 && strncmp(z+i,"true",4)==0
drh9dbf96b2022-01-06 01:40:09 +0000863 && !sqlite3Isalnum(z[i+4]) ){
drhe9c37f32015-08-15 21:25:36 +0000864 jsonParseAddNode(pParse, JSON_TRUE, 0, 0);
865 return i+4;
866 }else if( c=='f'
drh9fa866a2017-04-08 18:18:22 +0000867 && strncmp(z+i,"false",5)==0
drh9dbf96b2022-01-06 01:40:09 +0000868 && !sqlite3Isalnum(z[i+5]) ){
drhe9c37f32015-08-15 21:25:36 +0000869 jsonParseAddNode(pParse, JSON_FALSE, 0, 0);
870 return i+5;
871 }else if( c=='-' || (c>='0' && c<='9') ){
872 /* Parse number */
873 u8 seenDP = 0;
874 u8 seenE = 0;
drh9fa866a2017-04-08 18:18:22 +0000875 assert( '-' < '0' );
876 if( c<='0' ){
877 j = c=='-' ? i+1 : i;
878 if( z[j]=='0' && z[j+1]>='0' && z[j+1]<='9' ) return -1;
879 }
drhe9c37f32015-08-15 21:25:36 +0000880 j = i+1;
881 for(;; j++){
drh9fa866a2017-04-08 18:18:22 +0000882 c = z[j];
drhe9c37f32015-08-15 21:25:36 +0000883 if( c>='0' && c<='9' ) continue;
884 if( c=='.' ){
drh9fa866a2017-04-08 18:18:22 +0000885 if( z[j-1]=='-' ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000886 if( seenDP ) return -1;
887 seenDP = 1;
888 continue;
889 }
890 if( c=='e' || c=='E' ){
drh9fa866a2017-04-08 18:18:22 +0000891 if( z[j-1]<'0' ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000892 if( seenE ) return -1;
893 seenDP = seenE = 1;
drh9fa866a2017-04-08 18:18:22 +0000894 c = z[j+1];
drh8784eca2015-08-23 02:42:30 +0000895 if( c=='+' || c=='-' ){
896 j++;
drh9fa866a2017-04-08 18:18:22 +0000897 c = z[j+1];
drh8784eca2015-08-23 02:42:30 +0000898 }
drhd1f00682015-08-29 16:02:37 +0000899 if( c<'0' || c>'9' ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000900 continue;
901 }
902 break;
903 }
drh9fa866a2017-04-08 18:18:22 +0000904 if( z[j-1]<'0' ) return -1;
drhe9c37f32015-08-15 21:25:36 +0000905 jsonParseAddNode(pParse, seenDP ? JSON_REAL : JSON_INT,
drh9fa866a2017-04-08 18:18:22 +0000906 j - i, &z[i]);
drhe9c37f32015-08-15 21:25:36 +0000907 return j;
908 }else if( c=='}' ){
909 return -2; /* End of {...} */
910 }else if( c==']' ){
911 return -3; /* End of [...] */
drh8cb15cc2015-09-24 01:40:45 +0000912 }else if( c==0 ){
913 return 0; /* End of file */
drhe9c37f32015-08-15 21:25:36 +0000914 }else{
915 return -1; /* Syntax error */
916 }
917}
918
919/*
920** Parse a complete JSON string. Return 0 on success or non-zero if there
921** are any errors. If an error occurs, free all memory associated with
922** pParse.
923**
924** pParse is uninitialized when this routine is called.
925*/
drhbc8f0922015-08-22 19:39:04 +0000926static int jsonParse(
927 JsonParse *pParse, /* Initialize and fill this JsonParse object */
928 sqlite3_context *pCtx, /* Report errors here */
929 const char *zJson /* Input JSON text to be parsed */
930){
drhe9c37f32015-08-15 21:25:36 +0000931 int i;
drhe9c37f32015-08-15 21:25:36 +0000932 memset(pParse, 0, sizeof(*pParse));
drhc3722b22015-08-23 20:44:59 +0000933 if( zJson==0 ) return 1;
drhe9c37f32015-08-15 21:25:36 +0000934 pParse->zJson = zJson;
935 i = jsonParseValue(pParse, 0);
drhc3722b22015-08-23 20:44:59 +0000936 if( pParse->oom ) i = -1;
drhe9c37f32015-08-15 21:25:36 +0000937 if( i>0 ){
drhff6d50e2017-04-11 18:55:05 +0000938 assert( pParse->iDepth==0 );
drh9dbf96b2022-01-06 01:40:09 +0000939 while( fast_isspace(zJson[i]) ) i++;
drhe9c37f32015-08-15 21:25:36 +0000940 if( zJson[i] ) i = -1;
941 }
drhd1f00682015-08-29 16:02:37 +0000942 if( i<=0 ){
drhf2df7e72015-08-28 20:07:40 +0000943 if( pCtx!=0 ){
944 if( pParse->oom ){
945 sqlite3_result_error_nomem(pCtx);
946 }else{
947 sqlite3_result_error(pCtx, "malformed JSON", -1);
948 }
949 }
drh505ad2c2015-08-21 17:33:11 +0000950 jsonParseReset(pParse);
drhe9c37f32015-08-15 21:25:36 +0000951 return 1;
952 }
953 return 0;
954}
drh301eecc2015-08-17 20:14:19 +0000955
drh505ad2c2015-08-21 17:33:11 +0000956/* Mark node i of pParse as being a child of iParent. Call recursively
957** to fill in all the descendants of node i.
958*/
959static void jsonParseFillInParentage(JsonParse *pParse, u32 i, u32 iParent){
960 JsonNode *pNode = &pParse->aNode[i];
961 u32 j;
962 pParse->aUp[i] = iParent;
963 switch( pNode->eType ){
964 case JSON_ARRAY: {
965 for(j=1; j<=pNode->n; j += jsonNodeSize(pNode+j)){
966 jsonParseFillInParentage(pParse, i+j, i);
967 }
968 break;
969 }
970 case JSON_OBJECT: {
971 for(j=1; j<=pNode->n; j += jsonNodeSize(pNode+j+1)+1){
972 pParse->aUp[i+j] = i;
973 jsonParseFillInParentage(pParse, i+j+1, i);
974 }
975 break;
976 }
977 default: {
978 break;
979 }
980 }
981}
982
983/*
984** Compute the parentage of all nodes in a completed parse.
985*/
986static int jsonParseFindParents(JsonParse *pParse){
987 u32 *aUp;
988 assert( pParse->aUp==0 );
drh2d77d802019-01-08 20:02:48 +0000989 aUp = pParse->aUp = sqlite3_malloc64( sizeof(u32)*pParse->nNode );
drhc3722b22015-08-23 20:44:59 +0000990 if( aUp==0 ){
991 pParse->oom = 1;
992 return SQLITE_NOMEM;
993 }
drh505ad2c2015-08-21 17:33:11 +0000994 jsonParseFillInParentage(pParse, 0, 0);
995 return SQLITE_OK;
996}
997
drh8cb0c832015-09-22 00:21:03 +0000998/*
drh3fb153c2017-05-11 16:49:59 +0000999** Magic number used for the JSON parse cache in sqlite3_get_auxdata()
1000*/
drhe35fc302018-08-30 01:52:10 +00001001#define JSON_CACHE_ID (-429938) /* First cache entry */
1002#define JSON_CACHE_SZ 4 /* Max number of cache entries */
drh3fb153c2017-05-11 16:49:59 +00001003
1004/*
1005** Obtain a complete parse of the JSON found in the first argument
1006** of the argv array. Use the sqlite3_get_auxdata() cache for this
1007** parse if it is available. If the cache is not available or if it
1008** is no longer valid, parse the JSON again and return the new parse,
1009** and also register the new parse so that it will be available for
1010** future sqlite3_get_auxdata() calls.
1011*/
1012static JsonParse *jsonParseCached(
1013 sqlite3_context *pCtx,
drhe35fc302018-08-30 01:52:10 +00001014 sqlite3_value **argv,
1015 sqlite3_context *pErrCtx
drh3fb153c2017-05-11 16:49:59 +00001016){
1017 const char *zJson = (const char*)sqlite3_value_text(argv[0]);
1018 int nJson = sqlite3_value_bytes(argv[0]);
1019 JsonParse *p;
drhe35fc302018-08-30 01:52:10 +00001020 JsonParse *pMatch = 0;
1021 int iKey;
1022 int iMinKey = 0;
1023 u32 iMinHold = 0xffffffff;
1024 u32 iMaxHold = 0;
drh3fb153c2017-05-11 16:49:59 +00001025 if( zJson==0 ) return 0;
drhe35fc302018-08-30 01:52:10 +00001026 for(iKey=0; iKey<JSON_CACHE_SZ; iKey++){
1027 p = (JsonParse*)sqlite3_get_auxdata(pCtx, JSON_CACHE_ID+iKey);
1028 if( p==0 ){
1029 iMinKey = iKey;
1030 break;
1031 }
1032 if( pMatch==0
1033 && p->nJson==nJson
1034 && memcmp(p->zJson,zJson,nJson)==0
1035 ){
1036 p->nErr = 0;
1037 pMatch = p;
1038 }else if( p->iHold<iMinHold ){
1039 iMinHold = p->iHold;
1040 iMinKey = iKey;
1041 }
1042 if( p->iHold>iMaxHold ){
1043 iMaxHold = p->iHold;
1044 }
1045 }
1046 if( pMatch ){
1047 pMatch->nErr = 0;
1048 pMatch->iHold = iMaxHold+1;
1049 return pMatch;
drh3fb153c2017-05-11 16:49:59 +00001050 }
drh2d77d802019-01-08 20:02:48 +00001051 p = sqlite3_malloc64( sizeof(*p) + nJson + 1 );
drh3fb153c2017-05-11 16:49:59 +00001052 if( p==0 ){
1053 sqlite3_result_error_nomem(pCtx);
1054 return 0;
1055 }
1056 memset(p, 0, sizeof(*p));
1057 p->zJson = (char*)&p[1];
1058 memcpy((char*)p->zJson, zJson, nJson+1);
drhe35fc302018-08-30 01:52:10 +00001059 if( jsonParse(p, pErrCtx, p->zJson) ){
drh3fb153c2017-05-11 16:49:59 +00001060 sqlite3_free(p);
1061 return 0;
1062 }
1063 p->nJson = nJson;
drhe35fc302018-08-30 01:52:10 +00001064 p->iHold = iMaxHold+1;
1065 sqlite3_set_auxdata(pCtx, JSON_CACHE_ID+iMinKey, p,
1066 (void(*)(void*))jsonParseFree);
1067 return (JsonParse*)sqlite3_get_auxdata(pCtx, JSON_CACHE_ID+iMinKey);
drh3fb153c2017-05-11 16:49:59 +00001068}
1069
1070/*
drh8cb0c832015-09-22 00:21:03 +00001071** Compare the OBJECT label at pNode against zKey,nKey. Return true on
1072** a match.
1073*/
mistachkinf2c26ed2015-10-12 22:20:29 +00001074static int jsonLabelCompare(JsonNode *pNode, const char *zKey, u32 nKey){
drh285f2ef2021-10-15 16:15:04 +00001075 assert( pNode->eU==1 );
drh8cb0c832015-09-22 00:21:03 +00001076 if( pNode->jnFlags & JNODE_RAW ){
1077 if( pNode->n!=nKey ) return 0;
1078 return strncmp(pNode->u.zJContent, zKey, nKey)==0;
1079 }else{
1080 if( pNode->n!=nKey+2 ) return 0;
1081 return strncmp(pNode->u.zJContent+1, zKey, nKey)==0;
1082 }
1083}
1084
drh52216ad2015-08-18 02:28:03 +00001085/* forward declaration */
drha7714022015-08-29 00:54:49 +00001086static JsonNode *jsonLookupAppend(JsonParse*,const char*,int*,const char**);
drh52216ad2015-08-18 02:28:03 +00001087
drh987eb1f2015-08-17 15:17:37 +00001088/*
1089** Search along zPath to find the node specified. Return a pointer
1090** to that node, or NULL if zPath is malformed or if there is no such
1091** node.
drh52216ad2015-08-18 02:28:03 +00001092**
1093** If pApnd!=0, then try to append new nodes to complete zPath if it is
1094** possible to do so and if no existing node corresponds to zPath. If
1095** new nodes are appended *pApnd is set to 1.
drh987eb1f2015-08-17 15:17:37 +00001096*/
drha7714022015-08-29 00:54:49 +00001097static JsonNode *jsonLookupStep(
drh52216ad2015-08-18 02:28:03 +00001098 JsonParse *pParse, /* The JSON to search */
1099 u32 iRoot, /* Begin the search at this node */
1100 const char *zPath, /* The path to search */
drha7714022015-08-29 00:54:49 +00001101 int *pApnd, /* Append nodes to complete path if not NULL */
1102 const char **pzErr /* Make *pzErr point to any syntax error in zPath */
drh52216ad2015-08-18 02:28:03 +00001103){
drhbc8f0922015-08-22 19:39:04 +00001104 u32 i, j, nKey;
drh6b43cc82015-08-19 23:02:49 +00001105 const char *zKey;
drh52216ad2015-08-18 02:28:03 +00001106 JsonNode *pRoot = &pParse->aNode[iRoot];
drh987eb1f2015-08-17 15:17:37 +00001107 if( zPath[0]==0 ) return pRoot;
drh7e35e812019-07-31 12:13:58 +00001108 if( pRoot->jnFlags & JNODE_REPLACE ) return 0;
drh987eb1f2015-08-17 15:17:37 +00001109 if( zPath[0]=='.' ){
1110 if( pRoot->eType!=JSON_OBJECT ) return 0;
1111 zPath++;
drh6b43cc82015-08-19 23:02:49 +00001112 if( zPath[0]=='"' ){
1113 zKey = zPath + 1;
1114 for(i=1; zPath[i] && zPath[i]!='"'; i++){}
1115 nKey = i-1;
drha8f39a92015-09-21 22:53:16 +00001116 if( zPath[i] ){
1117 i++;
1118 }else{
1119 *pzErr = zPath;
1120 return 0;
1121 }
drhb07fb4f1c2022-04-04 14:24:14 +00001122 testcase( nKey==0 );
drh6b43cc82015-08-19 23:02:49 +00001123 }else{
1124 zKey = zPath;
1125 for(i=0; zPath[i] && zPath[i]!='.' && zPath[i]!='['; i++){}
1126 nKey = i;
drhb07fb4f1c2022-04-04 14:24:14 +00001127 if( nKey==0 ){
1128 *pzErr = zPath;
1129 return 0;
1130 }
drha7714022015-08-29 00:54:49 +00001131 }
drh987eb1f2015-08-17 15:17:37 +00001132 j = 1;
drh52216ad2015-08-18 02:28:03 +00001133 for(;;){
1134 while( j<=pRoot->n ){
drh8cb0c832015-09-22 00:21:03 +00001135 if( jsonLabelCompare(pRoot+j, zKey, nKey) ){
drha7714022015-08-29 00:54:49 +00001136 return jsonLookupStep(pParse, iRoot+j+1, &zPath[i], pApnd, pzErr);
drh52216ad2015-08-18 02:28:03 +00001137 }
1138 j++;
drh505ad2c2015-08-21 17:33:11 +00001139 j += jsonNodeSize(&pRoot[j]);
drh987eb1f2015-08-17 15:17:37 +00001140 }
drh52216ad2015-08-18 02:28:03 +00001141 if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;
drh285f2ef2021-10-15 16:15:04 +00001142 assert( pRoot->eU==2 );
drh52216ad2015-08-18 02:28:03 +00001143 iRoot += pRoot->u.iAppend;
1144 pRoot = &pParse->aNode[iRoot];
1145 j = 1;
1146 }
1147 if( pApnd ){
drhbc8f0922015-08-22 19:39:04 +00001148 u32 iStart, iLabel;
1149 JsonNode *pNode;
1150 iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
danfe9a8322019-06-17 14:50:33 +00001151 iLabel = jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
drh52216ad2015-08-18 02:28:03 +00001152 zPath += i;
drha7714022015-08-29 00:54:49 +00001153 pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
drhbc8f0922015-08-22 19:39:04 +00001154 if( pParse->oom ) return 0;
1155 if( pNode ){
1156 pRoot = &pParse->aNode[iRoot];
drh285f2ef2021-10-15 16:15:04 +00001157 assert( pRoot->eU==0 );
drhbc8f0922015-08-22 19:39:04 +00001158 pRoot->u.iAppend = iStart - iRoot;
1159 pRoot->jnFlags |= JNODE_APPEND;
drh285f2ef2021-10-15 16:15:04 +00001160 VVA( pRoot->eU = 2 );
drhbc8f0922015-08-22 19:39:04 +00001161 pParse->aNode[iLabel].jnFlags |= JNODE_RAW;
1162 }
1163 return pNode;
drh987eb1f2015-08-17 15:17:37 +00001164 }
drh52818642019-11-22 17:37:56 +00001165 }else if( zPath[0]=='[' ){
drh987eb1f2015-08-17 15:17:37 +00001166 i = 0;
drh3d1d2a92015-09-22 01:15:49 +00001167 j = 1;
drh9dbf96b2022-01-06 01:40:09 +00001168 while( sqlite3Isdigit(zPath[j]) ){
drh3d1d2a92015-09-22 01:15:49 +00001169 i = i*10 + zPath[j] - '0';
1170 j++;
drh987eb1f2015-08-17 15:17:37 +00001171 }
drh52818642019-11-22 17:37:56 +00001172 if( j<2 || zPath[j]!=']' ){
1173 if( zPath[1]=='#' ){
1174 JsonNode *pBase = pRoot;
1175 int iBase = iRoot;
1176 if( pRoot->eType!=JSON_ARRAY ) return 0;
1177 for(;;){
1178 while( j<=pBase->n ){
1179 if( (pBase[j].jnFlags & JNODE_REMOVE)==0 ) i++;
1180 j += jsonNodeSize(&pBase[j]);
1181 }
1182 if( (pBase->jnFlags & JNODE_APPEND)==0 ) break;
drh285f2ef2021-10-15 16:15:04 +00001183 assert( pBase->eU==2 );
drh52818642019-11-22 17:37:56 +00001184 iBase += pBase->u.iAppend;
1185 pBase = &pParse->aNode[iBase];
1186 j = 1;
1187 }
1188 j = 2;
drh9dbf96b2022-01-06 01:40:09 +00001189 if( zPath[2]=='-' && sqlite3Isdigit(zPath[3]) ){
drh52818642019-11-22 17:37:56 +00001190 unsigned int x = 0;
1191 j = 3;
1192 do{
1193 x = x*10 + zPath[j] - '0';
1194 j++;
drh9dbf96b2022-01-06 01:40:09 +00001195 }while( sqlite3Isdigit(zPath[j]) );
drh52818642019-11-22 17:37:56 +00001196 if( x>i ) return 0;
1197 i -= x;
1198 }
1199 if( zPath[j]!=']' ){
1200 *pzErr = zPath;
1201 return 0;
1202 }
1203 }else{
1204 *pzErr = zPath;
1205 return 0;
1206 }
drha7714022015-08-29 00:54:49 +00001207 }
drh52818642019-11-22 17:37:56 +00001208 if( pRoot->eType!=JSON_ARRAY ) return 0;
drh3d1d2a92015-09-22 01:15:49 +00001209 zPath += j + 1;
drh987eb1f2015-08-17 15:17:37 +00001210 j = 1;
drh52216ad2015-08-18 02:28:03 +00001211 for(;;){
drhbc8f0922015-08-22 19:39:04 +00001212 while( j<=pRoot->n && (i>0 || (pRoot[j].jnFlags & JNODE_REMOVE)!=0) ){
1213 if( (pRoot[j].jnFlags & JNODE_REMOVE)==0 ) i--;
drh505ad2c2015-08-21 17:33:11 +00001214 j += jsonNodeSize(&pRoot[j]);
drh52216ad2015-08-18 02:28:03 +00001215 }
1216 if( (pRoot->jnFlags & JNODE_APPEND)==0 ) break;
drh285f2ef2021-10-15 16:15:04 +00001217 assert( pRoot->eU==2 );
drh52216ad2015-08-18 02:28:03 +00001218 iRoot += pRoot->u.iAppend;
1219 pRoot = &pParse->aNode[iRoot];
1220 j = 1;
drh987eb1f2015-08-17 15:17:37 +00001221 }
1222 if( j<=pRoot->n ){
drha7714022015-08-29 00:54:49 +00001223 return jsonLookupStep(pParse, iRoot+j, zPath, pApnd, pzErr);
drh52216ad2015-08-18 02:28:03 +00001224 }
1225 if( i==0 && pApnd ){
drhbc8f0922015-08-22 19:39:04 +00001226 u32 iStart;
1227 JsonNode *pNode;
1228 iStart = jsonParseAddNode(pParse, JSON_ARRAY, 1, 0);
drha7714022015-08-29 00:54:49 +00001229 pNode = jsonLookupAppend(pParse, zPath, pApnd, pzErr);
drhbc8f0922015-08-22 19:39:04 +00001230 if( pParse->oom ) return 0;
1231 if( pNode ){
1232 pRoot = &pParse->aNode[iRoot];
drh285f2ef2021-10-15 16:15:04 +00001233 assert( pRoot->eU==0 );
drhbc8f0922015-08-22 19:39:04 +00001234 pRoot->u.iAppend = iStart - iRoot;
1235 pRoot->jnFlags |= JNODE_APPEND;
drh285f2ef2021-10-15 16:15:04 +00001236 VVA( pRoot->eU = 2 );
drhbc8f0922015-08-22 19:39:04 +00001237 }
1238 return pNode;
drh987eb1f2015-08-17 15:17:37 +00001239 }
drh3d1d2a92015-09-22 01:15:49 +00001240 }else{
drha7714022015-08-29 00:54:49 +00001241 *pzErr = zPath;
drh987eb1f2015-08-17 15:17:37 +00001242 }
1243 return 0;
1244}
1245
drh52216ad2015-08-18 02:28:03 +00001246/*
drhbc8f0922015-08-22 19:39:04 +00001247** Append content to pParse that will complete zPath. Return a pointer
1248** to the inserted node, or return NULL if the append fails.
drh52216ad2015-08-18 02:28:03 +00001249*/
1250static JsonNode *jsonLookupAppend(
1251 JsonParse *pParse, /* Append content to the JSON parse */
1252 const char *zPath, /* Description of content to append */
drha7714022015-08-29 00:54:49 +00001253 int *pApnd, /* Set this flag to 1 */
1254 const char **pzErr /* Make this point to any syntax error */
drh52216ad2015-08-18 02:28:03 +00001255){
1256 *pApnd = 1;
1257 if( zPath[0]==0 ){
1258 jsonParseAddNode(pParse, JSON_NULL, 0, 0);
1259 return pParse->oom ? 0 : &pParse->aNode[pParse->nNode-1];
1260 }
1261 if( zPath[0]=='.' ){
1262 jsonParseAddNode(pParse, JSON_OBJECT, 0, 0);
1263 }else if( strncmp(zPath,"[0]",3)==0 ){
1264 jsonParseAddNode(pParse, JSON_ARRAY, 0, 0);
1265 }else{
1266 return 0;
1267 }
1268 if( pParse->oom ) return 0;
drha7714022015-08-29 00:54:49 +00001269 return jsonLookupStep(pParse, pParse->nNode-1, zPath, pApnd, pzErr);
drh52216ad2015-08-18 02:28:03 +00001270}
1271
drhbc8f0922015-08-22 19:39:04 +00001272/*
drha7714022015-08-29 00:54:49 +00001273** Return the text of a syntax error message on a JSON path. Space is
1274** obtained from sqlite3_malloc().
1275*/
1276static char *jsonPathSyntaxError(const char *zErr){
1277 return sqlite3_mprintf("JSON path error near '%q'", zErr);
1278}
1279
1280/*
1281** Do a node lookup using zPath. Return a pointer to the node on success.
1282** Return NULL if not found or if there is an error.
1283**
1284** On an error, write an error message into pCtx and increment the
1285** pParse->nErr counter.
1286**
1287** If pApnd!=NULL then try to append missing nodes and set *pApnd = 1 if
1288** nodes are appended.
drha7714022015-08-29 00:54:49 +00001289*/
1290static JsonNode *jsonLookup(
1291 JsonParse *pParse, /* The JSON to search */
1292 const char *zPath, /* The path to search */
1293 int *pApnd, /* Append nodes to complete path if not NULL */
drhf5ddb9c2015-09-11 00:06:41 +00001294 sqlite3_context *pCtx /* Report errors here, if not NULL */
drha7714022015-08-29 00:54:49 +00001295){
1296 const char *zErr = 0;
1297 JsonNode *pNode = 0;
drha8f39a92015-09-21 22:53:16 +00001298 char *zMsg;
drha7714022015-08-29 00:54:49 +00001299
1300 if( zPath==0 ) return 0;
1301 if( zPath[0]!='$' ){
1302 zErr = zPath;
1303 goto lookup_err;
1304 }
1305 zPath++;
drha7714022015-08-29 00:54:49 +00001306 pNode = jsonLookupStep(pParse, 0, zPath, pApnd, &zErr);
drha8f39a92015-09-21 22:53:16 +00001307 if( zErr==0 ) return pNode;
drha7714022015-08-29 00:54:49 +00001308
1309lookup_err:
1310 pParse->nErr++;
drha8f39a92015-09-21 22:53:16 +00001311 assert( zErr!=0 && pCtx!=0 );
1312 zMsg = jsonPathSyntaxError(zErr);
1313 if( zMsg ){
1314 sqlite3_result_error(pCtx, zMsg, -1);
1315 sqlite3_free(zMsg);
1316 }else{
1317 sqlite3_result_error_nomem(pCtx);
drha7714022015-08-29 00:54:49 +00001318 }
drha7714022015-08-29 00:54:49 +00001319 return 0;
1320}
1321
1322
1323/*
drhbc8f0922015-08-22 19:39:04 +00001324** Report the wrong number of arguments for json_insert(), json_replace()
1325** or json_set().
1326*/
1327static void jsonWrongNumArgs(
1328 sqlite3_context *pCtx,
1329 const char *zFuncName
1330){
1331 char *zMsg = sqlite3_mprintf("json_%s() needs an odd number of arguments",
1332 zFuncName);
1333 sqlite3_result_error(pCtx, zMsg, -1);
1334 sqlite3_free(zMsg);
1335}
drh52216ad2015-08-18 02:28:03 +00001336
drh29c99692017-03-24 12:35:17 +00001337/*
1338** Mark all NULL entries in the Object passed in as JNODE_REMOVE.
1339*/
1340static void jsonRemoveAllNulls(JsonNode *pNode){
1341 int i, n;
1342 assert( pNode->eType==JSON_OBJECT );
1343 n = pNode->n;
1344 for(i=2; i<=n; i += jsonNodeSize(&pNode[i])+1){
1345 switch( pNode[i].eType ){
1346 case JSON_NULL:
1347 pNode[i].jnFlags |= JNODE_REMOVE;
1348 break;
1349 case JSON_OBJECT:
1350 jsonRemoveAllNulls(&pNode[i]);
1351 break;
1352 }
1353 }
1354}
1355
drha7714022015-08-29 00:54:49 +00001356
drh987eb1f2015-08-17 15:17:37 +00001357/****************************************************************************
1358** SQL functions used for testing and debugging
1359****************************************************************************/
drhe9c37f32015-08-15 21:25:36 +00001360
drh301eecc2015-08-17 20:14:19 +00001361#ifdef SQLITE_DEBUG
drhe9c37f32015-08-15 21:25:36 +00001362/*
drh5634cc02015-08-17 11:28:03 +00001363** The json_parse(JSON) function returns a string which describes
drhe9c37f32015-08-15 21:25:36 +00001364** a parse of the JSON provided. Or it returns NULL if JSON is not
1365** well-formed.
1366*/
drh5634cc02015-08-17 11:28:03 +00001367static void jsonParseFunc(
drhbc8f0922015-08-22 19:39:04 +00001368 sqlite3_context *ctx,
drhe9c37f32015-08-15 21:25:36 +00001369 int argc,
1370 sqlite3_value **argv
1371){
drh505ad2c2015-08-21 17:33:11 +00001372 JsonString s; /* Output string - not real JSON */
1373 JsonParse x; /* The parse */
drhe9c37f32015-08-15 21:25:36 +00001374 u32 i;
drhe9c37f32015-08-15 21:25:36 +00001375
1376 assert( argc==1 );
drhbc8f0922015-08-22 19:39:04 +00001377 if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
drh8784eca2015-08-23 02:42:30 +00001378 jsonParseFindParents(&x);
drhbc8f0922015-08-22 19:39:04 +00001379 jsonInit(&s, ctx);
drhe9c37f32015-08-15 21:25:36 +00001380 for(i=0; i<x.nNode; i++){
drh852944e2015-09-10 03:29:11 +00001381 const char *zType;
1382 if( x.aNode[i].jnFlags & JNODE_LABEL ){
1383 assert( x.aNode[i].eType==JSON_STRING );
1384 zType = "label";
1385 }else{
1386 zType = jsonType[x.aNode[i].eType];
drhe9c37f32015-08-15 21:25:36 +00001387 }
drh852944e2015-09-10 03:29:11 +00001388 jsonPrintf(100, &s,"node %3u: %7s n=%-4d up=%-4d",
1389 i, zType, x.aNode[i].n, x.aUp[i]);
drh285f2ef2021-10-15 16:15:04 +00001390 assert( x.aNode[i].eU==0 || x.aNode[i].eU==1 );
drh852944e2015-09-10 03:29:11 +00001391 if( x.aNode[i].u.zJContent!=0 ){
drh285f2ef2021-10-15 16:15:04 +00001392 assert( x.aNode[i].eU==1 );
drh852944e2015-09-10 03:29:11 +00001393 jsonAppendRaw(&s, " ", 1);
1394 jsonAppendRaw(&s, x.aNode[i].u.zJContent, x.aNode[i].n);
drh285f2ef2021-10-15 16:15:04 +00001395 }else{
1396 assert( x.aNode[i].eU==0 );
drh852944e2015-09-10 03:29:11 +00001397 }
1398 jsonAppendRaw(&s, "\n", 1);
drhe9c37f32015-08-15 21:25:36 +00001399 }
drh505ad2c2015-08-21 17:33:11 +00001400 jsonParseReset(&x);
drhe9c37f32015-08-15 21:25:36 +00001401 jsonResult(&s);
1402}
1403
drh5634cc02015-08-17 11:28:03 +00001404/*
drhf5ddb9c2015-09-11 00:06:41 +00001405** The json_test1(JSON) function return true (1) if the input is JSON
1406** text generated by another json function. It returns (0) if the input
1407** is not known to be JSON.
drh5634cc02015-08-17 11:28:03 +00001408*/
1409static void jsonTest1Func(
drhbc8f0922015-08-22 19:39:04 +00001410 sqlite3_context *ctx,
drh5634cc02015-08-17 11:28:03 +00001411 int argc,
1412 sqlite3_value **argv
1413){
drh9dbf96b2022-01-06 01:40:09 +00001414 UNUSED_PARAMETER(argc);
drhf5ddb9c2015-09-11 00:06:41 +00001415 sqlite3_result_int(ctx, sqlite3_value_subtype(argv[0])==JSON_SUBTYPE);
drh5634cc02015-08-17 11:28:03 +00001416}
drh301eecc2015-08-17 20:14:19 +00001417#endif /* SQLITE_DEBUG */
drh5634cc02015-08-17 11:28:03 +00001418
drh987eb1f2015-08-17 15:17:37 +00001419/****************************************************************************
drhff135ae2015-12-30 01:07:02 +00001420** Scalar SQL function implementations
drh987eb1f2015-08-17 15:17:37 +00001421****************************************************************************/
1422
1423/*
drh2ad96f52016-06-17 13:01:51 +00001424** Implementation of the json_QUOTE(VALUE) function. Return a JSON value
1425** corresponding to the SQL value input. Mostly this means putting
1426** double-quotes around strings and returning the unquoted string "null"
1427** when given a NULL input.
1428*/
1429static void jsonQuoteFunc(
1430 sqlite3_context *ctx,
1431 int argc,
1432 sqlite3_value **argv
1433){
1434 JsonString jx;
drh9dbf96b2022-01-06 01:40:09 +00001435 UNUSED_PARAMETER(argc);
drh2ad96f52016-06-17 13:01:51 +00001436
1437 jsonInit(&jx, ctx);
1438 jsonAppendValue(&jx, argv[0]);
1439 jsonResult(&jx);
1440 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
1441}
1442
1443/*
drh987eb1f2015-08-17 15:17:37 +00001444** Implementation of the json_array(VALUE,...) function. Return a JSON
1445** array that contains all values given in arguments. Or if any argument
1446** is a BLOB, throw an error.
1447*/
1448static void jsonArrayFunc(
drhbc8f0922015-08-22 19:39:04 +00001449 sqlite3_context *ctx,
drh987eb1f2015-08-17 15:17:37 +00001450 int argc,
1451 sqlite3_value **argv
1452){
1453 int i;
drh505ad2c2015-08-21 17:33:11 +00001454 JsonString jx;
drh987eb1f2015-08-17 15:17:37 +00001455
drhbc8f0922015-08-22 19:39:04 +00001456 jsonInit(&jx, ctx);
drhd0960592015-08-17 21:22:32 +00001457 jsonAppendChar(&jx, '[');
drh987eb1f2015-08-17 15:17:37 +00001458 for(i=0; i<argc; i++){
drhd0960592015-08-17 21:22:32 +00001459 jsonAppendSeparator(&jx);
drhf5ddb9c2015-09-11 00:06:41 +00001460 jsonAppendValue(&jx, argv[i]);
drh987eb1f2015-08-17 15:17:37 +00001461 }
drhd0960592015-08-17 21:22:32 +00001462 jsonAppendChar(&jx, ']');
drh987eb1f2015-08-17 15:17:37 +00001463 jsonResult(&jx);
drhf5ddb9c2015-09-11 00:06:41 +00001464 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
drh987eb1f2015-08-17 15:17:37 +00001465}
1466
1467
1468/*
1469** json_array_length(JSON)
1470** json_array_length(JSON, PATH)
1471**
1472** Return the number of elements in the top-level JSON array.
1473** Return 0 if the input is not a well-formed JSON array.
1474*/
1475static void jsonArrayLengthFunc(
drhbc8f0922015-08-22 19:39:04 +00001476 sqlite3_context *ctx,
drh987eb1f2015-08-17 15:17:37 +00001477 int argc,
1478 sqlite3_value **argv
1479){
drh3fb153c2017-05-11 16:49:59 +00001480 JsonParse *p; /* The parse */
drh987eb1f2015-08-17 15:17:37 +00001481 sqlite3_int64 n = 0;
1482 u32 i;
drha8f39a92015-09-21 22:53:16 +00001483 JsonNode *pNode;
drh987eb1f2015-08-17 15:17:37 +00001484
drhe35fc302018-08-30 01:52:10 +00001485 p = jsonParseCached(ctx, argv, ctx);
drh3fb153c2017-05-11 16:49:59 +00001486 if( p==0 ) return;
1487 assert( p->nNode );
drha8f39a92015-09-21 22:53:16 +00001488 if( argc==2 ){
1489 const char *zPath = (const char*)sqlite3_value_text(argv[1]);
drh3fb153c2017-05-11 16:49:59 +00001490 pNode = jsonLookup(p, zPath, 0, ctx);
drha8f39a92015-09-21 22:53:16 +00001491 }else{
drh3fb153c2017-05-11 16:49:59 +00001492 pNode = p->aNode;
drha8f39a92015-09-21 22:53:16 +00001493 }
1494 if( pNode==0 ){
drh3fb153c2017-05-11 16:49:59 +00001495 return;
1496 }
1497 if( pNode->eType==JSON_ARRAY ){
drha8f39a92015-09-21 22:53:16 +00001498 assert( (pNode->jnFlags & JNODE_APPEND)==0 );
1499 for(i=1; i<=pNode->n; n++){
1500 i += jsonNodeSize(&pNode[i]);
drh987eb1f2015-08-17 15:17:37 +00001501 }
drh987eb1f2015-08-17 15:17:37 +00001502 }
drh3fb153c2017-05-11 16:49:59 +00001503 sqlite3_result_int64(ctx, n);
drhf6ec8d42015-08-28 03:48:04 +00001504}
1505
1506/*
drhdc60c682022-01-08 15:05:53 +00001507** Bit values for the flags passed into jsonExtractFunc() or
1508** jsonSetFunc() via the user-data value.
1509*/
drhd83c90b2022-01-10 15:43:13 +00001510#define JSON_JSON 0x01 /* Result is always JSON */
1511#define JSON_SQL 0x02 /* Result is always SQL */
1512#define JSON_ABPATH 0x03 /* Allow abbreviated JSON path specs */
drhdc60c682022-01-08 15:05:53 +00001513#define JSON_ISSET 0x04 /* json_set(), not json_insert() */
1514
1515/*
drh3ad93bb2015-08-29 19:41:45 +00001516** json_extract(JSON, PATH, ...)
drhdc60c682022-01-08 15:05:53 +00001517** "->"(JSON,PATH)
1518** "->>"(JSON,PATH)
drh987eb1f2015-08-17 15:17:37 +00001519**
drhdc60c682022-01-08 15:05:53 +00001520** Return the element described by PATH. Return NULL if that PATH element
drhd83c90b2022-01-10 15:43:13 +00001521** is not found.
drhdc60c682022-01-08 15:05:53 +00001522**
drhd83c90b2022-01-10 15:43:13 +00001523** If JSON_JSON is set or if more that one PATH argument is supplied then
1524** always return a JSON representation of the result. If JSON_SQL is set,
1525** then always return an SQL representation of the result. If neither flag
1526** is present and argc==2, then return JSON for objects and arrays and SQL
1527** for all other values.
drhdc60c682022-01-08 15:05:53 +00001528**
drhd83c90b2022-01-10 15:43:13 +00001529** When multiple PATH arguments are supplied, the result is a JSON array
1530** containing the result of each PATH.
drhdc60c682022-01-08 15:05:53 +00001531**
drhd83c90b2022-01-10 15:43:13 +00001532** Abbreviated JSON path expressions are allows if JSON_ABPATH, for
1533** compatibility with PG.
drh987eb1f2015-08-17 15:17:37 +00001534*/
1535static void jsonExtractFunc(
drhbc8f0922015-08-22 19:39:04 +00001536 sqlite3_context *ctx,
drh987eb1f2015-08-17 15:17:37 +00001537 int argc,
1538 sqlite3_value **argv
1539){
drh3fb153c2017-05-11 16:49:59 +00001540 JsonParse *p; /* The parse */
drh987eb1f2015-08-17 15:17:37 +00001541 JsonNode *pNode;
1542 const char *zPath;
drhdaefcd92022-01-08 15:37:13 +00001543 int flags = SQLITE_PTR_TO_INT(sqlite3_user_data(ctx));
drh3ad93bb2015-08-29 19:41:45 +00001544 JsonString jx;
drh3ad93bb2015-08-29 19:41:45 +00001545
1546 if( argc<2 ) return;
drhd83c90b2022-01-10 15:43:13 +00001547 p = jsonParseCached(ctx, argv, ctx);
1548 if( p==0 ) return;
drh12b9fa92022-01-07 15:47:12 +00001549 if( argc==2 ){
drhd83c90b2022-01-10 15:43:13 +00001550 /* With a single PATH argument */
drh12b9fa92022-01-07 15:47:12 +00001551 zPath = (const char*)sqlite3_value_text(argv[1]);
drhd83c90b2022-01-10 15:43:13 +00001552 if( zPath==0 ) return;
drhaa97b572022-01-11 18:01:17 +00001553 if( flags & JSON_ABPATH ){
1554 if( zPath[0]!='$' ){
1555 /* The -> and ->> operators accept abbreviated PATH arguments. This
1556 ** is mostly for compatibility with PostgreSQL, but also for
1557 ** convenience.
1558 **
1559 ** NUMBER ==> $[NUMBER] // PG compatible
1560 ** LABEL ==> $.LABEL // PG compatible
1561 ** [NUMBER] ==> $[NUMBER] // Not PG. Purely for convenience
1562 */
1563 jsonInit(&jx, ctx);
1564 if( sqlite3Isdigit(zPath[0]) ){
1565 jsonAppendRaw(&jx, "$[", 2);
1566 jsonAppendRaw(&jx, zPath, (int)strlen(zPath));
1567 jsonAppendRaw(&jx, "]", 2);
1568 }else{
1569 jsonAppendRaw(&jx, "$.", 1 + (zPath[0]!='['));
1570 jsonAppendRaw(&jx, zPath, (int)strlen(zPath));
1571 jsonAppendChar(&jx, 0);
1572 }
1573 pNode = jx.bErr ? 0 : jsonLookup(p, jx.zBuf, 0, ctx);
1574 jsonReset(&jx);
drh12b9fa92022-01-07 15:47:12 +00001575 }else{
drhaa97b572022-01-11 18:01:17 +00001576 pNode = jsonLookup(p, zPath, 0, ctx);
drh12b9fa92022-01-07 15:47:12 +00001577 }
drhaa97b572022-01-11 18:01:17 +00001578 if( pNode ){
1579 if( flags & JSON_JSON ){
drhd83c90b2022-01-10 15:43:13 +00001580 jsonReturnJson(pNode, ctx, 0);
1581 }else{
1582 jsonReturn(pNode, ctx, 0);
1583 sqlite3_result_subtype(ctx, 0);
1584 }
1585 }
drh12b9fa92022-01-07 15:47:12 +00001586 }else{
1587 pNode = jsonLookup(p, zPath, 0, ctx);
drhd83c90b2022-01-10 15:43:13 +00001588 if( p->nErr==0 && pNode ) jsonReturn(pNode, ctx, 0);
drh12b9fa92022-01-07 15:47:12 +00001589 }
drh12b9fa92022-01-07 15:47:12 +00001590 }else{
1591 /* Two or more PATH arguments results in a JSON array with each
1592 ** element of the array being the value selected by one of the PATHs */
1593 int i;
1594 jsonInit(&jx, ctx);
1595 jsonAppendChar(&jx, '[');
1596 for(i=1; i<argc; i++){
1597 zPath = (const char*)sqlite3_value_text(argv[i]);
1598 pNode = jsonLookup(p, zPath, 0, ctx);
1599 if( p->nErr ) break;
drh3ad93bb2015-08-29 19:41:45 +00001600 jsonAppendSeparator(&jx);
1601 if( pNode ){
1602 jsonRenderNode(pNode, &jx, 0);
1603 }else{
1604 jsonAppendRaw(&jx, "null", 4);
1605 }
drh3ad93bb2015-08-29 19:41:45 +00001606 }
drh12b9fa92022-01-07 15:47:12 +00001607 if( i==argc ){
1608 jsonAppendChar(&jx, ']');
1609 jsonResult(&jx);
1610 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
1611 }
1612 jsonReset(&jx);
drh987eb1f2015-08-17 15:17:37 +00001613 }
drh987eb1f2015-08-17 15:17:37 +00001614}
1615
drh633647a2017-03-22 21:24:31 +00001616/* This is the RFC 7396 MergePatch algorithm.
1617*/
1618static JsonNode *jsonMergePatch(
1619 JsonParse *pParse, /* The JSON parser that contains the TARGET */
mistachkinb1ed7172017-04-14 14:50:34 +00001620 u32 iTarget, /* Node of the TARGET in pParse */
drh633647a2017-03-22 21:24:31 +00001621 JsonNode *pPatch /* The PATCH */
1622){
drh0002d242017-03-23 00:46:15 +00001623 u32 i, j;
1624 u32 iRoot;
drh633647a2017-03-22 21:24:31 +00001625 JsonNode *pTarget;
1626 if( pPatch->eType!=JSON_OBJECT ){
1627 return pPatch;
1628 }
drhe684ac62022-03-08 13:59:46 +00001629 assert( iTarget<pParse->nNode );
drh633647a2017-03-22 21:24:31 +00001630 pTarget = &pParse->aNode[iTarget];
1631 assert( (pPatch->jnFlags & JNODE_APPEND)==0 );
1632 if( pTarget->eType!=JSON_OBJECT ){
drh29c99692017-03-24 12:35:17 +00001633 jsonRemoveAllNulls(pPatch);
drh633647a2017-03-22 21:24:31 +00001634 return pPatch;
1635 }
drhbb7aa2d2017-03-23 00:13:52 +00001636 iRoot = iTarget;
drh633647a2017-03-22 21:24:31 +00001637 for(i=1; i<pPatch->n; i += jsonNodeSize(&pPatch[i+1])+1){
drhba7cce32017-03-24 19:45:05 +00001638 u32 nKey;
drh633647a2017-03-22 21:24:31 +00001639 const char *zKey;
1640 assert( pPatch[i].eType==JSON_STRING );
1641 assert( pPatch[i].jnFlags & JNODE_LABEL );
drh285f2ef2021-10-15 16:15:04 +00001642 assert( pPatch[i].eU==1 );
drh633647a2017-03-22 21:24:31 +00001643 nKey = pPatch[i].n;
1644 zKey = pPatch[i].u.zJContent;
drhbb7aa2d2017-03-23 00:13:52 +00001645 assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
drh633647a2017-03-22 21:24:31 +00001646 for(j=1; j<pTarget->n; j += jsonNodeSize(&pTarget[j+1])+1 ){
1647 assert( pTarget[j].eType==JSON_STRING );
1648 assert( pTarget[j].jnFlags & JNODE_LABEL );
drhbb7aa2d2017-03-23 00:13:52 +00001649 assert( (pPatch[i].jnFlags & JNODE_RAW)==0 );
drh1fe162f2017-03-23 12:56:44 +00001650 if( pTarget[j].n==nKey && strncmp(pTarget[j].u.zJContent,zKey,nKey)==0 ){
1651 if( pTarget[j+1].jnFlags & (JNODE_REMOVE|JNODE_PATCH) ) break;
drh633647a2017-03-22 21:24:31 +00001652 if( pPatch[i+1].eType==JSON_NULL ){
1653 pTarget[j+1].jnFlags |= JNODE_REMOVE;
1654 }else{
drhbb7aa2d2017-03-23 00:13:52 +00001655 JsonNode *pNew = jsonMergePatch(pParse, iTarget+j+1, &pPatch[i+1]);
drh633647a2017-03-22 21:24:31 +00001656 if( pNew==0 ) return 0;
1657 pTarget = &pParse->aNode[iTarget];
1658 if( pNew!=&pTarget[j+1] ){
drha2852ac2021-11-15 01:45:11 +00001659 assert( pTarget[j+1].eU==0
1660 || pTarget[j+1].eU==1
1661 || pTarget[j+1].eU==2 );
drh285f2ef2021-10-15 16:15:04 +00001662 testcase( pTarget[j+1].eU==1 );
drha2852ac2021-11-15 01:45:11 +00001663 testcase( pTarget[j+1].eU==2 );
drh285f2ef2021-10-15 16:15:04 +00001664 VVA( pTarget[j+1].eU = 5 );
drh633647a2017-03-22 21:24:31 +00001665 pTarget[j+1].u.pPatch = pNew;
1666 pTarget[j+1].jnFlags |= JNODE_PATCH;
1667 }
1668 }
1669 break;
1670 }
1671 }
drhbb7aa2d2017-03-23 00:13:52 +00001672 if( j>=pTarget->n && pPatch[i+1].eType!=JSON_NULL ){
drh633647a2017-03-22 21:24:31 +00001673 int iStart, iPatch;
1674 iStart = jsonParseAddNode(pParse, JSON_OBJECT, 2, 0);
1675 jsonParseAddNode(pParse, JSON_STRING, nKey, zKey);
1676 iPatch = jsonParseAddNode(pParse, JSON_TRUE, 0, 0);
1677 if( pParse->oom ) return 0;
drh29c99692017-03-24 12:35:17 +00001678 jsonRemoveAllNulls(pPatch);
drh633647a2017-03-22 21:24:31 +00001679 pTarget = &pParse->aNode[iTarget];
drh8b554e22021-10-20 20:22:37 +00001680 assert( pParse->aNode[iRoot].eU==0 || pParse->aNode[iRoot].eU==2 );
1681 testcase( pParse->aNode[iRoot].eU==2 );
drhbb7aa2d2017-03-23 00:13:52 +00001682 pParse->aNode[iRoot].jnFlags |= JNODE_APPEND;
drh285f2ef2021-10-15 16:15:04 +00001683 VVA( pParse->aNode[iRoot].eU = 2 );
drhbb7aa2d2017-03-23 00:13:52 +00001684 pParse->aNode[iRoot].u.iAppend = iStart - iRoot;
1685 iRoot = iStart;
drh285f2ef2021-10-15 16:15:04 +00001686 assert( pParse->aNode[iPatch].eU==0 );
1687 VVA( pParse->aNode[iPatch].eU = 5 );
drh633647a2017-03-22 21:24:31 +00001688 pParse->aNode[iPatch].jnFlags |= JNODE_PATCH;
1689 pParse->aNode[iPatch].u.pPatch = &pPatch[i+1];
1690 }
1691 }
1692 return pTarget;
1693}
1694
1695/*
1696** Implementation of the json_mergepatch(JSON1,JSON2) function. Return a JSON
1697** object that is the result of running the RFC 7396 MergePatch() algorithm
1698** on the two arguments.
1699*/
drh37f03df2017-03-23 20:33:49 +00001700static void jsonPatchFunc(
drh633647a2017-03-22 21:24:31 +00001701 sqlite3_context *ctx,
1702 int argc,
1703 sqlite3_value **argv
1704){
1705 JsonParse x; /* The JSON that is being patched */
1706 JsonParse y; /* The patch */
drhbb7aa2d2017-03-23 00:13:52 +00001707 JsonNode *pResult; /* The result of the merge */
drh633647a2017-03-22 21:24:31 +00001708
drh9dbf96b2022-01-06 01:40:09 +00001709 UNUSED_PARAMETER(argc);
drh633647a2017-03-22 21:24:31 +00001710 if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
1711 if( jsonParse(&y, ctx, (const char*)sqlite3_value_text(argv[1])) ){
1712 jsonParseReset(&x);
1713 return;
1714 }
drhbb7aa2d2017-03-23 00:13:52 +00001715 pResult = jsonMergePatch(&x, 0, y.aNode);
1716 assert( pResult!=0 || x.oom );
1717 if( pResult ){
1718 jsonReturnJson(pResult, ctx, 0);
1719 }else{
1720 sqlite3_result_error_nomem(ctx);
1721 }
drh633647a2017-03-22 21:24:31 +00001722 jsonParseReset(&x);
1723 jsonParseReset(&y);
1724}
1725
1726
drh987eb1f2015-08-17 15:17:37 +00001727/*
1728** Implementation of the json_object(NAME,VALUE,...) function. Return a JSON
1729** object that contains all name/value given in arguments. Or if any name
1730** is not a string or if any value is a BLOB, throw an error.
1731*/
1732static void jsonObjectFunc(
drhbc8f0922015-08-22 19:39:04 +00001733 sqlite3_context *ctx,
drh987eb1f2015-08-17 15:17:37 +00001734 int argc,
1735 sqlite3_value **argv
1736){
1737 int i;
drh505ad2c2015-08-21 17:33:11 +00001738 JsonString jx;
drh987eb1f2015-08-17 15:17:37 +00001739 const char *z;
1740 u32 n;
1741
1742 if( argc&1 ){
drhbc8f0922015-08-22 19:39:04 +00001743 sqlite3_result_error(ctx, "json_object() requires an even number "
drh987eb1f2015-08-17 15:17:37 +00001744 "of arguments", -1);
1745 return;
1746 }
drhbc8f0922015-08-22 19:39:04 +00001747 jsonInit(&jx, ctx);
drhd0960592015-08-17 21:22:32 +00001748 jsonAppendChar(&jx, '{');
drh987eb1f2015-08-17 15:17:37 +00001749 for(i=0; i<argc; i+=2){
drh987eb1f2015-08-17 15:17:37 +00001750 if( sqlite3_value_type(argv[i])!=SQLITE_TEXT ){
drhbc8f0922015-08-22 19:39:04 +00001751 sqlite3_result_error(ctx, "json_object() labels must be TEXT", -1);
drhdc384952015-09-19 18:54:39 +00001752 jsonReset(&jx);
drh987eb1f2015-08-17 15:17:37 +00001753 return;
1754 }
drhd0960592015-08-17 21:22:32 +00001755 jsonAppendSeparator(&jx);
drh987eb1f2015-08-17 15:17:37 +00001756 z = (const char*)sqlite3_value_text(argv[i]);
1757 n = (u32)sqlite3_value_bytes(argv[i]);
1758 jsonAppendString(&jx, z, n);
drhd0960592015-08-17 21:22:32 +00001759 jsonAppendChar(&jx, ':');
drhf5ddb9c2015-09-11 00:06:41 +00001760 jsonAppendValue(&jx, argv[i+1]);
drh987eb1f2015-08-17 15:17:37 +00001761 }
drhd0960592015-08-17 21:22:32 +00001762 jsonAppendChar(&jx, '}');
drh987eb1f2015-08-17 15:17:37 +00001763 jsonResult(&jx);
drhf5ddb9c2015-09-11 00:06:41 +00001764 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
drh987eb1f2015-08-17 15:17:37 +00001765}
1766
1767
1768/*
drh301eecc2015-08-17 20:14:19 +00001769** json_remove(JSON, PATH, ...)
1770**
drh3ad93bb2015-08-29 19:41:45 +00001771** Remove the named elements from JSON and return the result. malformed
1772** JSON or PATH arguments result in an error.
drh301eecc2015-08-17 20:14:19 +00001773*/
1774static void jsonRemoveFunc(
drhbc8f0922015-08-22 19:39:04 +00001775 sqlite3_context *ctx,
drh301eecc2015-08-17 20:14:19 +00001776 int argc,
1777 sqlite3_value **argv
1778){
1779 JsonParse x; /* The parse */
1780 JsonNode *pNode;
1781 const char *zPath;
1782 u32 i;
1783
1784 if( argc<1 ) return;
drhbc8f0922015-08-22 19:39:04 +00001785 if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
drha8f39a92015-09-21 22:53:16 +00001786 assert( x.nNode );
1787 for(i=1; i<(u32)argc; i++){
1788 zPath = (const char*)sqlite3_value_text(argv[i]);
1789 if( zPath==0 ) goto remove_done;
1790 pNode = jsonLookup(&x, zPath, 0, ctx);
1791 if( x.nErr ) goto remove_done;
1792 if( pNode ) pNode->jnFlags |= JNODE_REMOVE;
1793 }
1794 if( (x.aNode[0].jnFlags & JNODE_REMOVE)==0 ){
1795 jsonReturnJson(x.aNode, ctx, 0);
drhd0960592015-08-17 21:22:32 +00001796 }
drha7714022015-08-29 00:54:49 +00001797remove_done:
drh505ad2c2015-08-21 17:33:11 +00001798 jsonParseReset(&x);
drhd0960592015-08-17 21:22:32 +00001799}
1800
1801/*
1802** json_replace(JSON, PATH, VALUE, ...)
1803**
1804** Replace the value at PATH with VALUE. If PATH does not already exist,
drh3ad93bb2015-08-29 19:41:45 +00001805** this routine is a no-op. If JSON or PATH is malformed, throw an error.
drhd0960592015-08-17 21:22:32 +00001806*/
1807static void jsonReplaceFunc(
drhbc8f0922015-08-22 19:39:04 +00001808 sqlite3_context *ctx,
drhd0960592015-08-17 21:22:32 +00001809 int argc,
1810 sqlite3_value **argv
1811){
1812 JsonParse x; /* The parse */
1813 JsonNode *pNode;
1814 const char *zPath;
1815 u32 i;
1816
1817 if( argc<1 ) return;
1818 if( (argc&1)==0 ) {
drhbc8f0922015-08-22 19:39:04 +00001819 jsonWrongNumArgs(ctx, "replace");
drhd0960592015-08-17 21:22:32 +00001820 return;
1821 }
drhbc8f0922015-08-22 19:39:04 +00001822 if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
drha8f39a92015-09-21 22:53:16 +00001823 assert( x.nNode );
1824 for(i=1; i<(u32)argc; i+=2){
1825 zPath = (const char*)sqlite3_value_text(argv[i]);
1826 pNode = jsonLookup(&x, zPath, 0, ctx);
1827 if( x.nErr ) goto replace_err;
1828 if( pNode ){
drh285f2ef2021-10-15 16:15:04 +00001829 assert( pNode->eU==0 || pNode->eU==1 || pNode->eU==4 );
drh9dbf96b2022-01-06 01:40:09 +00001830 testcase( pNode->eU!=0 && pNode->eU!=1 );
drha8f39a92015-09-21 22:53:16 +00001831 pNode->jnFlags |= (u8)JNODE_REPLACE;
drh285f2ef2021-10-15 16:15:04 +00001832 VVA( pNode->eU = 4 );
drh633647a2017-03-22 21:24:31 +00001833 pNode->u.iReplace = i + 1;
drhd0960592015-08-17 21:22:32 +00001834 }
drha8f39a92015-09-21 22:53:16 +00001835 }
1836 if( x.aNode[0].jnFlags & JNODE_REPLACE ){
drh285f2ef2021-10-15 16:15:04 +00001837 assert( x.aNode[0].eU==4 );
drh633647a2017-03-22 21:24:31 +00001838 sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
drha8f39a92015-09-21 22:53:16 +00001839 }else{
1840 jsonReturnJson(x.aNode, ctx, argv);
drh301eecc2015-08-17 20:14:19 +00001841 }
drha7714022015-08-29 00:54:49 +00001842replace_err:
drh505ad2c2015-08-21 17:33:11 +00001843 jsonParseReset(&x);
drh301eecc2015-08-17 20:14:19 +00001844}
drh505ad2c2015-08-21 17:33:11 +00001845
drhdc60c682022-01-08 15:05:53 +00001846
drh52216ad2015-08-18 02:28:03 +00001847/*
1848** json_set(JSON, PATH, VALUE, ...)
1849**
1850** Set the value at PATH to VALUE. Create the PATH if it does not already
1851** exist. Overwrite existing values that do exist.
drh3ad93bb2015-08-29 19:41:45 +00001852** If JSON or PATH is malformed, throw an error.
drh52216ad2015-08-18 02:28:03 +00001853**
1854** json_insert(JSON, PATH, VALUE, ...)
1855**
1856** Create PATH and initialize it to VALUE. If PATH already exists, this
drh3ad93bb2015-08-29 19:41:45 +00001857** routine is a no-op. If JSON or PATH is malformed, throw an error.
drh52216ad2015-08-18 02:28:03 +00001858*/
1859static void jsonSetFunc(
drhbc8f0922015-08-22 19:39:04 +00001860 sqlite3_context *ctx,
drh52216ad2015-08-18 02:28:03 +00001861 int argc,
1862 sqlite3_value **argv
1863){
1864 JsonParse x; /* The parse */
1865 JsonNode *pNode;
1866 const char *zPath;
1867 u32 i;
1868 int bApnd;
drh9dbf96b2022-01-06 01:40:09 +00001869 int bIsSet = sqlite3_user_data(ctx)!=0;
drh52216ad2015-08-18 02:28:03 +00001870
1871 if( argc<1 ) return;
1872 if( (argc&1)==0 ) {
drhbc8f0922015-08-22 19:39:04 +00001873 jsonWrongNumArgs(ctx, bIsSet ? "set" : "insert");
drh52216ad2015-08-18 02:28:03 +00001874 return;
1875 }
drhbc8f0922015-08-22 19:39:04 +00001876 if( jsonParse(&x, ctx, (const char*)sqlite3_value_text(argv[0])) ) return;
drha8f39a92015-09-21 22:53:16 +00001877 assert( x.nNode );
1878 for(i=1; i<(u32)argc; i+=2){
1879 zPath = (const char*)sqlite3_value_text(argv[i]);
1880 bApnd = 0;
1881 pNode = jsonLookup(&x, zPath, &bApnd, ctx);
1882 if( x.oom ){
1883 sqlite3_result_error_nomem(ctx);
1884 goto jsonSetDone;
1885 }else if( x.nErr ){
1886 goto jsonSetDone;
1887 }else if( pNode && (bApnd || bIsSet) ){
drh14818362022-01-17 15:23:57 +00001888 testcase( pNode->eU!=0 && pNode->eU!=1 );
1889 assert( pNode->eU!=3 && pNode->eU!=5 );
drh285f2ef2021-10-15 16:15:04 +00001890 VVA( pNode->eU = 4 );
drha8f39a92015-09-21 22:53:16 +00001891 pNode->jnFlags |= (u8)JNODE_REPLACE;
drh633647a2017-03-22 21:24:31 +00001892 pNode->u.iReplace = i + 1;
drh52216ad2015-08-18 02:28:03 +00001893 }
drha8f39a92015-09-21 22:53:16 +00001894 }
1895 if( x.aNode[0].jnFlags & JNODE_REPLACE ){
drh285f2ef2021-10-15 16:15:04 +00001896 assert( x.aNode[0].eU==4 );
drh633647a2017-03-22 21:24:31 +00001897 sqlite3_result_value(ctx, argv[x.aNode[0].u.iReplace]);
drha8f39a92015-09-21 22:53:16 +00001898 }else{
1899 jsonReturnJson(x.aNode, ctx, argv);
drh52216ad2015-08-18 02:28:03 +00001900 }
drhbc8f0922015-08-22 19:39:04 +00001901jsonSetDone:
drh505ad2c2015-08-21 17:33:11 +00001902 jsonParseReset(&x);
drh52216ad2015-08-18 02:28:03 +00001903}
drh301eecc2015-08-17 20:14:19 +00001904
1905/*
drh987eb1f2015-08-17 15:17:37 +00001906** json_type(JSON)
1907** json_type(JSON, PATH)
1908**
drha4e4e182022-01-07 16:03:00 +00001909** Return the top-level "type" of a JSON string. json_type() raises an
drha6c596b2022-01-11 22:06:25 +00001910** error if either the JSON or PATH inputs are not well-formed.
drh987eb1f2015-08-17 15:17:37 +00001911*/
1912static void jsonTypeFunc(
drhbc8f0922015-08-22 19:39:04 +00001913 sqlite3_context *ctx,
drh987eb1f2015-08-17 15:17:37 +00001914 int argc,
1915 sqlite3_value **argv
1916){
drhe35fc302018-08-30 01:52:10 +00001917 JsonParse *p; /* The parse */
drh987eb1f2015-08-17 15:17:37 +00001918 const char *zPath;
drha8f39a92015-09-21 22:53:16 +00001919 JsonNode *pNode;
drh987eb1f2015-08-17 15:17:37 +00001920
drha6c596b2022-01-11 22:06:25 +00001921 p = jsonParseCached(ctx, argv, ctx);
drhe35fc302018-08-30 01:52:10 +00001922 if( p==0 ) return;
drha8f39a92015-09-21 22:53:16 +00001923 if( argc==2 ){
1924 zPath = (const char*)sqlite3_value_text(argv[1]);
drhe35fc302018-08-30 01:52:10 +00001925 pNode = jsonLookup(p, zPath, 0, ctx);
drha8f39a92015-09-21 22:53:16 +00001926 }else{
drhe35fc302018-08-30 01:52:10 +00001927 pNode = p->aNode;
drha8f39a92015-09-21 22:53:16 +00001928 }
1929 if( pNode ){
1930 sqlite3_result_text(ctx, jsonType[pNode->eType], -1, SQLITE_STATIC);
drh987eb1f2015-08-17 15:17:37 +00001931 }
drh987eb1f2015-08-17 15:17:37 +00001932}
drh5634cc02015-08-17 11:28:03 +00001933
drhbc8f0922015-08-22 19:39:04 +00001934/*
1935** json_valid(JSON)
1936**
drh3ad93bb2015-08-29 19:41:45 +00001937** Return 1 if JSON is a well-formed JSON string according to RFC-7159.
1938** Return 0 otherwise.
drhbc8f0922015-08-22 19:39:04 +00001939*/
1940static void jsonValidFunc(
1941 sqlite3_context *ctx,
1942 int argc,
1943 sqlite3_value **argv
1944){
drhe35fc302018-08-30 01:52:10 +00001945 JsonParse *p; /* The parse */
drh9dbf96b2022-01-06 01:40:09 +00001946 UNUSED_PARAMETER(argc);
drhe35fc302018-08-30 01:52:10 +00001947 p = jsonParseCached(ctx, argv, 0);
1948 sqlite3_result_int(ctx, p!=0);
drhbc8f0922015-08-22 19:39:04 +00001949}
1950
drhff135ae2015-12-30 01:07:02 +00001951
1952/****************************************************************************
1953** Aggregate SQL function implementations
1954****************************************************************************/
1955/*
1956** json_group_array(VALUE)
1957**
1958** Return a JSON array composed of all values in the aggregate.
1959*/
1960static void jsonArrayStep(
1961 sqlite3_context *ctx,
1962 int argc,
1963 sqlite3_value **argv
1964){
1965 JsonString *pStr;
drh9dbf96b2022-01-06 01:40:09 +00001966 UNUSED_PARAMETER(argc);
drhff135ae2015-12-30 01:07:02 +00001967 pStr = (JsonString*)sqlite3_aggregate_context(ctx, sizeof(*pStr));
1968 if( pStr ){
1969 if( pStr->zBuf==0 ){
1970 jsonInit(pStr, ctx);
1971 jsonAppendChar(pStr, '[');
drhfab5b072019-09-14 00:21:34 +00001972 }else if( pStr->nUsed>1 ){
drhff135ae2015-12-30 01:07:02 +00001973 jsonAppendChar(pStr, ',');
drhff135ae2015-12-30 01:07:02 +00001974 }
dan8505d732021-04-14 12:11:39 +00001975 pStr->pCtx = ctx;
drhff135ae2015-12-30 01:07:02 +00001976 jsonAppendValue(pStr, argv[0]);
1977 }
1978}
drh8be47a72018-07-05 20:05:29 +00001979static void jsonArrayCompute(sqlite3_context *ctx, int isFinal){
drhff135ae2015-12-30 01:07:02 +00001980 JsonString *pStr;
1981 pStr = (JsonString*)sqlite3_aggregate_context(ctx, 0);
1982 if( pStr ){
1983 pStr->pCtx = ctx;
1984 jsonAppendChar(pStr, ']');
1985 if( pStr->bErr ){
drh4a642b62016-02-05 01:55:27 +00001986 if( pStr->bErr==1 ) sqlite3_result_error_nomem(ctx);
drh23079262016-01-01 00:15:59 +00001987 assert( pStr->bStatic );
drh8be47a72018-07-05 20:05:29 +00001988 }else if( isFinal ){
mistachkined008ec2018-09-12 01:05:26 +00001989 sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed,
drhff135ae2015-12-30 01:07:02 +00001990 pStr->bStatic ? SQLITE_TRANSIENT : sqlite3_free);
1991 pStr->bStatic = 1;
drh8be47a72018-07-05 20:05:29 +00001992 }else{
mistachkined008ec2018-09-12 01:05:26 +00001993 sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed, SQLITE_TRANSIENT);
drh8be47a72018-07-05 20:05:29 +00001994 pStr->nUsed--;
drhff135ae2015-12-30 01:07:02 +00001995 }
1996 }else{
1997 sqlite3_result_text(ctx, "[]", 2, SQLITE_STATIC);
1998 }
1999 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
2000}
drh8be47a72018-07-05 20:05:29 +00002001static void jsonArrayValue(sqlite3_context *ctx){
2002 jsonArrayCompute(ctx, 0);
2003}
2004static void jsonArrayFinal(sqlite3_context *ctx){
2005 jsonArrayCompute(ctx, 1);
2006}
2007
2008#ifndef SQLITE_OMIT_WINDOWFUNC
2009/*
2010** This method works for both json_group_array() and json_group_object().
2011** It works by removing the first element of the group by searching forward
2012** to the first comma (",") that is not within a string and deleting all
2013** text through that comma.
2014*/
2015static void jsonGroupInverse(
2016 sqlite3_context *ctx,
2017 int argc,
2018 sqlite3_value **argv
2019){
drhe39f3882019-09-21 17:31:03 +00002020 unsigned int i;
drh8be47a72018-07-05 20:05:29 +00002021 int inStr = 0;
drhfab5b072019-09-14 00:21:34 +00002022 int nNest = 0;
drh8be47a72018-07-05 20:05:29 +00002023 char *z;
drhfab5b072019-09-14 00:21:34 +00002024 char c;
drh8be47a72018-07-05 20:05:29 +00002025 JsonString *pStr;
drh9dbf96b2022-01-06 01:40:09 +00002026 UNUSED_PARAMETER(argc);
2027 UNUSED_PARAMETER(argv);
drh8be47a72018-07-05 20:05:29 +00002028 pStr = (JsonString*)sqlite3_aggregate_context(ctx, 0);
drh491d4c82018-07-07 20:23:46 +00002029#ifdef NEVER
drhfd4b7282018-07-07 19:47:21 +00002030 /* pStr is always non-NULL since jsonArrayStep() or jsonObjectStep() will
2031 ** always have been called to initalize it */
2032 if( NEVER(!pStr) ) return;
drh491d4c82018-07-07 20:23:46 +00002033#endif
drh8be47a72018-07-05 20:05:29 +00002034 z = pStr->zBuf;
drh0e5cd342021-04-13 01:12:32 +00002035 for(i=1; i<pStr->nUsed && ((c = z[i])!=',' || inStr || nNest); i++){
drhfab5b072019-09-14 00:21:34 +00002036 if( c=='"' ){
drh8be47a72018-07-05 20:05:29 +00002037 inStr = !inStr;
drhfab5b072019-09-14 00:21:34 +00002038 }else if( c=='\\' ){
drh8be47a72018-07-05 20:05:29 +00002039 i++;
drhfab5b072019-09-14 00:21:34 +00002040 }else if( !inStr ){
2041 if( c=='{' || c=='[' ) nNest++;
2042 if( c=='}' || c==']' ) nNest--;
drh8be47a72018-07-05 20:05:29 +00002043 }
2044 }
drh0e5cd342021-04-13 01:12:32 +00002045 if( i<pStr->nUsed ){
2046 pStr->nUsed -= i;
2047 memmove(&z[1], &z[i+1], (size_t)pStr->nUsed-1);
2048 z[pStr->nUsed] = 0;
2049 }else{
2050 pStr->nUsed = 1;
2051 }
drh8be47a72018-07-05 20:05:29 +00002052}
2053#else
2054# define jsonGroupInverse 0
2055#endif
2056
drhff135ae2015-12-30 01:07:02 +00002057
2058/*
2059** json_group_obj(NAME,VALUE)
2060**
2061** Return a JSON object composed of all names and values in the aggregate.
2062*/
2063static void jsonObjectStep(
2064 sqlite3_context *ctx,
2065 int argc,
2066 sqlite3_value **argv
2067){
2068 JsonString *pStr;
2069 const char *z;
2070 u32 n;
drh9dbf96b2022-01-06 01:40:09 +00002071 UNUSED_PARAMETER(argc);
drhff135ae2015-12-30 01:07:02 +00002072 pStr = (JsonString*)sqlite3_aggregate_context(ctx, sizeof(*pStr));
2073 if( pStr ){
2074 if( pStr->zBuf==0 ){
2075 jsonInit(pStr, ctx);
2076 jsonAppendChar(pStr, '{');
drhfab5b072019-09-14 00:21:34 +00002077 }else if( pStr->nUsed>1 ){
drhff135ae2015-12-30 01:07:02 +00002078 jsonAppendChar(pStr, ',');
drhff135ae2015-12-30 01:07:02 +00002079 }
drhd2f55772021-05-28 12:15:19 +00002080 pStr->pCtx = ctx;
drhff135ae2015-12-30 01:07:02 +00002081 z = (const char*)sqlite3_value_text(argv[0]);
2082 n = (u32)sqlite3_value_bytes(argv[0]);
2083 jsonAppendString(pStr, z, n);
2084 jsonAppendChar(pStr, ':');
2085 jsonAppendValue(pStr, argv[1]);
2086 }
2087}
drh8be47a72018-07-05 20:05:29 +00002088static void jsonObjectCompute(sqlite3_context *ctx, int isFinal){
drhff135ae2015-12-30 01:07:02 +00002089 JsonString *pStr;
2090 pStr = (JsonString*)sqlite3_aggregate_context(ctx, 0);
2091 if( pStr ){
2092 jsonAppendChar(pStr, '}');
2093 if( pStr->bErr ){
drh6850a632016-11-07 18:18:08 +00002094 if( pStr->bErr==1 ) sqlite3_result_error_nomem(ctx);
drh23079262016-01-01 00:15:59 +00002095 assert( pStr->bStatic );
drh8be47a72018-07-05 20:05:29 +00002096 }else if( isFinal ){
mistachkined008ec2018-09-12 01:05:26 +00002097 sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed,
drhff135ae2015-12-30 01:07:02 +00002098 pStr->bStatic ? SQLITE_TRANSIENT : sqlite3_free);
2099 pStr->bStatic = 1;
drh8be47a72018-07-05 20:05:29 +00002100 }else{
mistachkined008ec2018-09-12 01:05:26 +00002101 sqlite3_result_text(ctx, pStr->zBuf, (int)pStr->nUsed, SQLITE_TRANSIENT);
drh8be47a72018-07-05 20:05:29 +00002102 pStr->nUsed--;
drhff135ae2015-12-30 01:07:02 +00002103 }
2104 }else{
2105 sqlite3_result_text(ctx, "{}", 2, SQLITE_STATIC);
2106 }
2107 sqlite3_result_subtype(ctx, JSON_SUBTYPE);
2108}
drh8be47a72018-07-05 20:05:29 +00002109static void jsonObjectValue(sqlite3_context *ctx){
2110 jsonObjectCompute(ctx, 0);
2111}
2112static void jsonObjectFinal(sqlite3_context *ctx){
2113 jsonObjectCompute(ctx, 1);
2114}
2115
drhff135ae2015-12-30 01:07:02 +00002116
2117
drhd2975922015-08-29 17:22:33 +00002118#ifndef SQLITE_OMIT_VIRTUALTABLE
drhcb6c6c62015-08-19 22:47:17 +00002119/****************************************************************************
2120** The json_each virtual table
2121****************************************************************************/
2122typedef struct JsonEachCursor JsonEachCursor;
2123struct JsonEachCursor {
2124 sqlite3_vtab_cursor base; /* Base class - must be first */
drh505ad2c2015-08-21 17:33:11 +00002125 u32 iRowid; /* The rowid */
drh852944e2015-09-10 03:29:11 +00002126 u32 iBegin; /* The first node of the scan */
drh505ad2c2015-08-21 17:33:11 +00002127 u32 i; /* Index in sParse.aNode[] of current row */
2128 u32 iEnd; /* EOF when i equals or exceeds this value */
2129 u8 eType; /* Type of top-level element */
2130 u8 bRecursive; /* True for json_tree(). False for json_each() */
2131 char *zJson; /* Input JSON */
drh383de692015-09-10 17:20:57 +00002132 char *zRoot; /* Path by which to filter zJson */
drh505ad2c2015-08-21 17:33:11 +00002133 JsonParse sParse; /* Parse of the input JSON */
drhcb6c6c62015-08-19 22:47:17 +00002134};
2135
2136/* Constructor for the json_each virtual table */
2137static int jsonEachConnect(
2138 sqlite3 *db,
2139 void *pAux,
2140 int argc, const char *const*argv,
2141 sqlite3_vtab **ppVtab,
2142 char **pzErr
2143){
2144 sqlite3_vtab *pNew;
drh505ad2c2015-08-21 17:33:11 +00002145 int rc;
drhcb6c6c62015-08-19 22:47:17 +00002146
2147/* Column numbers */
drh4af352d2015-08-21 20:02:48 +00002148#define JEACH_KEY 0
2149#define JEACH_VALUE 1
2150#define JEACH_TYPE 2
2151#define JEACH_ATOM 3
2152#define JEACH_ID 4
2153#define JEACH_PARENT 5
2154#define JEACH_FULLKEY 6
drh383de692015-09-10 17:20:57 +00002155#define JEACH_PATH 7
drh43579192018-11-16 16:04:50 +00002156/* The xBestIndex method assumes that the JSON and ROOT columns are
2157** the last two columns in the table. Should this ever changes, be
2158** sure to update the xBestIndex method. */
drh383de692015-09-10 17:20:57 +00002159#define JEACH_JSON 8
2160#define JEACH_ROOT 9
drhcb6c6c62015-08-19 22:47:17 +00002161
drh9dbf96b2022-01-06 01:40:09 +00002162 UNUSED_PARAMETER(pzErr);
2163 UNUSED_PARAMETER(argv);
2164 UNUSED_PARAMETER(argc);
2165 UNUSED_PARAMETER(pAux);
drh505ad2c2015-08-21 17:33:11 +00002166 rc = sqlite3_declare_vtab(db,
drh383de692015-09-10 17:20:57 +00002167 "CREATE TABLE x(key,value,type,atom,id,parent,fullkey,path,"
2168 "json HIDDEN,root HIDDEN)");
drh505ad2c2015-08-21 17:33:11 +00002169 if( rc==SQLITE_OK ){
2170 pNew = *ppVtab = sqlite3_malloc( sizeof(*pNew) );
2171 if( pNew==0 ) return SQLITE_NOMEM;
2172 memset(pNew, 0, sizeof(*pNew));
drh2b1c2aa2020-01-07 19:45:40 +00002173 sqlite3_vtab_config(db, SQLITE_VTAB_INNOCUOUS);
drh505ad2c2015-08-21 17:33:11 +00002174 }
2175 return rc;
drhcb6c6c62015-08-19 22:47:17 +00002176}
2177
2178/* destructor for json_each virtual table */
2179static int jsonEachDisconnect(sqlite3_vtab *pVtab){
2180 sqlite3_free(pVtab);
2181 return SQLITE_OK;
2182}
2183
drh505ad2c2015-08-21 17:33:11 +00002184/* constructor for a JsonEachCursor object for json_each(). */
2185static int jsonEachOpenEach(sqlite3_vtab *p, sqlite3_vtab_cursor **ppCursor){
drhcb6c6c62015-08-19 22:47:17 +00002186 JsonEachCursor *pCur;
drh6fd5c1e2015-08-21 20:37:12 +00002187
drh9dbf96b2022-01-06 01:40:09 +00002188 UNUSED_PARAMETER(p);
drhcb6c6c62015-08-19 22:47:17 +00002189 pCur = sqlite3_malloc( sizeof(*pCur) );
2190 if( pCur==0 ) return SQLITE_NOMEM;
2191 memset(pCur, 0, sizeof(*pCur));
2192 *ppCursor = &pCur->base;
2193 return SQLITE_OK;
2194}
2195
drh505ad2c2015-08-21 17:33:11 +00002196/* constructor for a JsonEachCursor object for json_tree(). */
2197static int jsonEachOpenTree(sqlite3_vtab *p, sqlite3_vtab_cursor **ppCursor){
2198 int rc = jsonEachOpenEach(p, ppCursor);
2199 if( rc==SQLITE_OK ){
2200 JsonEachCursor *pCur = (JsonEachCursor*)*ppCursor;
2201 pCur->bRecursive = 1;
2202 }
2203 return rc;
2204}
2205
drhcb6c6c62015-08-19 22:47:17 +00002206/* Reset a JsonEachCursor back to its original state. Free any memory
2207** held. */
2208static void jsonEachCursorReset(JsonEachCursor *p){
2209 sqlite3_free(p->zJson);
drh383de692015-09-10 17:20:57 +00002210 sqlite3_free(p->zRoot);
drh505ad2c2015-08-21 17:33:11 +00002211 jsonParseReset(&p->sParse);
drhcb6c6c62015-08-19 22:47:17 +00002212 p->iRowid = 0;
2213 p->i = 0;
2214 p->iEnd = 0;
2215 p->eType = 0;
drhcb6c6c62015-08-19 22:47:17 +00002216 p->zJson = 0;
drh383de692015-09-10 17:20:57 +00002217 p->zRoot = 0;
drhcb6c6c62015-08-19 22:47:17 +00002218}
2219
2220/* Destructor for a jsonEachCursor object */
2221static int jsonEachClose(sqlite3_vtab_cursor *cur){
2222 JsonEachCursor *p = (JsonEachCursor*)cur;
2223 jsonEachCursorReset(p);
2224 sqlite3_free(cur);
2225 return SQLITE_OK;
2226}
2227
2228/* Return TRUE if the jsonEachCursor object has been advanced off the end
2229** of the JSON object */
2230static int jsonEachEof(sqlite3_vtab_cursor *cur){
2231 JsonEachCursor *p = (JsonEachCursor*)cur;
2232 return p->i >= p->iEnd;
2233}
2234
drh505ad2c2015-08-21 17:33:11 +00002235/* Advance the cursor to the next element for json_tree() */
drh4af352d2015-08-21 20:02:48 +00002236static int jsonEachNext(sqlite3_vtab_cursor *cur){
drh505ad2c2015-08-21 17:33:11 +00002237 JsonEachCursor *p = (JsonEachCursor*)cur;
drh4af352d2015-08-21 20:02:48 +00002238 if( p->bRecursive ){
drh852944e2015-09-10 03:29:11 +00002239 if( p->sParse.aNode[p->i].jnFlags & JNODE_LABEL ) p->i++;
2240 p->i++;
drh4af352d2015-08-21 20:02:48 +00002241 p->iRowid++;
drh852944e2015-09-10 03:29:11 +00002242 if( p->i<p->iEnd ){
drh8784eca2015-08-23 02:42:30 +00002243 u32 iUp = p->sParse.aUp[p->i];
2244 JsonNode *pUp = &p->sParse.aNode[iUp];
drh4af352d2015-08-21 20:02:48 +00002245 p->eType = pUp->eType;
drh8784eca2015-08-23 02:42:30 +00002246 if( pUp->eType==JSON_ARRAY ){
drh285f2ef2021-10-15 16:15:04 +00002247 assert( pUp->eU==0 || pUp->eU==3 );
drh9dbf96b2022-01-06 01:40:09 +00002248 testcase( pUp->eU==3 );
drh285f2ef2021-10-15 16:15:04 +00002249 VVA( pUp->eU = 3 );
drh8784eca2015-08-23 02:42:30 +00002250 if( iUp==p->i-1 ){
2251 pUp->u.iKey = 0;
2252 }else{
2253 pUp->u.iKey++;
2254 }
drh4af352d2015-08-21 20:02:48 +00002255 }
2256 }
drh505ad2c2015-08-21 17:33:11 +00002257 }else{
drh4af352d2015-08-21 20:02:48 +00002258 switch( p->eType ){
2259 case JSON_ARRAY: {
2260 p->i += jsonNodeSize(&p->sParse.aNode[p->i]);
2261 p->iRowid++;
2262 break;
2263 }
2264 case JSON_OBJECT: {
2265 p->i += 1 + jsonNodeSize(&p->sParse.aNode[p->i+1]);
2266 p->iRowid++;
2267 break;
2268 }
2269 default: {
2270 p->i = p->iEnd;
2271 break;
2272 }
drh505ad2c2015-08-21 17:33:11 +00002273 }
2274 }
2275 return SQLITE_OK;
2276}
2277
drh0de10ac2022-04-04 15:15:45 +00002278/* Append an object label to the JSON Path being constructed
2279** in pStr.
2280*/
2281static void jsonAppendObjectPathElement(
2282 JsonString *pStr,
2283 JsonNode *pNode
2284){
2285 int jj, nn;
2286 const char *z;
2287 assert( pNode->eType==JSON_STRING );
2288 assert( pNode->jnFlags & JNODE_LABEL );
2289 assert( pNode->eU==1 );
2290 z = pNode->u.zJContent;
2291 nn = pNode->n;
2292 assert( nn>=2 );
2293 assert( z[0]=='"' );
2294 assert( z[nn-1]=='"' );
2295 if( nn>2 && sqlite3Isalpha(z[1]) ){
2296 for(jj=2; jj<nn-1 && sqlite3Isalnum(z[jj]); jj++){}
2297 if( jj==nn-1 ){
2298 z++;
2299 nn -= 2;
2300 }
2301 }
2302 jsonPrintf(nn+2, pStr, ".%.*s", nn, z);
2303}
2304
drh4af352d2015-08-21 20:02:48 +00002305/* Append the name of the path for element i to pStr
2306*/
2307static void jsonEachComputePath(
2308 JsonEachCursor *p, /* The cursor */
2309 JsonString *pStr, /* Write the path here */
2310 u32 i /* Path to this element */
2311){
2312 JsonNode *pNode, *pUp;
2313 u32 iUp;
2314 if( i==0 ){
2315 jsonAppendChar(pStr, '$');
2316 return;
drhcb6c6c62015-08-19 22:47:17 +00002317 }
drh4af352d2015-08-21 20:02:48 +00002318 iUp = p->sParse.aUp[i];
2319 jsonEachComputePath(p, pStr, iUp);
2320 pNode = &p->sParse.aNode[i];
2321 pUp = &p->sParse.aNode[iUp];
2322 if( pUp->eType==JSON_ARRAY ){
drh285f2ef2021-10-15 16:15:04 +00002323 assert( pUp->eU==3 || (pUp->eU==0 && pUp->u.iKey==0) );
2324 testcase( pUp->eU==0 );
drh4af352d2015-08-21 20:02:48 +00002325 jsonPrintf(30, pStr, "[%d]", pUp->u.iKey);
2326 }else{
2327 assert( pUp->eType==JSON_OBJECT );
drh852944e2015-09-10 03:29:11 +00002328 if( (pNode->jnFlags & JNODE_LABEL)==0 ) pNode--;
drh0de10ac2022-04-04 15:15:45 +00002329 jsonAppendObjectPathElement(pStr, pNode);
drh4af352d2015-08-21 20:02:48 +00002330 }
drhcb6c6c62015-08-19 22:47:17 +00002331}
2332
2333/* Return the value of a column */
2334static int jsonEachColumn(
2335 sqlite3_vtab_cursor *cur, /* The cursor */
2336 sqlite3_context *ctx, /* First argument to sqlite3_result_...() */
2337 int i /* Which column to return */
2338){
2339 JsonEachCursor *p = (JsonEachCursor*)cur;
drh505ad2c2015-08-21 17:33:11 +00002340 JsonNode *pThis = &p->sParse.aNode[p->i];
drhcb6c6c62015-08-19 22:47:17 +00002341 switch( i ){
2342 case JEACH_KEY: {
drh8784eca2015-08-23 02:42:30 +00002343 if( p->i==0 ) break;
drhcb6c6c62015-08-19 22:47:17 +00002344 if( p->eType==JSON_OBJECT ){
drh505ad2c2015-08-21 17:33:11 +00002345 jsonReturn(pThis, ctx, 0);
2346 }else if( p->eType==JSON_ARRAY ){
2347 u32 iKey;
2348 if( p->bRecursive ){
2349 if( p->iRowid==0 ) break;
drh285f2ef2021-10-15 16:15:04 +00002350 assert( p->sParse.aNode[p->sParse.aUp[p->i]].eU==3 );
drh8784eca2015-08-23 02:42:30 +00002351 iKey = p->sParse.aNode[p->sParse.aUp[p->i]].u.iKey;
drh505ad2c2015-08-21 17:33:11 +00002352 }else{
2353 iKey = p->iRowid;
2354 }
drh6fd5c1e2015-08-21 20:37:12 +00002355 sqlite3_result_int64(ctx, (sqlite3_int64)iKey);
drhcb6c6c62015-08-19 22:47:17 +00002356 }
2357 break;
2358 }
2359 case JEACH_VALUE: {
drh852944e2015-09-10 03:29:11 +00002360 if( pThis->jnFlags & JNODE_LABEL ) pThis++;
drh505ad2c2015-08-21 17:33:11 +00002361 jsonReturn(pThis, ctx, 0);
2362 break;
2363 }
2364 case JEACH_TYPE: {
drh852944e2015-09-10 03:29:11 +00002365 if( pThis->jnFlags & JNODE_LABEL ) pThis++;
drh505ad2c2015-08-21 17:33:11 +00002366 sqlite3_result_text(ctx, jsonType[pThis->eType], -1, SQLITE_STATIC);
2367 break;
2368 }
2369 case JEACH_ATOM: {
drh852944e2015-09-10 03:29:11 +00002370 if( pThis->jnFlags & JNODE_LABEL ) pThis++;
drh505ad2c2015-08-21 17:33:11 +00002371 if( pThis->eType>=JSON_ARRAY ) break;
2372 jsonReturn(pThis, ctx, 0);
2373 break;
2374 }
2375 case JEACH_ID: {
drh852944e2015-09-10 03:29:11 +00002376 sqlite3_result_int64(ctx,
2377 (sqlite3_int64)p->i + ((pThis->jnFlags & JNODE_LABEL)!=0));
drh505ad2c2015-08-21 17:33:11 +00002378 break;
2379 }
2380 case JEACH_PARENT: {
drh852944e2015-09-10 03:29:11 +00002381 if( p->i>p->iBegin && p->bRecursive ){
drh6fd5c1e2015-08-21 20:37:12 +00002382 sqlite3_result_int64(ctx, (sqlite3_int64)p->sParse.aUp[p->i]);
drhcb6c6c62015-08-19 22:47:17 +00002383 }
2384 break;
2385 }
drh4af352d2015-08-21 20:02:48 +00002386 case JEACH_FULLKEY: {
2387 JsonString x;
2388 jsonInit(&x, ctx);
2389 if( p->bRecursive ){
2390 jsonEachComputePath(p, &x, p->i);
2391 }else{
drh383de692015-09-10 17:20:57 +00002392 if( p->zRoot ){
2393 jsonAppendRaw(&x, p->zRoot, (int)strlen(p->zRoot));
drh4af352d2015-08-21 20:02:48 +00002394 }else{
2395 jsonAppendChar(&x, '$');
2396 }
2397 if( p->eType==JSON_ARRAY ){
2398 jsonPrintf(30, &x, "[%d]", p->iRowid);
drhdd7460f2018-05-16 12:19:11 +00002399 }else if( p->eType==JSON_OBJECT ){
drh0de10ac2022-04-04 15:15:45 +00002400 jsonAppendObjectPathElement(&x, pThis);
drh4af352d2015-08-21 20:02:48 +00002401 }
2402 }
2403 jsonResult(&x);
2404 break;
2405 }
drhcb6c6c62015-08-19 22:47:17 +00002406 case JEACH_PATH: {
drh383de692015-09-10 17:20:57 +00002407 if( p->bRecursive ){
2408 JsonString x;
2409 jsonInit(&x, ctx);
2410 jsonEachComputePath(p, &x, p->sParse.aUp[p->i]);
2411 jsonResult(&x);
2412 break;
drh4af352d2015-08-21 20:02:48 +00002413 }
drh383de692015-09-10 17:20:57 +00002414 /* For json_each() path and root are the same so fall through
2415 ** into the root case */
drh08b92082020-08-10 14:18:00 +00002416 /* no break */ deliberate_fall_through
drh383de692015-09-10 17:20:57 +00002417 }
drh6850a632016-11-07 18:18:08 +00002418 default: {
drh383de692015-09-10 17:20:57 +00002419 const char *zRoot = p->zRoot;
drh6850a632016-11-07 18:18:08 +00002420 if( zRoot==0 ) zRoot = "$";
drh383de692015-09-10 17:20:57 +00002421 sqlite3_result_text(ctx, zRoot, -1, SQLITE_STATIC);
drhcb6c6c62015-08-19 22:47:17 +00002422 break;
2423 }
drh3d1d2a92015-09-22 01:15:49 +00002424 case JEACH_JSON: {
drh505ad2c2015-08-21 17:33:11 +00002425 assert( i==JEACH_JSON );
drhcb6c6c62015-08-19 22:47:17 +00002426 sqlite3_result_text(ctx, p->sParse.zJson, -1, SQLITE_STATIC);
2427 break;
2428 }
2429 }
2430 return SQLITE_OK;
2431}
2432
2433/* Return the current rowid value */
2434static int jsonEachRowid(sqlite3_vtab_cursor *cur, sqlite_int64 *pRowid){
2435 JsonEachCursor *p = (JsonEachCursor*)cur;
2436 *pRowid = p->iRowid;
2437 return SQLITE_OK;
2438}
2439
2440/* The query strategy is to look for an equality constraint on the json
2441** column. Without such a constraint, the table cannot operate. idxNum is
drh383de692015-09-10 17:20:57 +00002442** 1 if the constraint is found, 3 if the constraint and zRoot are found,
drhcb6c6c62015-08-19 22:47:17 +00002443** and 0 otherwise.
2444*/
2445static int jsonEachBestIndex(
2446 sqlite3_vtab *tab,
2447 sqlite3_index_info *pIdxInfo
2448){
drh43579192018-11-16 16:04:50 +00002449 int i; /* Loop counter or computed array index */
2450 int aIdx[2]; /* Index of constraints for JSON and ROOT */
2451 int unusableMask = 0; /* Mask of unusable JSON and ROOT constraints */
2452 int idxMask = 0; /* Mask of usable == constraints JSON and ROOT */
drhcb6c6c62015-08-19 22:47:17 +00002453 const struct sqlite3_index_constraint *pConstraint;
drh6fd5c1e2015-08-21 20:37:12 +00002454
drh43579192018-11-16 16:04:50 +00002455 /* This implementation assumes that JSON and ROOT are the last two
2456 ** columns in the table */
2457 assert( JEACH_ROOT == JEACH_JSON+1 );
drh9dbf96b2022-01-06 01:40:09 +00002458 UNUSED_PARAMETER(tab);
drh43579192018-11-16 16:04:50 +00002459 aIdx[0] = aIdx[1] = -1;
drhcb6c6c62015-08-19 22:47:17 +00002460 pConstraint = pIdxInfo->aConstraint;
2461 for(i=0; i<pIdxInfo->nConstraint; i++, pConstraint++){
drh43579192018-11-16 16:04:50 +00002462 int iCol;
2463 int iMask;
2464 if( pConstraint->iColumn < JEACH_JSON ) continue;
2465 iCol = pConstraint->iColumn - JEACH_JSON;
2466 assert( iCol==0 || iCol==1 );
drh285f2ef2021-10-15 16:15:04 +00002467 testcase( iCol==0 );
drh43579192018-11-16 16:04:50 +00002468 iMask = 1 << iCol;
2469 if( pConstraint->usable==0 ){
2470 unusableMask |= iMask;
2471 }else if( pConstraint->op==SQLITE_INDEX_CONSTRAINT_EQ ){
2472 aIdx[iCol] = i;
2473 idxMask |= iMask;
drhcb6c6c62015-08-19 22:47:17 +00002474 }
2475 }
drh43579192018-11-16 16:04:50 +00002476 if( (unusableMask & ~idxMask)!=0 ){
2477 /* If there are any unusable constraints on JSON or ROOT, then reject
2478 ** this entire plan */
2479 return SQLITE_CONSTRAINT;
2480 }
2481 if( aIdx[0]<0 ){
2482 /* No JSON input. Leave estimatedCost at the huge value that it was
2483 ** initialized to to discourage the query planner from selecting this
2484 ** plan. */
drhcb6c6c62015-08-19 22:47:17 +00002485 pIdxInfo->idxNum = 0;
drhcb6c6c62015-08-19 22:47:17 +00002486 }else{
drh505ad2c2015-08-21 17:33:11 +00002487 pIdxInfo->estimatedCost = 1.0;
drh43579192018-11-16 16:04:50 +00002488 i = aIdx[0];
2489 pIdxInfo->aConstraintUsage[i].argvIndex = 1;
2490 pIdxInfo->aConstraintUsage[i].omit = 1;
2491 if( aIdx[1]<0 ){
2492 pIdxInfo->idxNum = 1; /* Only JSON supplied. Plan 1 */
drhcb6c6c62015-08-19 22:47:17 +00002493 }else{
drh43579192018-11-16 16:04:50 +00002494 i = aIdx[1];
2495 pIdxInfo->aConstraintUsage[i].argvIndex = 2;
2496 pIdxInfo->aConstraintUsage[i].omit = 1;
2497 pIdxInfo->idxNum = 3; /* Both JSON and ROOT are supplied. Plan 3 */
drhcb6c6c62015-08-19 22:47:17 +00002498 }
2499 }
2500 return SQLITE_OK;
2501}
2502
2503/* Start a search on a new JSON string */
2504static int jsonEachFilter(
2505 sqlite3_vtab_cursor *cur,
2506 int idxNum, const char *idxStr,
2507 int argc, sqlite3_value **argv
2508){
2509 JsonEachCursor *p = (JsonEachCursor*)cur;
2510 const char *z;
mistachkin16a93122015-09-11 18:05:01 +00002511 const char *zRoot = 0;
drhcb6c6c62015-08-19 22:47:17 +00002512 sqlite3_int64 n;
2513
drh9dbf96b2022-01-06 01:40:09 +00002514 UNUSED_PARAMETER(idxStr);
2515 UNUSED_PARAMETER(argc);
drhcb6c6c62015-08-19 22:47:17 +00002516 jsonEachCursorReset(p);
2517 if( idxNum==0 ) return SQLITE_OK;
2518 z = (const char*)sqlite3_value_text(argv[0]);
2519 if( z==0 ) return SQLITE_OK;
drhcb6c6c62015-08-19 22:47:17 +00002520 n = sqlite3_value_bytes(argv[0]);
drh6fd5c1e2015-08-21 20:37:12 +00002521 p->zJson = sqlite3_malloc64( n+1 );
drhcb6c6c62015-08-19 22:47:17 +00002522 if( p->zJson==0 ) return SQLITE_NOMEM;
drh6fd5c1e2015-08-21 20:37:12 +00002523 memcpy(p->zJson, z, (size_t)n+1);
drha7714022015-08-29 00:54:49 +00002524 if( jsonParse(&p->sParse, 0, p->zJson) ){
2525 int rc = SQLITE_NOMEM;
2526 if( p->sParse.oom==0 ){
2527 sqlite3_free(cur->pVtab->zErrMsg);
2528 cur->pVtab->zErrMsg = sqlite3_mprintf("malformed JSON");
2529 if( cur->pVtab->zErrMsg ) rc = SQLITE_ERROR;
2530 }
drhcb6c6c62015-08-19 22:47:17 +00002531 jsonEachCursorReset(p);
drha7714022015-08-29 00:54:49 +00002532 return rc;
2533 }else if( p->bRecursive && jsonParseFindParents(&p->sParse) ){
2534 jsonEachCursorReset(p);
2535 return SQLITE_NOMEM;
drhcb6c6c62015-08-19 22:47:17 +00002536 }else{
drh95677942015-09-24 01:06:37 +00002537 JsonNode *pNode = 0;
drhcb6c6c62015-08-19 22:47:17 +00002538 if( idxNum==3 ){
drha7714022015-08-29 00:54:49 +00002539 const char *zErr = 0;
drha8f39a92015-09-21 22:53:16 +00002540 zRoot = (const char*)sqlite3_value_text(argv[1]);
2541 if( zRoot==0 ) return SQLITE_OK;
drhcb6c6c62015-08-19 22:47:17 +00002542 n = sqlite3_value_bytes(argv[1]);
drh383de692015-09-10 17:20:57 +00002543 p->zRoot = sqlite3_malloc64( n+1 );
2544 if( p->zRoot==0 ) return SQLITE_NOMEM;
2545 memcpy(p->zRoot, zRoot, (size_t)n+1);
drha8f39a92015-09-21 22:53:16 +00002546 if( zRoot[0]!='$' ){
2547 zErr = zRoot;
2548 }else{
2549 pNode = jsonLookupStep(&p->sParse, 0, p->zRoot+1, 0, &zErr);
2550 }
2551 if( zErr ){
drha7714022015-08-29 00:54:49 +00002552 sqlite3_free(cur->pVtab->zErrMsg);
2553 cur->pVtab->zErrMsg = jsonPathSyntaxError(zErr);
drhcb6c6c62015-08-19 22:47:17 +00002554 jsonEachCursorReset(p);
drha7714022015-08-29 00:54:49 +00002555 return cur->pVtab->zErrMsg ? SQLITE_ERROR : SQLITE_NOMEM;
2556 }else if( pNode==0 ){
drhcb6c6c62015-08-19 22:47:17 +00002557 return SQLITE_OK;
2558 }
2559 }else{
2560 pNode = p->sParse.aNode;
2561 }
drh852944e2015-09-10 03:29:11 +00002562 p->iBegin = p->i = (int)(pNode - p->sParse.aNode);
drhcb6c6c62015-08-19 22:47:17 +00002563 p->eType = pNode->eType;
2564 if( p->eType>=JSON_ARRAY ){
drh285f2ef2021-10-15 16:15:04 +00002565 assert( pNode->eU==0 );
2566 VVA( pNode->eU = 3 );
drh8784eca2015-08-23 02:42:30 +00002567 pNode->u.iKey = 0;
drhc3722b22015-08-23 20:44:59 +00002568 p->iEnd = p->i + pNode->n + 1;
drh852944e2015-09-10 03:29:11 +00002569 if( p->bRecursive ){
drh3d1d2a92015-09-22 01:15:49 +00002570 p->eType = p->sParse.aNode[p->sParse.aUp[p->i]].eType;
drh852944e2015-09-10 03:29:11 +00002571 if( p->i>0 && (p->sParse.aNode[p->i-1].jnFlags & JNODE_LABEL)!=0 ){
2572 p->i--;
2573 }
2574 }else{
2575 p->i++;
2576 }
drhcb6c6c62015-08-19 22:47:17 +00002577 }else{
2578 p->iEnd = p->i+1;
2579 }
2580 }
drha8f39a92015-09-21 22:53:16 +00002581 return SQLITE_OK;
drhcb6c6c62015-08-19 22:47:17 +00002582}
2583
2584/* The methods of the json_each virtual table */
2585static sqlite3_module jsonEachModule = {
2586 0, /* iVersion */
2587 0, /* xCreate */
2588 jsonEachConnect, /* xConnect */
2589 jsonEachBestIndex, /* xBestIndex */
2590 jsonEachDisconnect, /* xDisconnect */
2591 0, /* xDestroy */
drh505ad2c2015-08-21 17:33:11 +00002592 jsonEachOpenEach, /* xOpen - open a cursor */
drhcb6c6c62015-08-19 22:47:17 +00002593 jsonEachClose, /* xClose - close a cursor */
2594 jsonEachFilter, /* xFilter - configure scan constraints */
drh4af352d2015-08-21 20:02:48 +00002595 jsonEachNext, /* xNext - advance a cursor */
drhcb6c6c62015-08-19 22:47:17 +00002596 jsonEachEof, /* xEof - check for end of scan */
2597 jsonEachColumn, /* xColumn - read data */
2598 jsonEachRowid, /* xRowid - read data */
2599 0, /* xUpdate */
2600 0, /* xBegin */
2601 0, /* xSync */
2602 0, /* xCommit */
2603 0, /* xRollback */
2604 0, /* xFindMethod */
2605 0, /* xRename */
drh6fd5c1e2015-08-21 20:37:12 +00002606 0, /* xSavepoint */
2607 0, /* xRelease */
drh84c501b2018-11-05 23:01:45 +00002608 0, /* xRollbackTo */
2609 0 /* xShadowName */
drhcb6c6c62015-08-19 22:47:17 +00002610};
2611
drh505ad2c2015-08-21 17:33:11 +00002612/* The methods of the json_tree virtual table. */
2613static sqlite3_module jsonTreeModule = {
2614 0, /* iVersion */
2615 0, /* xCreate */
2616 jsonEachConnect, /* xConnect */
2617 jsonEachBestIndex, /* xBestIndex */
2618 jsonEachDisconnect, /* xDisconnect */
2619 0, /* xDestroy */
2620 jsonEachOpenTree, /* xOpen - open a cursor */
2621 jsonEachClose, /* xClose - close a cursor */
2622 jsonEachFilter, /* xFilter - configure scan constraints */
drh4af352d2015-08-21 20:02:48 +00002623 jsonEachNext, /* xNext - advance a cursor */
drh505ad2c2015-08-21 17:33:11 +00002624 jsonEachEof, /* xEof - check for end of scan */
2625 jsonEachColumn, /* xColumn - read data */
2626 jsonEachRowid, /* xRowid - read data */
2627 0, /* xUpdate */
2628 0, /* xBegin */
2629 0, /* xSync */
2630 0, /* xCommit */
2631 0, /* xRollback */
2632 0, /* xFindMethod */
2633 0, /* xRename */
drh6fd5c1e2015-08-21 20:37:12 +00002634 0, /* xSavepoint */
2635 0, /* xRelease */
drh84c501b2018-11-05 23:01:45 +00002636 0, /* xRollbackTo */
2637 0 /* xShadowName */
drh505ad2c2015-08-21 17:33:11 +00002638};
drhd2975922015-08-29 17:22:33 +00002639#endif /* SQLITE_OMIT_VIRTUALTABLE */
drh9dbf96b2022-01-06 01:40:09 +00002640#endif /* !defined(SQLITE_OMIT_JSON) */
drh505ad2c2015-08-21 17:33:11 +00002641
drh9dbf96b2022-01-06 01:40:09 +00002642/*
2643** Register JSON functions.
2644*/
2645void sqlite3RegisterJsonFunctions(void){
2646#ifndef SQLITE_OMIT_JSON
2647 static FuncDef aJsonFunc[] = {
drhdaefcd92022-01-08 15:37:13 +00002648 JFUNCTION(json, 1, 0, jsonRemoveFunc),
2649 JFUNCTION(json_array, -1, 0, jsonArrayFunc),
2650 JFUNCTION(json_array_length, 1, 0, jsonArrayLengthFunc),
2651 JFUNCTION(json_array_length, 2, 0, jsonArrayLengthFunc),
2652 JFUNCTION(json_extract, -1, 0, jsonExtractFunc),
drhd83c90b2022-01-10 15:43:13 +00002653 JFUNCTION(->, 2, JSON_JSON, jsonExtractFunc),
2654 JFUNCTION(->>, 2, JSON_SQL, jsonExtractFunc),
drhdaefcd92022-01-08 15:37:13 +00002655 JFUNCTION(json_insert, -1, 0, jsonSetFunc),
drhdaefcd92022-01-08 15:37:13 +00002656 JFUNCTION(json_object, -1, 0, jsonObjectFunc),
2657 JFUNCTION(json_patch, 2, 0, jsonPatchFunc),
2658 JFUNCTION(json_quote, 1, 0, jsonQuoteFunc),
2659 JFUNCTION(json_remove, -1, 0, jsonRemoveFunc),
2660 JFUNCTION(json_replace, -1, 0, jsonReplaceFunc),
2661 JFUNCTION(json_set, -1, JSON_ISSET, jsonSetFunc),
2662 JFUNCTION(json_type, 1, 0, jsonTypeFunc),
2663 JFUNCTION(json_type, 2, 0, jsonTypeFunc),
2664 JFUNCTION(json_valid, 1, 0, jsonValidFunc),
drh301eecc2015-08-17 20:14:19 +00002665#if SQLITE_DEBUG
drhdaefcd92022-01-08 15:37:13 +00002666 JFUNCTION(json_parse, 1, 0, jsonParseFunc),
2667 JFUNCTION(json_test1, 1, 0, jsonTest1Func),
drh301eecc2015-08-17 20:14:19 +00002668#endif
drhdaefcd92022-01-08 15:37:13 +00002669 WAGGREGATE(json_group_array, 1, 0, 0,
drh9dbf96b2022-01-06 01:40:09 +00002670 jsonArrayStep, jsonArrayFinal, jsonArrayValue, jsonGroupInverse,
2671 SQLITE_SUBTYPE|SQLITE_UTF8|SQLITE_DETERMINISTIC|SQLITE_INNOCUOUS),
drhdaefcd92022-01-08 15:37:13 +00002672 WAGGREGATE(json_group_object, 2, 0, 0,
drh9dbf96b2022-01-06 01:40:09 +00002673 jsonObjectStep, jsonObjectFinal, jsonObjectValue, jsonGroupInverse,
2674 SQLITE_SUBTYPE|SQLITE_UTF8|SQLITE_DETERMINISTIC|SQLITE_INNOCUOUS)
drh5fa5c102015-08-12 16:49:40 +00002675 };
drh9dbf96b2022-01-06 01:40:09 +00002676 sqlite3InsertBuiltinFuncs(aJsonFunc, ArraySize(aJsonFunc));
2677#endif
2678}
2679
2680#if !defined(SQLITE_OMIT_VIRTUALTABLE) && !defined(SQLITE_OMIT_JSON)
2681/*
2682** Register the JSON table-valued functions
2683*/
2684int sqlite3JsonTableFunctions(sqlite3 *db){
2685 int rc = SQLITE_OK;
drh505ad2c2015-08-21 17:33:11 +00002686 static const struct {
drhdaefcd92022-01-08 15:37:13 +00002687 const char *zName;
2688 sqlite3_module *pModule;
drh505ad2c2015-08-21 17:33:11 +00002689 } aMod[] = {
2690 { "json_each", &jsonEachModule },
2691 { "json_tree", &jsonTreeModule },
2692 };
drh69b0ce32022-02-04 13:15:01 +00002693 unsigned int i;
drh505ad2c2015-08-21 17:33:11 +00002694 for(i=0; i<sizeof(aMod)/sizeof(aMod[0]) && rc==SQLITE_OK; i++){
2695 rc = sqlite3_create_module(db, aMod[i].zName, aMod[i].pModule, 0);
drhcb6c6c62015-08-19 22:47:17 +00002696 }
drh5fa5c102015-08-12 16:49:40 +00002697 return rc;
2698}
drh9dbf96b2022-01-06 01:40:09 +00002699#endif /* !defined(SQLITE_OMIT_VIRTUALTABLE) && !defined(SQLITE_OMIT_JSON) */