必须用innodb,myisam在爬虫场景中极易因断电、中断或并发导致数据损坏、表锁和统计不准;innodb通过事务日志实现崩溃恢复、行级锁保障并发安全,且统计准确可控。

爬虫数据存储必须用 InnoDB,MyISAM 在任何真实爬虫场景下都不稳——它连“写入中途断电丢半张表”这种基础风险都扛不住。
爬虫写入中断时,MyISAM 会留下损坏状态
爬虫常批量 INSERT INTO ... SELECT 或分页 INSERT,一旦网络抖动、进程被杀或服务器断电,MyISAM 的 .MYD 和 .MYI 文件极易不一致。此时 SELECT 可能直接报 Incorrect key file for table,必须停服运行 REPAIR TABLE,而该命令本身可能丢数据。
InnoDB 则靠 redo log 自动前滚、undo log 回滚,重启后秒级恢复到事务一致点,无需人工干预。
- 典型场景:凌晨定时爬取新闻列表,脚本执行到第 87 万条时被 OOM kill —— MyISAM 表已损坏;InnoDB 仅丢失未提交事务,其余数据完好
- 云环境更危险:AWS/Aliyun RDS 的自动主从切换、底层磁盘 I/O 暂停,都可能触发 MyISAM 不可逆损坏
高并发去重和更新必然需要行级锁与事务
真实爬虫不是单线程灌数据,而是多任务并行抓取+去重+更新状态(如 UPDATE urls SET status = 'done' WHERE url_hash = ?)。MyISAM 对这类操作一律锁整张表,后续所有插入、查询全部排队。
InnoDB 在 url_hash 有索引的前提下,只锁匹配的那几行,其他 URL 的写入和读取完全不受影响。
- 坑点:如果去重字段没建索引,或用了
LIKE '%keyword%'导致索引失效,InnoDB也会退化为表锁——但这可控,而 MyISAM 是无条件表锁 - 常见错误:用
INSERT IGNORE或REPLACE INTO做去重,MyISAM 不支持原子性,可能重复插入或丢失更新
COUNT(*) 和全表扫描的“快”在爬虫里毫无意义
MyISAM 的 COUNT(*) 快,是因为缓存了行数变量,但这个值在并发写入时不准,且崩溃后不可信。爬虫表几乎从不执行无条件 COUNT(*),而是查 COUNT(*) WHERE status = 'pending' 或 WHERE crawled_at > '2026-09-01'——这时两者都要走索引扫描,性能差异可忽略。
更关键的是:爬虫监控依赖准确统计。若 MyISAM 返回的 “pending 数量” 比实际少 2 万条,调度系统会误判任务完成,导致漏爬。
- 真实代价:MyISAM 的“快”建立在放弃一致性上,而爬虫数据的价值恰恰在于完整性和可追溯性
- 替代方案:高频统计需求应走单独计数表或 Redis,而非依赖引擎元数据
真正要警惕的不是“选哪个引擎”,而是别让历史遗留的 MyISAM 表混在爬虫库中——SHOW CREATE TABLE spider_urls 得确认是 ENGINE=InnoDB,否则某次批量更新就可能触发连锁故障。











