-
Notifications
You must be signed in to change notification settings - Fork 2
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
ActiveRecord >= 6.1 compatibility #61
Conversation
d874d66
to
a9d7925
Compare
a9d7925
to
c303ea7
Compare
ok @grdw this is finally ready! |
@@ -43,4 +45,4 @@ jobs: | |||
- name: Run rubocop | |||
run: bundle exec rake rubocop | |||
- name: Run tests | |||
run: bundle exec rake spec | |||
run: bundle exec --gemfile ${{ matrix.gemfile }} rspec |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this makes 100% sure that the gems used are the ones in the specified Gemfile (even though they were the ones installed in a previous step)
Metrics/BlockLength: | ||
Exclude: | ||
- spec/**/*_spec.rb | ||
|
||
Metrics/ClassLength: | ||
CountAsOne: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
copying some common styles I use, I tend to find the default strictness to be a bit of a headache
@@ -1,5 +1,8 @@ | |||
# CHANGELOG | |||
|
|||
## 0.3.0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
went with a minor bump because (1) we're still at a 0.
release so no rules! and (2) this fixes core functionality for a number of significant usages
@@ -0,0 +1,19 @@ | |||
#!/bin/bash |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is just for testing locally. it won't try all the ruby versions, but at least it'll go through each ActiveRecord version. it's much more likely that we have a bug specific to an AR version than a ruby version
@@ -18,11 +18,11 @@ Gem::Specification.new do |spec| | |||
# Specify which files should be added to the gem when it is released. | |||
# The `git ls-files -z` loads the files in the RubyGem that have been added into git. | |||
spec.files = Dir.chdir(File.expand_path(__dir__)) do | |||
`git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features|doc)/}) } | |||
`git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features|doc|bin)/}) } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no reason to have the test script and console
included in the packaged gem
end | ||
spec.require_paths = ['lib'] | ||
|
||
spec.add_dependency 'activerecord', '>= 5' | ||
spec.add_dependency 'activerecord', '>= 5', '< 6.2' |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
starting to test on 7.0 alpha already, but I didn't want to include it in here yet
index_name, index_type, index_columns, index_options = add_index_options(table_name, column_name, options) | ||
execute "ALTER TABLE #{quote_table_name(table_name)} ADD #{index_type} INDEX #{quote_column_name(index_name)} (#{index_columns})#{index_options}" # rubocop:disable Layout/LineLength | ||
end | ||
if Gem.loaded_specs['activerecord'].version >= Gem::Version.new('6.1') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if there's a prettier way of achieving this, I'm all ears. this was an easy solution that seems pretty simple to follow
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There are multiple ways of making this prettier:
Splitting into modules:
# in lib/active_record/connection_adapters/mysql2_ghost_adapter/indexes_six.rb
module IndexesSix
def add_index(....)
end
end
# in lib/active_record/connection_adapters/mysql2_ghost_adapter/indexes_five.rb
module IndexesFive
def add_index(....)
end
end
# in lib/active_record/connection_adapters/mysql2_ghost_adapter.rb
module ConnectionAdapters
class Mysql2GhostAdapter < Mysql2Adapter
if Gem.loaded_specs['activerecord'].version >= Gem::Version.new('6.1')
include Mysql2GhostAdapter::IndexesSix
else
include Mysql2GhostAdapter::IndexesFive
end
end
end
Another way would be dynamically including a module based on the version:
version = if Gem.loaded_specs['activerecord'].version >= Gem::Version.new('6.1')
"Five"
else
"Six"
end
include const_get("SomeLib::#{version}")
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
since the number of methods is relatively low, I somewhat prefer the existing way to including modules as its easier to navigate. the second approach is nice, though, if we end up needing another conditional. I will make an issue for it as a pattern to consider if we also need 7.0 compatibility (somewhat likely)
@@ -111,6 +144,25 @@ def schema_migration_update?(sql) | |||
INSERT_SCHEMA_MIGRATION_PATTERN =~ sql || | |||
DROP_SCHEMA_MIGRATION_PATTERN =~ sql | |||
end | |||
|
|||
def build_add_index_sql(table_name, column_names, index_name, # rubocop:disable Metrics/ParameterLists |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
inspired by the ActiveRecord code used to build a CREATE INDEX
query (we can't use that because gh-ost
only triggers on ALTER TABLE
queries
allow(mysql_client).to receive(:escape).with(table.to_s).and_return(table.to_s) | ||
allow(mysql_client).to receive(:more_results?) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
just mocked these because tests started failing on them. I didn't do too much digging into how ActiveRecord is using these return values (other than obviously using the escape
method to... escape a string)
spec/active_record/connection_adapters/mysql2_ghost_adapter_spec.rb
Outdated
Show resolved
Hide resolved
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't know enough about ActiveRecord internals to feel confident in my approval but it looks like good ruby 😅
Description
Some method signatures changed (somewhat recently?) that started causing errors with the methods we've redefined around adding and removing indexes. We need to use the new method signatures so we're compatible with all versions.
Fixes #60
Fixes #59
Type of change
Please delete options that are not relevant.
How Has This Been Tested?
Checklist: