MDEV-11557 port MySQL-5.7 JSON tests to MariaDB.

paths ending on [0]..[0] should be handled in conforming manner.
This commit is contained in:
Alexey Botchkov 2017-01-26 16:35:05 +04:00
parent 71495a1748
commit d96ee168a1
5 changed files with 150 additions and 53 deletions

View file

@ -444,3 +444,53 @@ json CREATE TABLE `json` (
`j` int(11) DEFAULT NULL
) ENGINE=MyISAM DEFAULT CHARSET=latin1
drop table json;
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2]' )
1
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0]' )
1
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0]' )
1
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0][0]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0][0]' )
1
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2]' );
json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2]' )
2
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0]' );
json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0]' )
2
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0]' );
json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0]' )
2
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0][0]' );
json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0][0]' )
2
select json_length( '{"a":{"b":{"d":1}}, "a":{"c":{"d":1, "j":2}}}', '$.a[0][0][0].c' );
json_length( '{"a":{"b":{"d":1}}, "a":{"c":{"d":1, "j":2}}}', '$.a[0][0][0].c' )
2
select json_set('1', '$[0]', 100);
json_set('1', '$[0]', 100)
100
select json_set('1', '$[0][0]', 100);
json_set('1', '$[0][0]', 100)
100
select json_set('1', '$[1]', 100);
json_set('1', '$[1]', 100)
[1, 100]
select json_set('{"a":12}', '$[0]', 100);
json_set('{"a":12}', '$[0]', 100)
100
select json_set('{"a":12}', '$[0].a', 100);
json_set('{"a":12}', '$[0].a', 100)
{"a":100}
select json_set('{"a":12}', '$[0][0].a', 100);
json_set('{"a":12}', '$[0][0].a', 100)
{"a":100}
select json_set('{"a":12}', '$[0][1].a', 100);
json_set('{"a":12}', '$[0][1].a', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_set'

View file

@ -420,10 +420,10 @@ json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2]' )
1
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0]' )
NULL
1
select json_length( '[ 1, [ 2, 3, 4 ], {"a": 1} ]', '$[2][0]' );
json_length( '[ 1, [ 2, 3, 4 ], {"a": 1} ]', '$[2][0]' )
NULL
1
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][1]' );
json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][1]' )
NULL
@ -1694,13 +1694,13 @@ JSON_ARRAY_APPEND
# ----------------------------------------------------------------------
select json_array_append('{"a":1}', '$[0]', 100);
json_array_append('{"a":1}', '$[0]', 100)
NULL
[{"a":1}, 100]
select json_array_append('3', '$[0]', 100);
json_array_append('3', '$[0]', 100)
NULL
[3, 100]
select json_array_append('3', '$[0][0][0][0]', 100);
json_array_append('3', '$[0][0][0][0]', 100)
NULL
[3, 100]
# ----------------------------------------------------------------------
# Test of JSON_INSERT function.
# ----------------------------------------------------------------------
@ -2118,7 +2118,7 @@ json_set('1', '$', 4)
4
select json_set('1', '$[0]', 4);
json_set('1', '$[0]', 4)
[1, 4]
4
select json_set('1', '$[1]', 4);
json_set('1', '$[1]', 4)
[1, 4]
@ -2127,13 +2127,13 @@ json_set('1', '$[10]', '4', '$[11]', 5)
[1, "4", 5]
select json_set('[1,2,3]', '$[2][0]', 4);
json_set('[1,2,3]', '$[2][0]', 4)
[1,2,[3, 4]]
[1,2,4]
select json_set('[1,2,3]', '$[2][2]', 4);
json_set('[1,2,3]', '$[2][2]', 4)
[1,2,[3, 4]]
select json_set('{"a": 3}', '$.a[0]', 4);
json_set('{"a": 3}', '$.a[0]', 4)
{"a": [3, 4]}
{"a": 4}
select json_set('{"a": 3}', '$.a[1]', 4, '$.a[2]', '5');
json_set('{"a": 3}', '$.a[1]', 4, '$.a[2]', '5')
{"a": [3, 4, "5"]}
@ -2280,7 +2280,7 @@ json_replace('1', '$', 4)
4
select json_replace('1', '$[0]', 4);
json_replace('1', '$[0]', 4)
1
4
select json_replace('1', '$[1]', 4);
json_replace('1', '$[1]', 4)
1
@ -2289,13 +2289,13 @@ json_replace('1', '$[10]', '4', '$[11]', 5)
1
select json_replace('[1,2,3]', '$[2][0]', 4);
json_replace('[1,2,3]', '$[2][0]', 4)
[1,2,3]
[1,2,4]
select json_replace('[1,2,3]', '$[2][2]', 4);
json_replace('[1,2,3]', '$[2][2]', 4)
[1,2,3]
select json_replace('{"a": 3}', '$.a[0]', 4);
json_replace('{"a": 3}', '$.a[0]', 4)
{"a": 3}
{"a": 4}
select json_replace('{"a": 3}', '$.a[1]', 4, '$.a[2]', '5');
json_replace('{"a": 3}', '$.a[1]', 4, '$.a[2]', '5')
{"a": 3}
@ -2312,7 +2312,7 @@ true);
JSON_REPLACE('{ "a" : "foo", "b" : [ 1, 2, 3 ] }',
'$.a[0]',
true)
{ "a" : "foo", "b" : [ 1, 2, 3 ] }
{ "a" : true, "b" : [ 1, 2, 3 ] }
SELECT JSON_REPLACE('{ "a" : "foo", "b" : [ 1, 2, 3 ] }',
'$.b[5]',
true);
@ -3489,23 +3489,19 @@ JSON_SET('1', '$', 100)
100
SELECT JSON_SET('1', '$[0]', 100);
JSON_SET('1', '$[0]', 100)
[1, 100]
100
SELECT JSON_SET('1', '$[0][0]', 100);
JSON_SET('1', '$[0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_set'
100
SELECT JSON_SET('1', '$[0][0][0]', 100);
JSON_SET('1', '$[0][0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_set'
100
SELECT JSON_SET('[]', '$', 100);
JSON_SET('[]', '$', 100)
100
SELECT JSON_SET('[]', '$[0]', 100);
JSON_SET('[]', '$[0]', 100)
[, 100]
[100]
SELECT JSON_SET('[]', '$[0][0]', 100);
JSON_SET('[]', '$[0][0]', 100)
NULL
@ -3524,12 +3520,10 @@ JSON_SET('[1]', '$[0]', 100)
[100]
SELECT JSON_SET('[1]', '$[0][0]', 100);
JSON_SET('[1]', '$[0][0]', 100)
[[1, 100]]
[100]
SELECT JSON_SET('[1]', '$[0][0][0]', 100);
JSON_SET('[1]', '$[0][0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_set'
[100]
SELECT JSON_SET('[[1]]', '$', 100);
JSON_SET('[[1]]', '$', 100)
100
@ -3541,7 +3535,7 @@ JSON_SET('[[1]]', '$[0][0]', 100)
[[100]]
SELECT JSON_SET('[[1]]', '$[0][0][0]', 100);
JSON_SET('[[1]]', '$[0][0][0]', 100)
[[[1, 100]]]
[[100]]
SELECT JSON_SET('[[[1]]]', '$', 100);
JSON_SET('[[[1]]]', '$', 100)
100
@ -3559,17 +3553,13 @@ JSON_REPLACE('1', '$', 100)
100
SELECT JSON_REPLACE('1', '$[0]', 100);
JSON_REPLACE('1', '$[0]', 100)
1
100
SELECT JSON_REPLACE('1', '$[0][0]', 100);
JSON_REPLACE('1', '$[0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_update'
100
SELECT JSON_REPLACE('1', '$[0][0][0]', 100);
JSON_REPLACE('1', '$[0][0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_update'
100
SELECT JSON_REPLACE('[]', '$', 100);
JSON_REPLACE('[]', '$', 100)
100
@ -3594,12 +3584,10 @@ JSON_REPLACE('[1]', '$[0]', 100)
[100]
SELECT JSON_REPLACE('[1]', '$[0][0]', 100);
JSON_REPLACE('[1]', '$[0][0]', 100)
[1]
[100]
SELECT JSON_REPLACE('[1]', '$[0][0][0]', 100);
JSON_REPLACE('[1]', '$[0][0][0]', 100)
NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 1 to function 'json_update'
[100]
SELECT JSON_REPLACE('[[1]]', '$', 100);
JSON_REPLACE('[[1]]', '$', 100)
100
@ -3611,7 +3599,7 @@ JSON_REPLACE('[[1]]', '$[0][0]', 100)
[[100]]
SELECT JSON_REPLACE('[[1]]', '$[0][0][0]', 100);
JSON_REPLACE('[[1]]', '$[0][0][0]', 100)
[[1]]
[[100]]
SELECT JSON_REPLACE('[[[1]]]', '$', 100);
JSON_REPLACE('[[[1]]]', '$', 100)
100

View file

@ -179,3 +179,21 @@ create table json (j INT);
show create table json;
drop table json;
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2]' );
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0]' );
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0]' );
select json_length( '[ 1, [ 2, 3, 4 ], 5 ]', '$[2][0][0][0]' );
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2]' );
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0]' );
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0]' );
select json_length( '[ 1, [ 2, 3, 4 ], {"a":5, "b":6} ]', '$[2][0][0][0]' );
select json_length( '{"a":{"b":{"d":1}}, "a":{"c":{"d":1, "j":2}}}', '$.a[0][0][0].c' );
select json_set('1', '$[0]', 100);
select json_set('1', '$[0][0]', 100);
select json_set('1', '$[1]', 100);
select json_set('{"a":12}', '$[0]', 100);
select json_set('{"a":12}', '$[0].a', 100);
select json_set('{"a":12}', '$[0][0].a', 100);
select json_set('{"a":12}', '$[0][1].a', 100);

View file

@ -1983,13 +1983,22 @@ String *Item_func_json_insert::val_str(String *str)
if (je.value_type != JSON_VALUE_ARRAY)
{
const uchar *v_from= je.value_begin;
if (!mode_insert)
continue;
int do_array_autowrap;
if (mode_insert)
do_array_autowrap= !mode_replace || lp->n_item;
else
{
if (lp->n_item)
continue;
do_array_autowrap= 0;
}
str->length(0);
/* Wrap the value as an array. */
if (append_simple(str, js->ptr(), (const char *) v_from - js->ptr()) ||
str->append("[", 1))
(do_array_autowrap && str->append("[", 1)))
goto js_error; /* Out of memory. */
if (je.value_type == JSON_VALUE_OBJECT)
@ -1998,10 +2007,11 @@ String *Item_func_json_insert::val_str(String *str)
goto js_error;
}
if (append_simple(str, v_from, je.s.c_str - v_from) ||
str->append(", ", 2) ||
if ((do_array_autowrap &&
(append_simple(str, v_from, je.s.c_str - v_from) ||
str->append(", ", 2))) ||
append_json_value(str, args[n_arg+1], &tmp_val) ||
str->append("]", 1) ||
(do_array_autowrap && str->append("]", 1)) ||
append_simple(str, je.s.c_str, js->end()-(const char *) je.s.c_str))
goto js_error; /* Out of memory. */
@ -2033,7 +2043,7 @@ String *Item_func_json_insert::val_str(String *str)
v_to= (const char *) (je.s.c_str - je.sav_c_len);
str->length(0);
if (append_simple(str, js->ptr(), v_to - js->ptr()) ||
str->append(", ", 2) ||
(n_item > 0 && str->append(", ", 2)) ||
append_json_value(str, args[n_arg+1], &tmp_val) ||
append_simple(str, v_to, js->end() - v_to))
goto js_error; /* Out of memory. */

View file

@ -1187,6 +1187,8 @@ int json_skip_key(json_engine_t *j)
}
#define SKIPPED_STEP_MARK ((uint) ~0)
/*
Current step of the patch matches the JSON construction.
Now we should either stop the search or go to the next
@ -1195,24 +1197,48 @@ int json_skip_key(json_engine_t *j)
static int handle_match(json_engine_t *je, json_path_t *p,
json_path_step_t **p_cur_step, uint *array_counters)
{
json_path_step_t *next_step= *p_cur_step + 1;
DBUG_ASSERT(*p_cur_step < p->last_step);
if (json_read_value(je))
return 1;
if (json_value_scalar(je))
return 0;
(*p_cur_step)++;
array_counters[*p_cur_step - p->steps]= 0;
if ((int) je->value_type !=
(int) ((*p_cur_step)->type & JSON_PATH_KEY_OR_ARRAY))
{
(*p_cur_step)--;
return json_skip_level(je);
while (next_step->type == JSON_PATH_ARRAY && next_step->n_item == 0)
{
if (++next_step > p->last_step)
{
je->s.c_str= je->value_begin;
return 1;
}
}
return 0;
}
if (next_step->type == JSON_PATH_ARRAY && next_step->n_item == 0 &&
je->value_type & JSON_VALUE_OBJECT)
{
do
{
array_counters[next_step - p->steps]= SKIPPED_STEP_MARK;
if (++next_step > p->last_step)
{
je->s.c_str= je->value_begin;
return 1;
}
} while (next_step->type == JSON_PATH_ARRAY && next_step->n_item == 0);
}
array_counters[next_step - p->steps]= 0;
if ((int) je->value_type !=
(int) (next_step->type & JSON_PATH_KEY_OR_ARRAY))
return json_skip_level(je);
*p_cur_step= next_step;
return 0;
}
@ -1277,6 +1303,11 @@ int json_find_path(json_engine_t *je,
json_skip_array_item(je);
break;
case JST_OBJ_END:
do
{
(*p_cur_step)--;
} while (array_counters[(*p_cur_step) - p->steps] == SKIPPED_STEP_MARK);
break;
case JST_ARRAY_END:
(*p_cur_step)--;
break;