MariaDB 在使用大型 WHERE IN 时崩溃

MariaDB crashes when using large WHERE IN

我有一个旧项目,我正在尝试升级到更新版本的 SQL。目前是 运行 MySql 5.5 并且工作正常。我已经将 som 测试数据迁移到 MariaDB 10.5.9,但是当我尝试 运行 查询(在 MySql 5.5 上运行良好)时,MariaDB 崩溃了。

查询量很大,广泛使用WHERE IN。目前我无法遗憾地重构查询,所以我试图找出导致崩溃的原因。

它有 3 个 WHERE IN。第一个是 24 个项目,第二个是 696 个,第三个是 2 个。如果我只从第一个或第二个 WHERE IN 中删除一个项目,它会立即工作 returns 数据。 answers table 是 MyISAM

我遇到的错误

SQL Error [08S01]: Communications link failure

The last packet sent successfully to the server was 0 milliseconds ago. The driver has not received any packets from the server.

和查询

SELECT
    definition_id,
    answer AS value
FROM
    answers
WHERE
    definition_id IN (...)
    AND respondent_id in (...)
    AND context IN (1, 0)
LIMIT 50

我已经尝试将 max_allowed_packet 更改为更高的值(在 5.5 中为 16MB),但遗憾的是它没有任何改变。

EXPLAIN SQL_NO_CACHE 的结果(如果我删除了 WHERE IN 中的大量数据以避免崩溃)

id select_type table type possible_keys key key_len ref rows Extra
1 PRIMARY ALL 824 Using temporary; Using filesort
2 DERIVED s1 range definition_respondent_context,respondent_id definition_respondent_context 12 824 Using index condition; Using temporary; Using filesort
2 DERIVED s2 eq_ref definition_respondent_context,respondent_id definition_respondent_context 12 const,database_name.s1.respondent_id,const 1

编辑:我设法通过对定义 table

使用连接使其工作
SELECT
    a.definition_id,
    a.answer AS value
FROM
    answers AS a
JOIN definitions AS d ON a.definition_id = d.id
WHERE
    d.id IN (...)
    AND a.respondent_id in (...)
    AND a.context IN (1, 0)
LIMIT 50

您的问题的一个解决方案是更改您的 design/approach,这样您就没有包含 500-1000 个项目的 WHERE IN (...) 子句。一方面,您是否会让某个应用程序将如此多的参数传递回您的数据库实例是值得怀疑的。因此,假设此数据不是来自外部,那么应该可以将其维护在单独的 table 中。假设您为此有两个 table,您的查询可能会变成:

SELECT a.definition_id, a.answer AS value
FROM answers a
INNER JOIN definitions d
    ON d.id = a.definition_id
INNER JOIN respondents r
    ON r.id = a.respondent_id
WHERE
    context IN (1, 0)
-- ORDER BY <something>
LIMIT 50;