Commit 30903c37 authored by Alexander Barkov's avatar Alexander Barkov

MDEV-22976 CAST(JSON_EXTRACT() AS DECIMAL) does not handle boolean values

Item_func_json_extract did not implement val_decimal(),
so CAST(JSON_EXTRACT('{"x":true}', '$.x') AS DECIMAL) erroneously
returned 0 with a warning because of convertion from the string "true"
to decimal.

Implementing val_decimal(), so boolean values are correctly handled.
parent 009ef36d
......@@ -916,5 +916,18 @@ NULL
Warnings:
Warning 4037 Unexpected end of JSON text in argument 2 to function 'json_merge_patch'
#
# MDEV-22976 CAST(JSON_EXTRACT() AS DECIMAL) does not handle boolean values
#
SELECT
CAST(JSON_EXTRACT('{"x":true}', '$.x') AS DOUBLE) AS cf,
CAST(JSON_EXTRACT('{"x":true}', '$.x') AS DECIMAL) AS cd;
cf cd
1 1
SELECT
CAST(JSON_EXTRACT('{"x":false}', '$.x') AS DOUBLE) AS cf,
CAST(JSON_EXTRACT('{"x":false}', '$.x') AS DECIMAL) AS cd;
cf cd
0 0
#
# End of 10.2 tests
#
......@@ -540,6 +540,19 @@ SELECT JSON_MERGE_PATCH('{}');
SELECT JSON_MERGE_PATCH('{', '[1,2,3]');
SELECT JSON_MERGE_PATCH('{"a":"b"}', '[1,');
--echo #
--echo # MDEV-22976 CAST(JSON_EXTRACT() AS DECIMAL) does not handle boolean values
--echo #
SELECT
CAST(JSON_EXTRACT('{"x":true}', '$.x') AS DOUBLE) AS cf,
CAST(JSON_EXTRACT('{"x":true}', '$.x') AS DECIMAL) AS cd;
SELECT
CAST(JSON_EXTRACT('{"x":false}', '$.x') AS DOUBLE) AS cf,
CAST(JSON_EXTRACT('{"x":false}', '$.x') AS DECIMAL) AS cd;
--echo #
--echo # End of 10.2 tests
--echo #
......@@ -962,6 +962,41 @@ double Item_func_json_extract::val_real()
}
my_decimal *Item_func_json_extract::val_decimal(my_decimal *to)
{
json_value_types type;
char *value;
int value_len;
if (read_json(NULL, &type, &value, &value_len) != NULL)
{
switch (type)
{
case JSON_VALUE_STRING:
case JSON_VALUE_NUMBER:
{
my_decimal *res= decimal_from_string_with_check(to, collation.collation,
value,
value + value_len);
null_value= res == NULL;
return res;
}
case JSON_VALUE_TRUE:
int2my_decimal(E_DEC_FATAL_ERROR, 1, false/*unsigned_flag*/, to);
return to;
case JSON_VALUE_OBJECT:
case JSON_VALUE_ARRAY:
case JSON_VALUE_FALSE:
case JSON_VALUE_NULL:
break;
};
}
int2my_decimal(E_DEC_FATAL_ERROR, 0, false/*unsigned_flag*/, to);
return to;
}
bool Item_func_json_contains::fix_length_and_dec()
{
a2_constant= args[1]->const_item();
......
......@@ -171,6 +171,7 @@ class Item_func_json_extract: public Item_json_str_multipath
String *val_str(String *);
longlong val_int();
double val_real();
my_decimal *val_decimal(my_decimal *);
uint get_n_paths() const { return arg_count - 1; }
Item *get_copy(THD *thd, MEM_ROOT *mem_root)
{ return get_item_copy<Item_func_json_extract>(thd, mem_root, this); }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment