When I run a RSpec test for (JRuby + sqlite), but not (Ruby 1.9.3 + [mysql | postgres])
describe SomeModel do
it { should have_db_index(:name).unique(true) }
end
The spec fails even though the schema.rb shows the db field as unquiely indexed.
ActiveRecord::Schema.define(:version => 20120908004000) do
create_table “some_model”, :force => true do |t| t.string “name”, :limit => 63, :null => false end add_index “apps”, [“name”], :name => “index_apps_on_name”, :unique => true end
The issue seems to be that MySQL and Postgres connection adapters behave differently than the Sqlite.
So I did some digging. The shoulda matchers use this to evaluate index uniqueness.
::ActiveRecord::Base.connection.indexes(App.table_name).detect {|e| e.columns == [“name”]}
sqlite
<struct ActiveRecord::ConnectionAdapters::IndexDefinition table=“apps”, name=“index_apps_on_name”, unique=7, columns=[“name”], lengths=nil, orders=nil>
mysql
<struct ActiveRecord::ConnectionAdapters::IndexDefinition table=“apps”, name=“index_apps_on_name”, unique=true, columns=[“name”], lengths=nil, orders=nil>
postgres
<struct ActiveRecord::ConnectionAdapters::IndexDefinition table=“apps”, name=“index_apps_on_name”, unique=true, columns=[“name”], lengths=nil, orders=nil>
The difference is mysql2: unqiue = true, pg: unique = true, sqlite: unique = 7.
(1)
Is Sqlite unique supposed to be 7?
I don’t think so.
(2)
If not, anyone know where would I go to refactor this?
Somewhere in ActiveRecord::ConnectionAdapters::SQLiteAdapter?
I tried looking in api.rubyonrails.org, but Postgres was the only adapter with the indexes method.