MySQL 最近的动作很快,已经计划推出 8.0 版本,会新增很多新特性
在 5.7 中,JSON 已经被正式支持,但在 SQL 中对 JSON 的处理能力较弱,8.0 中这部分能力会加强,例如新增了这两个JSON聚合函数
JSON_ARRAYAGG()
JSON_OBJECTAGG()
通过JSON聚合函数,可以在 SQL 中直接把数据整合为JSON结构,非常简单
CREATE TABLE `t1` (
`key` varchar(8) DEFAULT NULL,
`grp` varchar(8) DEFAULT NULL,
`val` varchar(8)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
INSERT INTO t1(`key`, `grp`, `val`) VALUES
("key1", "g1", "v1"),
("key2", "g1", "v2"),
("key3", "g2", "v3");
把字段 ‘key’ 的所有值整合为一个JSON数组
mysql> SELECT JSON_ARRAYAGG(`key`) AS `keys` FROM t1;
+--------------------------+
| keys |
+--------------------------+
| ["key1", "key2", "key3"] |
+--------------------------+
1 row in set (0.00 sec)
分组聚合
mysql> SELECT grp, JSON_ARRAYAGG(`key`) AS `keys_grouped` FROM t1 GROUP BY grp;
+------+------------------+
| grp | keys_grouped |
+------+------------------+
| g1 | ["key1", "key2"] |
| g2 | ["key3"] |
+------+------------------+
2 rows in set (0.00 sec)
mysql> SELECT grp, JSON_OBJECTAGG(`key`, val) AS `key_val_grouped` FROM t1 GROUP BY grp;
+------+------------------------------+
| grp | key_val_grouped |
+------+------------------------------+
| g1 | {"key1": "v1", "key2": "v2"} |
| g2 | {"key3": "v3"} |
+------+------------------------------+
2 rows in set (0.00 sec)
把某两列的值整合为JSON对象
mysql> SELECT JSON_OBJECTAGG(`key`, val) AS `key_val` FROM t1;
+------------------------+
| key_val |
+------------------------+
| {
"key1": "v1",
"key2": "v2",
"key3": "v3"
} |
+------------------------+
1 row in set (0.00 sec)
例如一个产品表,其中包含产品的通用属性(名称、价格...)
产品还有自己的单独属性,例如 电脑会包含 cpu/内存 等型号、衣服会包含 颜色、材质 等
引申出另外两张表:扩展属性表、属性值表
查询出产品的所有信息,包括所有属性及其值,并整合为JSON结构
建表
// 产品表
CREATE TABLE `product` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(120) DEFAULT NULL,
`manufacturer` varchar(120) DEFAULT NULL,
`price` int(11) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
// 扩展属性表
CREATE TABLE `attribute` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`name` varchar(120) DEFAULT NULL,
`description` varchar(256) DEFAULT NULL,
PRIMARY KEY (`id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
// 属性值表
CREATE TABLE `value` (
`prod_id` int(11) NOT NULL,
`attribute_id` int(11) NOT NULL,
`value` text,
PRIMARY KEY (`prod_id`,`attribute_id`)
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
添加测试数据
// 插入一些属性
INSERT INTO attribute(id, name) VALUES
(1, "color"),
(2, "material"),
(3, "style"),
(4, "bulb_type"),
(5, "usage"),
(6, "cpu_type"),
(7, "cpu_speed"),
(8, "weight"),
(9, "battery_life"),
(10, "fuel_type");
// 插入一个产品:台灯
INSERT INTO product(id, name, manufacturer, price) VALUES
(1, "LED Desk Lamp", "X", 26);
// 插入台灯对应的属性值
INSERT INTO value VALUES
(1, 1, "black"),
(1, 2, "plastic"),
(1, 3, "classic"),
(1, 4, "LED"),
(1, 5, "Indoor use only");
// 插入一个产品:电脑
INSERT INTO product(id, name, manufacturer, price) VALUES
(2, "Laptop", "Y", 800);
// 插入电脑对应的属性值
INSERT INTO value VALUES
(2, 1, "blue"),
(2, 6, "quad core"),
(2, 7, "3400 mhz"),
(2, 8, "2,1 kg"),
(2, 9, "9h");
// 插入一个产品:烧烤架
INSERT INTO product(id, name, manufacturer, price) VALUES
(3, "Grill", "Z", 300);
// 插入对应属性值
INSERT INTO value VALUES
(3, 1, "black"),
(3, 8, "5 kg"),
(3, 10, "gas");
查询
// 关联3张表,按产品ID分组
// 把查询结果聚合为JSON对象
SELECT
JSON_OBJECT("key", p.id,
"title", p.name,
"manufacturer", p.manufacturer,
"price", p.price,
"specifications", JSON_OBJECTAGG(a.name, v.value)) as product
FROM
product as p JOIN value as v
ON p.id=v.prod_id
JOIN attribute as a
ON a.id=v.attribute_id
GROUP BY v.prod_id;
结果示例
{
"key": 1,
"price": 26,
"title": "LED Desk Lamp",
"manufacturer": "X",
"specifications": {
"color": "black",
"style": "classic",
"usage": "Indoor use only",
"material": "plastic",
"bulb_type": "LED"
}
}
......
本文整理自:
MySQL 8.0 Labs: JSON aggregation functions
MySQL 8 实验版本下载地址: MySQL Labs
(选择 MySQL Server 8.0.0 Optimizer)
原文来自:性能与架构
声明:所有来源为“聚合数据”的内容信息,未经本网许可,不得转载!如对内容有异议或投诉,请与我们联系。邮箱:marketing@think-land.com
支持全球约2.4万个城市地区天气查询,如:天气实况、逐日天气预报、24小时历史天气等
支持识别各类商场、超市及药店的购物小票,包括店名、单号、总金额、消费时间、明细商品名称、单价、数量、金额等信息,可用于商品售卖信息统计、购物中心用户积分兑换及企业内部报销等场景
涉农贷款地址识别,支持对私和对公两种方式。输入地址的行政区划越完整,识别准确度越高。
根据给定的手机号、姓名、身份证、人像图片核验是否一致
通过企业关键词查询企业涉讼详情,如裁判文书、开庭公告、执行公告、失信公告、案件流程等等。