外部锁定是使用文件系统锁定来管理多个进程对 MyISAM
数据库表的争用。外部锁定用于情况下,单个进程(如 MySQL 服务器)不能假设是唯一需要访问表的进程。以下是一些示例:
-
如果您运行多个服务器使用相同的数据库目录(不推荐),每个服务器必须启用外部锁定。
-
如果您使用 myisamchk 对
MyISAM
表执行表维护操作,您必须确保服务器未运行,或者服务器启用外部锁定,以便锁定表文件以与 myisamchk 协调访问表。同样适用于使用 myisampack 打包MyISAM
表。如果服务器启用外部锁定,您可以随时使用 myisamchk 进行读操作,例如检查表。在这种情况下,如果服务器尝试更新 myisamchk 正在使用的表,服务器将等待 myisamchk 完成后继续。
如果您使用 myisamchk 进行写操作,例如修复或优化表,或者使用 myisampack 打包表,您 必须 确保 mysqld 服务器不使用该表。如果您不停止 mysqld,至少在运行 myisamchk 之前执行 mysqladmin flush-tables。如果服务器和 myisamchk 同时访问表,表 可能会损坏。
在外部锁定生效时,每个需要访问表的进程在访问表之前都会获取表文件的文件系统锁。如果无法获取所有必要的锁,进程将被阻止访问表,直到锁可以被释放(当前持有锁的进程释放锁后)。
外部锁定会影响服务器性能,因为服务器有时需要等待其他进程释放锁后才能访问表。
如果您运行单个服务器来访问给定的数据目录(这是通常情况),并且没有其他程序(如 myisamchk)需要在服务器运行时修改表,那么外部锁定是不必要的。如果您只是使用其他程序 读取 表,而不是修改表,那么外部锁定不是必需的,尽管 myisamchk 可能会报告警告,如果服务器在 myisamchk 读取表时修改表。
禁用外部锁定时,要使用 myisamchk,您必须停止服务器或在运行 myisamchk 时锁定和刷新表。要避免这种要求,请使用 CHECK TABLE
和 REPAIR TABLE
语句来检查和修复 MyISAM
表。
对于 mysqld,外部锁定由 skip_external_locking
系统变量控制。当该变量启用时,外部锁定将被禁用,反之亦然。外部锁定默认情况下是禁用的。
可以在服务器启动时使用 --external-locking
或 --skip-external-locking
选项来控制外部锁定。
如果您使用外部锁定选项来启用对 MyISAM
表的更新来自多个 MySQL 进程,请不要使用 delay_key_write
系统变量设置为 ALL
或使用 DELAY_KEY_WRITE=1
表选项 для任何共享表。否则,索引可能会损坏。
满足该条件的最简单方法是始终使用 --external-locking
选项与 --delay-key-write=OFF
选项一起。(这不是默认设置,因为在许多设置中,混合使用前面的选项是有用的。)