Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit597e41e

Browse files
committed
Fix json_to_record() bug with nested objects.
A thinko concerning nesting depth caused json_to_record() to produce bogusoutput if a field of its input object contained a sub-object with a fieldname matching one of the requested output column names. Per bug #13996from Johann Visagie.I added a regression test case based on his example, plus parallel testsfor json_to_recordset, jsonb_to_record, jsonb_to_recordset. The latterthree do not exhibit the same bug (which suggests that we may be missingsome opportunities to share code...) but testing seems like a good ideain any case.Back-patch to 9.4 where these functions were introduced.
1 parent55965eb commit597e41e

File tree

5 files changed

+49
-2
lines changed

5 files changed

+49
-2
lines changed

‎src/backend/utils/adt/jsonfuncs.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2350,7 +2350,7 @@ hash_object_field_end(void *state, char *fname, bool isnull)
23502350
/*
23512351
* Ignore nested fields.
23522352
*/
2353-
if (_state->lex->lex_level>2)
2353+
if (_state->lex->lex_level>1)
23542354
return;
23552355

23562356
/*

‎src/test/regress/expected/json.out

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1552,3 +1552,19 @@ select * from json_to_recordset('[{"a":1,"b":{"d":"foo"},"c":true},{"a":2,"c":fa
15521552
2 | {"d":"bar"} | f
15531553
(2 rows)
15541554

1555+
select *, c is null as c_is_null
1556+
from json_to_record('{"a":1, "b":{"c":16, "d":2}, "x":8}'::json)
1557+
as t(a int, b json, c text, x int);
1558+
a | b | c | x | c_is_null
1559+
---+-----------------+---+---+-----------
1560+
1 | {"c":16, "d":2} | | 8 | t
1561+
(1 row)
1562+
1563+
select *, c is null as c_is_null
1564+
from json_to_recordset('[{"a":1, "b":{"c":16, "d":2}, "x":8}]'::json)
1565+
as t(a int, b json, c text, x int);
1566+
a | b | c | x | c_is_null
1567+
---+-----------------+---+---+-----------
1568+
1 | {"c":16, "d":2} | | 8 | t
1569+
(1 row)
1570+

‎src/test/regress/expected/jsonb.out

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1760,6 +1760,22 @@ select * from jsonb_to_recordset('[{"a":1,"b":"foo","d":false},{"a":2,"b":"bar",
17601760
2 | bar | t
17611761
(2 rows)
17621762

1763+
select *, c is null as c_is_null
1764+
from jsonb_to_record('{"a":1, "b":{"c":16, "d":2}, "x":8}'::jsonb)
1765+
as t(a int, b jsonb, c text, x int);
1766+
a | b | c | x | c_is_null
1767+
---+-------------------+---+---+-----------
1768+
1 | {"c": 16, "d": 2} | | 8 | t
1769+
(1 row)
1770+
1771+
select *, c is null as c_is_null
1772+
from jsonb_to_recordset('[{"a":1, "b":{"c":16, "d":2}, "x":8}]'::jsonb)
1773+
as t(a int, b jsonb, c text, x int);
1774+
a | b | c | x | c_is_null
1775+
---+-------------------+---+---+-----------
1776+
1 | {"c": 16, "d": 2} | | 8 | t
1777+
(1 row)
1778+
17631779
-- indexing
17641780
SELECT count(*) FROM testjsonb WHERE j @> '{"wait":null}';
17651781
count

‎src/test/regress/sql/json.sql

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -487,7 +487,6 @@ select json_object('{a,b,NULL,"d e f"}','{1,2,3,"a b c"}');
487487

488488
select json_object('{a,b,"","d e f"}','{1,2,3,"a b c"}');
489489

490-
491490
-- json_to_record and json_to_recordset
492491

493492
select*from json_to_record('{"a":1,"b":"foo","c":"bar"}')
@@ -498,3 +497,11 @@ select * from json_to_recordset('[{"a":1,"b":"foo","d":false},{"a":2,"b":"bar","
498497

499498
select*from json_to_recordset('[{"a":1,"b":{"d":"foo"},"c":true},{"a":2,"c":false,"b":{"d":"bar"}}]')
500499
as x(aint, b json, cboolean);
500+
501+
select*, c isnullas c_is_null
502+
from json_to_record('{"a":1, "b":{"c":16, "d":2}, "x":8}'::json)
503+
as t(aint, b json, ctext, xint);
504+
505+
select*, c isnullas c_is_null
506+
from json_to_recordset('[{"a":1, "b":{"c":16, "d":2}, "x":8}]'::json)
507+
as t(aint, b json, ctext, xint);

‎src/test/regress/sql/jsonb.sql

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -372,6 +372,14 @@ select * from jsonb_to_record('{"a":1,"b":"foo","c":"bar"}')
372372
select*from jsonb_to_recordset('[{"a":1,"b":"foo","d":false},{"a":2,"b":"bar","c":true}]')
373373
as x(aint, btext, cboolean);
374374

375+
select*, c isnullas c_is_null
376+
from jsonb_to_record('{"a":1, "b":{"c":16, "d":2}, "x":8}'::jsonb)
377+
as t(aint, b jsonb, ctext, xint);
378+
379+
select*, c isnullas c_is_null
380+
from jsonb_to_recordset('[{"a":1, "b":{"c":16, "d":2}, "x":8}]'::jsonb)
381+
as t(aint, b jsonb, ctext, xint);
382+
375383
-- indexing
376384
SELECTcount(*)FROM testjsonbWHERE j @>'{"wait":null}';
377385
SELECTcount(*)FROM testjsonbWHERE j @>'{"wait":"CC"}';

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp