diff --git a/expression/integration_test.go b/expression/integration_test.go index 27d7a5cbc5db3..09735e94af0df 100755 --- a/expression/integration_test.go +++ b/expression/integration_test.go @@ -7342,6 +7342,19 @@ func (s *testIntegrationSuite) TestIssue20860(c *C) { c.Assert(tk.ExecToErr("update t set d = adddate(d, interval 1 day) where id < 10"), NotNil) } +func (s *testIntegrationSerialSuite) TestJsonObjectCompare(c *C) { + tk := testkit.NewTestKit(c, s.store) + tk.MustExec("use test") + + tk.MustQuery("select json_object('k', -1) > json_object('k', 2)").Check(testkit.Rows("0")) + tk.MustQuery("select json_object('k', -1) < json_object('k', 2)").Check(testkit.Rows("1")) + + tk.MustExec("drop table if exists tx") + tk.MustExec("create table tx(a double, b int)") + tk.MustExec("insert into tx values (3.0, 3)") + tk.MustQuery("select json_object('k', a) = json_object('k', b) from tx").Check(testkit.Rows("1")) +} + func (s *testIntegrationSerialSuite) TestIssue21290(c *C) { tk := testkit.NewTestKit(c, s.store) tk.MustExec("use test") diff --git a/types/json/binary_functions.go b/types/json/binary_functions.go index 4da946fa0b447..3fa030ea63100 100644 --- a/types/json/binary_functions.go +++ b/types/json/binary_functions.go @@ -729,9 +729,24 @@ func CompareBinary(left, right BinaryJSON) int { } cmp = leftCount - rightCount case TypeCodeObject: - // only equal is defined on two json objects. - // larger and smaller are not defined. - cmp = bytes.Compare(left.Value, right.Value) + // reference: + // https://github.com/mysql/mysql-server/blob/ee4455a33b10f1b1886044322e4893f587b319ed/sql/json_dom.cc#L2561 + leftCount, rightCount := left.GetElemCount(), right.GetElemCount() + cmp := compareInt64(int64(leftCount), int64(rightCount)) + if cmp != 0 { + return cmp + } + for i := 0; i < leftCount; i++ { + leftKey, rightKey := left.objectGetKey(i), right.objectGetKey(i) + cmp = bytes.Compare(leftKey, rightKey) + if cmp != 0 { + return cmp + } + cmp = CompareBinary(left.objectGetVal(i), right.objectGetVal(i)) + if cmp != 0 { + return cmp + } + } } } else { cmp = precedence1 - precedence2