无法运行Rails测试:UNIQUE约束失败(reviews.id)
我之前也碰到过这个坑!这确实是Rails fixtures的ID冲突问题,尤其是用SQLite的时候容易踩。给你几个靠谱的解决办法,按顺序试试:
先检查你的reviews fixtures文件
打开test/fixtures/reviews.yml,看看是不是手动给多个review指定了相同的id值?比如:review_one: id: 1 # 其他字段... review_two: id: 1 # 其他字段...如果是这样,删掉手动写的
id行就行,Rails会自动为fixtures分配唯一ID;要是必须手动指定,就把每个review的id改成不重复的数值。重置测试数据库的自增序列
有时候即使fixtures没指定ID,SQLite的自增序列可能和fixtures里的ID脱节了。直接运行这条命令就能搞定:rails db:test:prepare它会重新创建测试数据库、同步schema,同时重置所有表的序列,能解决大部分ID冲突问题。
强制重新加载fixtures(可选)
确保你的测试类继承了ActionDispatch::IntegrationTest或ActiveSupport::TestCase,如果还是有问题,可以在测试的setup方法里强制重新加载所有fixtures:setup do fixtures :all end彻底重置测试数据库
如果前面的方法都不管用,就用这两条命令彻底清空并重建测试环境:rails db:test:purge rails db:test:preparepurge会清空测试数据库的所有数据和表,prepare会重新创建表并加载fixtures,能彻底解决序列混乱的问题。
补充个小知识点:SQLite的自增序列是和表的最大ID绑定的,如果之前手动插入过数据或者fixtures里的ID超过了当前序列值,就会导致插入时冲突。所以尽量避免在fixtures里手动指定ID,让Rails自动生成是最稳妥的。
内容的提问来源于stack exchange,提问作者Arthur

