My Rails application uses two databases, first is postgresql and second -sqlite, the last for test environment. I used Devise gem which uses inet data type to carring infomation about IP. It works well for postgresql, but couses some errors for sqlite. I had installed a gem postgres_ext and added it to Gemfile, but it didn't solve the problem. Below is a piece of log:
$ RAILS_ENV=test rake db:setup
(in /user/project)
db/test.sqlite3 already exists
-- enable_extension("plpgsql")
-> 0.0030s
-- create_table("comments", {:force=>:cascade})
-> 0.3368s
-- add_index("comments", ["commentable_id"],
{:name=>"index_comments_on_commentable_id", :using=>:btree})
-> 0.1680s
-- add_index("comments", ["commentable_type"], {:name=>"index_comments_on_commentable_type", :using=>:btree})
-> 0.1898s
-- add_index("comments", ["user_id"], {:name=>"index_comments_on_user_id", :using=>:btree})
-> 0.1568s
-- create_table("contacts", {:force=>:cascade})
-> 0.2803s
-- create_table("delayed_jobs", {:force=>:cascade})
-> 0.2818s
-- add_index("delayed_jobs", ["priority", "run_at"], {:name=>"delayed_jobs_priority", :using=>:btree})
-> 0.1677s
-- create_table("exercises", {:force=>:cascade})
-> 0.3360s
-- create_table("languages", {:force=>:cascade})
-> 0.3025s
-- create_table("levels", {:force=>:cascade})
-> 0.2692s
-- create_table("solutions", {:force=>:cascade})
-> 0.3262s
-- create_table("users", {:force=>:cascade})
rake aborted!
NoMethodError: undefined method `inet' for #<ActiveRecord::ConnectionAdapters::TableDefinition:0x00000007563ec8>
/home/mtczerwinski/Projekty/ruby/railsilla/db/schema.rb:104:in `block (2 levels) in <top (required)>'
and so on.
Can you tell me what I am doing wrong ?
You can replace it with "string" type and it will work
# pg
# t.inet :current_sign_in_ip
# t.inet :last_sign_in_ip
# mysql
t.string :current_sign_in_ip
t.string :last_sign_in_ip
PostgreSQL has a native inet
type:
8.9.1. inet
The
inet
type holds an IPv4 or IPv6 host address, and optionally its subnet, all in one field. [...]
but SQLite doesn't. Apparently your users
table has an inet
column in it so that part of your schema is PostgreSQL-specific.
Using a different database for testing than you use for development and production is just as bad an idea as using different databases for development and production. ActiveRecord offers very little in the way of portability so switch your test environment to PostgreSQL too.
My CI/CD fires some tests to see that the build is correct, and I can't use the production database for those tests. It doesn't make sense to lose functionality and convert everything to string just because I want to test that the application has been deployed properly. So when I deploy I copy a modified database.yml that redefines test to:
test:
adapter: sqlite3
database: db/test.sqlite3
pool: 5
timeout: 5000
This allows me to test locally and in Travis using a proper database (the same than in production) To avoid problems with sqlite, I redefine .inet inside the migration (only if the database is SQLIte3).
# Redefine inet to string for SQLite3
if t.class.to_s.include? "::SQLite3"
t.define_singleton_method(:inet) do |*args|
t.string *args
end
end
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With