在rspec中不会引发ConstraintException

时间:2017-12-06 08:30:07

标签: ruby-on-rails ruby activerecord rspec exception-handling

我想在删除记录时编写一个处理FOREIGN KEY constraint错误的测试,但不会引发ConstraintException。

表的架构如下

class CreateCountries < ActiveRecord::Migration[5.1]
  def change
    create_table :countries do |t|
      t.string :name
      t.integer :sequence
    end
  end
end

class CreateStates < ActiveRecord::Migration[5.1]
  def change
    create_table :states do |t|
      t.string :name
      t.integer :sequence
      t.references :country, foreign_key: true
    end
  end
end

我确认在rails console删除它时会引发ConstraintException。

c = Country.create!(name: 'country')
State.create!(name: 'state', country: c)
c.destroy
  

(0.1ms)开始交易     SQL(0.8ms)DELETE FROM“countries”WHERE“countries”。“id”=? [[“id”,10]]      (6.1ms)回滚事务   ActiveRecord :: InvalidForeignKey:SQLite3 :: ConstraintException:FOREIGN KEY约束失败:DELETE FROM“countries”WHERE“countries”。“id”=?   来自/Users/masamoto/.rbenv/versions/2.4.2/lib/ruby/gems/2.4.0/gems/sqlite3-1.3.13/lib/sqlite3/statement.rb:108:in`step'

然而,在rspec中没有发生错误,在我看来它被正常删除了。

describe 'Error' do
  it 'Destroy' do
    country = Country.create!(name: 'hohooho')
    State.create!(name: 'oooooo', country: country)
    country.destroy
  end
end
  

错误         破坏

     

以0.0339秒结束(文件加载时间为3.27秒)   1例,0次失败

我认为交易没有提交,我尝试设置config.use_transactional_fixtures = false,但它没有改变。

我尝试了显式提交,但结果是一样的。

describe 'Error' do
  it 'Destroy' do
    country = nil
    ActiveRecord::Base.transaction do
      country = Country.create!(name: 'hohooho')
      State.create!(name: 'oooooo', country: country)
    end

    ActiveRecord::Base.transaction do
      country.destroy
    end
  end
end

有没有人有想法?

1 个答案:

答案 0 :(得分:1)

这是因为您的外键约束不在测试数据库中。

将以下内容添加到application.rb文件

config.active_record.schema_format = :sql

并运行

rake db:test:prepare

应解决问题

可在此处找到更多信息missing foreign key in test database