mysql - 如何使用 MySQL 8 在 JSON 数组上创建索引

标签 mysql mysql-8.0

我在 mysql 8 中有一个 JSON 字段,如下所示:

[{"key": "apples", "string_values": ["red"]}, {"key": "oranges", "string_values": ["orange"]}]

有没有办法在字符串值上创建索引?我希望我能做这样的事情:

ALTER TABLE mytable ADD INDEX myindex( 
    (CAST(metadata->'$[*].string_values' AS UNSIGNED ARRAY)) 
);

但是返回以下错误:无法在索引的标量键部分中存储数组或对象

fiddle 例如:https://dbfiddle.uk/?rdbms=mysql_8.0&fiddle=ae36a5169094ae67a290febf09f49f0c

编辑:

我开始认为我能做到这一点的唯一方法是使用生成的列:

以下选择现在将命中索引。

ALTER TABLE mytable ADD string_values JSON AS (JSON_EXTRACT(metadata, '$[*].string_values[0]'));

ALTER TABLE mytable ADD INDEX idx_string_values( 
    (CAST(string_values->'$' AS CHAR(100) ARRAY))
);

SELECT * FROM mytable WHERE 'red' MEMBER OF(string_values->'$');

最佳答案

有 2 个独立的问题。


第一个是可以解决的。下一个 fiddle 描述了它:

CREATE TABLE mytable (metadata JSON);
INSERT INTO mytable VALUES ('[{"key": "apples", "string_values": ["red"]}, {"key": "oranges", "string_values": ["orange"]}]');
-- you try to index arrays
SELECT metadata->'$[*].string_values' FROM mytable;
-- but you need in scalar values
SELECT metadata->'$[*].string_values[0]' FROM mytable;
| metadata->'$[*].string_values' |
| :----------------------------- |
| [["red"], ["orange"]]          |

| metadata->'$[*].string_values[0]' |
| :-------------------------------- |
| ["red", "orange"]                 |

db<> fiddle here


第二个问题无法解决。

仔细查看您尝试创建索引时使用的语句:

ALTER TABLE mytable ADD INDEX myindex((CAST(metadata->'$[*].string_values' AS UNSIGNED ARRAY)));

数组["red", "orange"]中的值不是数字。

关于mysql - 如何使用 MySQL 8 在 JSON 数组上创建索引,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/66593730/

相关文章:

php - 使用隐藏字段将数组中的搜索结果重新提交回 MySQL 数据库

mysql - 在多个子查询中使用查询结果

mysql8.0.22设置默认值DATE_FORMAT(sysdate() ,'%Y%m%d' )错误

java - Spring data JPA 将 unsigned BIGINT 转换为 Long 而不是 BigInteger

mysql - 将记录传递给 MySQL 8 中的函数

macos - MYSQL服务器实例8.0.13自动随机关闭和开启

mysql - MySQL 中的动态数据透视表

sql - 有没有一种干净的方法来清理 MySQL 中的重复条目?

mysql - Django Raw Query SQL 注入(inject)显示攻击

mySQL8.0触发语句