[MDEV-27533] The result of `CONVERT(json USING ...)` is erroneously treated as JSON Created: 2022-01-18  Updated: 2023-04-27

Status: Open
Project: MariaDB Server
Component/s: Character Sets, JSON
Affects Version/s: 10.5
Fix Version/s: 10.4, 10.5, 10.6

Type: Bug Priority: Major
Reporter: Alexander Barkov Assignee: Alexander Barkov
Resolution: Unresolved Votes: 0
Labels: None

Issue Links:
Relates
relates to MDEV-27018 IF and COALESCE lose "json" property Closed

 Description   

I run this script:

-- Note, to reproduce in 10.2 change CAST(..VARCHAR(30)) to CAST(..CHAR(30))
SET NAMES utf8;
SELECT json_object('a',CAST(json_object('b','c') AS VARCHAR(30)));

+------------------------------------------------------------+
| json_object('a',CAST(json_object('b','c') AS VARCHAR(30))) |
+------------------------------------------------------------+
| {"a": "{\"b\": \"c\"}"}                                    |
+------------------------------------------------------------+

The output looks good:

  • The result json_object('b','c') is a JSON value
  • Then it's passed to CAST(). The result of CAST() is a general purpose string, it's not a JSON value any more.
  • The result of CAST() is passed to the outer JSON_OBJECT(), and it correctly gets escaped.

Now I run this script:

SET NAMES utf8;
SELECT json_object('a',CONVERT(json_object('b','c') USING utf8));

+-----------------------------------------------------------+
| json_object('a',CONVERT(json_object('b','c') USING utf8)) |
+-----------------------------------------------------------+
| {"a": {"b": "c"}}                                         |
+-----------------------------------------------------------+

Looks wrong. It should return the same result with the previous script, because the result of CONVERT() is a general purpose string, so it must be escaped when passed to the outer json_object().

What other databases do

If I run equivalent scripts in Oracle 21c, they both escape, which looks correct:

SELECT json_object('a' VALUE CAST(json_object('b' VALUE 'c') AS VARCHAR(30))) FROM DUAL;

JSON_OBJECT('A'VALUECAST(JSON_OBJECT('B'VALUE'C')ASVARCHAR(30)))
{"a":"{\"b\":\"c\"}"}

SELECT json_object('a' VALUE CONVERT(json_object('b' VALUE 'c'),'US7ASCII', 'WE8ISO8859P1')) FROM DUAL;

JSON_OBJECT('A'VALUECONVERT(JSON_OBJECT('B'VALUE'C'),'US7ASCII','WE8ISO8859P1'))
{"a":"{\"b\":\"c\"}"}


Generated at Thu Feb 08 09:53:38 UTC 2024 using Jira 8.20.16#820016-sha1:9d11dbea5f4be3d4cc21f03a88dd11d8c8687422.