事务和锁定表(INNODB_TRX
、
INNODB_LOCKS
和
INNODB_LOCK_WAITS
)公开的数据代表了对快速变化数据的一瞥。这不像用户表,其中数据仅在发生应用程序启动的更新时发生变化。底层数据是内部系统管理的数据,并且可以非常快速地改变。
出于性能原因,并为了最大限度地减少事务和锁定表之间误导性连接的可能性,
每当对任何表发出a 时,InnoDB
都会将所需的事务和锁定信息收集到中间缓冲区
中。SELECT
仅当自上次读取缓冲区后超过 0.1 秒时,才会刷新此缓冲区。填充三个表所需的数据以原子方式一致地获取并保存在这个全局内部缓冲区中,形成时间点
“快照”. 如果在 0.1 秒内发生多个表访问(当 MySQL 处理这些表之间的连接时,它们几乎肯定会这样做),则使用相同的快照来满足查询。
当您在单个查询中将这些表中的任何一个连接在一起时,将返回正确的结果,因为这三个表的数据来自同一个快照。因为缓冲区不会随着这些表中的任何一个的每次查询而刷新,如果您在十分之一秒内对这些表发出单独的查询,则查询之间的结果是相同的。另一方面,对相同或不同表发出的两次单独查询间隔超过十分之一秒可能会看到不同的结果,因为数据来自不同的快照。
因为InnoDB
在收集事务和锁定数据时必须暂时停止,所以对这些表的过于频繁的查询会对其他用户所看到的性能产生负面影响。
由于这些表包含敏感信息(至少
INNODB_LOCKS.LOCK_DATA
和
INNODB_TRX.TRX_QUERY
),出于安全原因,只PROCESS
允许具有特权的用户使用SELECT
它们。
如前所述,填充事务和锁定表(INNODB_TRX
、
INNODB_LOCKS
和
INNODB_LOCK_WAITS
)的数据被自动提取并保存到提供“时间点”快照的中间缓冲区。从同一快照查询时,所有三个表中的数据是一致的。然而,底层数据变化如此之快,以至于对其他同样快速变化的数据的类似瞥见可能并不同步。InnoDB
因此,在将事务中的数据与表中的数据进行比较和锁定表时应该小心PROCESSLIST
。来自的数据PROCESSLIST
表与有关锁定和事务的数据不来自相同的快照。即使你发单
SELECT
(比如join
INNODB_TRX
and
PROCESSLIST
),那些表的内容一般也不一致。
INNODB_TRX
可能引用中不存在的行,或者当前正在执行的事务的 SQL 查询可能与PROCESSLIST
中所示的
不同。
INNODB_TRX.TRX_QUERY
PROCESSLIST.INFO