Skip to content
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

Rails > 6 and Ruby > 3 support #577

Open
wants to merge 6 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Prev Previous commit
Next Next commit
Upgrade ruby sintaxe on gem
  • Loading branch information
Daniel Cunha committed Jun 13, 2023
commit 27b3d98cd2c21eccb910ec23e55d010b4602ee5c
3 changes: 2 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,11 @@
.bundle
.rvmrc
.ruby-version
Gemfile.lock
gemfiles/*.lock
pkg/*
*.rbc
tmp/*
.*.sw[a-z]
database.log
.byebug_history
.env
1 change: 1 addition & 0 deletions .tool-versions
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
ruby 3.0.6
102 changes: 102 additions & 0 deletions Gemfile.lock
Original file line number Diff line number Diff line change
@@ -0,0 +1,102 @@
PATH
remote: .
specs:
ar-octopus-ruby-3 (0.11.2)
activerecord (~> 6.0.6.1)
activesupport (~> 6.0.6.1)

GEM
remote: https://rubygems.org/
specs:
activemodel (6.0.6.1)
activesupport (= 6.0.6.1)
activerecord (6.0.6.1)
activemodel (= 6.0.6.1)
activesupport (= 6.0.6.1)
activesupport (6.0.6.1)
concurrent-ruby (~> 1.0, >= 1.0.2)
i18n (>= 0.7, < 2)
minitest (~> 5.1)
tzinfo (~> 1.1)
zeitwerk (~> 2.2, >= 2.2.2)
appraisal (2.4.1)
bundler
rake
thor (>= 0.14.0)
ast (2.4.2)
byebug (11.1.3)
coderay (1.1.3)
concurrent-ruby (1.2.2)
diff-lcs (1.5.0)
i18n (1.14.1)
concurrent-ruby (~> 1.0)
json (2.6.3)
method_source (1.0.0)
minitest (5.18.0)
mysql2 (0.5.5)
parallel (1.23.0)
parser (3.2.2.3)
ast (~> 2.4.1)
racc
pg (0.21.0)
pry (0.14.2)
coderay (~> 1.1)
method_source (~> 1.0)
pry-byebug (3.10.1)
byebug (~> 11.0)
pry (>= 0.13, < 0.15)
racc (1.7.0)
rainbow (3.1.1)
rake (13.0.6)
regexp_parser (2.8.1)
rexml (3.2.5)
rspec (3.12.0)
rspec-core (~> 3.12.0)
rspec-expectations (~> 3.12.0)
rspec-mocks (~> 3.12.0)
rspec-core (3.12.2)
rspec-support (~> 3.12.0)
rspec-expectations (3.12.3)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.12.0)
rspec-mocks (3.12.5)
diff-lcs (>= 1.2.0, < 2.0)
rspec-support (~> 3.12.0)
rspec-support (3.12.0)
rubocop (1.52.1)
json (~> 2.3)
parallel (~> 1.10)
parser (>= 3.2.2.3)
rainbow (>= 2.2.2, < 4.0)
regexp_parser (>= 1.8, < 3.0)
rexml (>= 3.2.5, < 4.0)
rubocop-ast (>= 1.28.0, < 2.0)
ruby-progressbar (~> 1.7)
unicode-display_width (>= 2.4.0, < 3.0)
rubocop-ast (1.29.0)
parser (>= 3.2.1.0)
ruby-progressbar (1.13.0)
sqlite3 (1.6.3-x86_64-linux)
thor (1.2.2)
thread_safe (0.3.6)
tzinfo (1.2.11)
thread_safe (~> 0.1)
unicode-display_width (2.4.2)
zeitwerk (2.6.8)

PLATFORMS
x86_64-linux

DEPENDENCIES
appraisal (>= 0.3.8)
ar-octopus-ruby-3!
mysql2 (~> 0.5)
pg (~> 0.18)
pry-byebug
rake
rspec (>= 3)
rubocop
sqlite3 (~> 1.4)

BUNDLED WITH
2.4.13
2 changes: 1 addition & 1 deletion Rakefile
Original file line number Diff line number Diff line change
Expand Up @@ -65,7 +65,7 @@ namespace :db do
class BlankModel < ActiveRecord::Base; end

BlankModel.using(shard_symbol).connection.initialize_schema_migrations_table
BlankModel.using(shard_symbol).connection.initialize_metadata_table if Octopus.atleast_rails50?
BlankModel.using(shard_symbol).connection.initialize_metadata_table if Octopus.atleast_rails50?

BlankModel.using(shard_symbol).connection.create_table(:users) do |u|
u.string :name
Expand Down
16 changes: 10 additions & 6 deletions ar-octopus.gemspec
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ $LOAD_PATH.push File.expand_path('../lib', __FILE__)
require 'octopus/version'

Gem::Specification.new do |s|
s.name = 'ar-octopus'
s.name = 'ar-octopus-ruby-3'
s.version = Octopus::VERSION
s.authors = ['Thiago Pradi', 'Mike Perham', 'Gabriel Sobrinho']
s.email = ['tchandy@gmail.com', 'mperham@gmail.com', 'gabriel.sobrinho@gmail.com']
Expand All @@ -17,22 +17,26 @@ Gem::Specification.new do |s|
s.require_paths = ['lib']

s.post_install_message = "Important: If you are upgrading from < Octopus 0.5.0 you need to run:\n" \
"$ rake octopus:copy_schema_versions\n\n" \
"$ rake octopus:copy_scha_versions\n\n" \
'Octopus now stores schema version information in each shard and migrations will not ' \
'work properly unless this task is invoked.'

s.required_ruby_version = '>= 2.2.0'

s.add_dependency 'activerecord', '>= 4.2.0'
s.add_dependency 'activesupport', '>= 4.2.0'
s.add_dependency 'activerecord', "~> 6.0.6.1"
s.add_dependency 'activesupport', "~> 6.0.6.1"

s.add_development_dependency 'appraisal', '>= 0.3.8'
s.add_development_dependency 'mysql2', '>= 0.3.18', "< 0.5"
# To install the mysql2 gem its necessary execute the following command before run bundle
# $ sudo apt-get install libmysqlclient-dev
s.add_development_dependency 'mysql2', '~> 0.5'
s.add_development_dependency 'pg', '~> 0.18'
s.add_development_dependency 'rake'
s.add_development_dependency 'rspec', '>= 3'
s.add_development_dependency 'rubocop'
s.add_development_dependency 'sqlite3', '~> 1.3.6'
# To install the sqlite3 gem its necessary execute the following command before run bundle
# $ sudo apt-get install -y sqlite3 libsqlite3-dev
s.add_development_dependency 'sqlite3', '~> 1.4'
s.add_development_dependency 'pry-byebug'

s.license = 'MIT'
Expand Down
7 changes: 6 additions & 1 deletion lib/octopus.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
require 'active_record'
require 'active_support/version'
require 'active_support/core_ext/class'
require 'byebug'

require 'yaml'
require 'erb'
Expand Down Expand Up @@ -101,7 +102,7 @@ def self.rails42?
def self.rails50?
ActiveRecord::VERSION::MAJOR == 5 && ActiveRecord::VERSION::MINOR == 0
end

def self.atleast_rails50?
ActiveRecord::VERSION::MAJOR >= 5
end
Expand All @@ -114,6 +115,10 @@ def self.rails52?
ActiveRecord::VERSION::MAJOR == 5 && ActiveRecord::VERSION::MINOR == 2
end

def self.rails60?
ActiveRecord::VERSION::MAJOR > 6 || ActiveRecord::VERSION::MAJOR == 6
end

def self.atleast_rails51?
ActiveRecord::VERSION::MAJOR > 5 || (ActiveRecord::VERSION::MAJOR == 5 && ActiveRecord::VERSION::MINOR >= 1)
end
Expand Down
4 changes: 2 additions & 2 deletions lib/octopus/persistence.rb
Original file line number Diff line number Diff line change
Expand Up @@ -32,8 +32,8 @@ def update_column(*args)
run_on_shard { super }
end

def increment!(*args)
run_on_shard { super }
def increment!(...)
run_on_shard { super(...) }
end

def decrement!(*args)
Expand Down
42 changes: 33 additions & 9 deletions lib/octopus/proxy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -120,10 +120,10 @@ def check_schema_migrations(shard)
def transaction(options = {}, &block)
if !sharded && current_model_replicated?
run_queries_on_shard(Octopus.master_shard) do
select_connection.transaction(options, &block)
select_connection.transaction(**options, &block)
end
else
select_connection.transaction(options, &block)
select_connection.transaction(**options, &block)
end
end

Expand Down Expand Up @@ -192,15 +192,15 @@ def send_queries_to_slave_group(method, *args, &block)
def current_model_replicated?
replicated && (current_model.try(:replicated) || fully_replicated?)
end

def initialize_schema_migrations_table
if Octopus.atleast_rails52?
select_connection.transaction { ActiveRecord::SchemaMigration.create_table }
else
else
select_connection.initialize_schema_migrations_table
end
end

def initialize_metadata_table
select_connection.transaction { ActiveRecord::InternalMetadata.create_table }
end
Expand All @@ -212,17 +212,24 @@ def initialize_metadata_table
# We are planning to migrate to a much stable logic for the Proxy that doesn't require method missing.
def legacy_method_missing_logic(method, *args, &block)
if should_clean_connection_proxy?(method)
conn = select_connection
clean_connection_proxy
conn.send(method, *args, &block)
args, preparable = handle_args(args)

val = preparable.nil? ?
select_connection.send(method, *args, &block) :
select_connection.send(method, *args, **preparable, &block)
elsif should_send_queries_to_shard_slave_group?(method)
send_queries_to_shard_slave_group(method, *args, &block)
elsif should_send_queries_to_slave_group?(method)
send_queries_to_slave_group(method, *args, &block)
elsif should_send_queries_to_replicated_databases?(method)
send_queries_to_selected_slave(method, *args, &block)
else
val = select_connection.send(method, *args, &block)
args, preparable = handle_args(args)

val = preparable.nil? ?
select_connection.send(method, *args, &block) :
select_connection.send(method, *args, **preparable, &block)

if val.instance_of? ActiveRecord::Result
val.current_shard = shard_name
Expand Down Expand Up @@ -309,7 +316,12 @@ def send_queries_to_balancer(balancer, method, *args, &block)
# while preserving `current_shard`
def send_queries_to_slave(slave, method, *args, &block)
using_shard(slave) do
val = select_connection.send(method, *args, &block)
args, preparable = handle_args(args)

val = preparable.nil? ?
select_connection.send(method, *args, &block) :
select_connection.send(method, *args, **preparable, &block)

if val.instance_of? ActiveRecord::Result
val.current_shard = slave
end
Expand Down Expand Up @@ -361,5 +373,17 @@ def using_group(group, &_block)
self.current_group = older_group
end
end

private

def handle_args(args)
return [[], nil] if args.empty?

preparable_args = args.select{ |arg| arg.is_a?(Hash) && arg.key?(:preparable)}
return [args, nil] if preparable_args.empty?

args -= preparable_args
return [args, preparable_args.first]
end
end
end
8 changes: 6 additions & 2 deletions lib/octopus/relation_proxy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,9 @@ def method_missing(method, *args, &block)
if !block && BATCH_METHODS.include?(method)
::Enumerator.new do |yielder|
run_on_shard do
@ar_relation.public_send(method, *args) do |batch_item|
parsed_args = args.empty? ? {} : args.first

@ar_relation.public_send(method, **parsed_args) do |batch_item|
yielder << batch_item
end
end
Expand All @@ -43,7 +45,9 @@ def method_missing(method, *args, &block)
elsif WHERE_CHAIN_METHODS.include?(method)
::Octopus::ScopeProxy.new(@current_shard, run_on_shard { @ar_relation.public_send(method, *args) } )
elsif block
@ar_relation.public_send(method, *args, &block)
parsed_args = args.empty? ? {} : args.first

@ar_relation.public_send(method, **parsed_args, &block)
else
run_on_shard do
if method == :load_records
Expand Down
2 changes: 1 addition & 1 deletion lib/octopus/scope_proxy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ def using(shard)

# Transaction Method send all queries to a specified shard.
def transaction(options = {}, &block)
run_on_shard { klass.transaction(options, &block) }
run_on_shard { klass.transaction(**options, &block) }
end

def connection
Expand Down
2 changes: 1 addition & 1 deletion lib/octopus/version.rb
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
module Octopus
VERSION = '0.10.2'
VERSION = '0.11.2'
end
6 changes: 3 additions & 3 deletions sample_app/config/database.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
# gem install sqlite3-ruby (not necessary on OS X Leopard)
development:
adapter: postgresql
username: postgres
username: postgres
password:
database: octopus_sample_app_development
encoding: unicode
Expand All @@ -13,15 +13,15 @@ development:
# Do not set this db to the same as development or production.
test: &test
adapter: postgresql
username: postgres
username: postgres
password:
database: octopus_sample_app_test
encoding: unicode
host: localhost

production:
adapter: postgresql
username: postgres
username: postgres
password:
database: octopus_sample_app_production
encoding: unicode
Expand Down
4 changes: 3 additions & 1 deletion spec/octopus/migration_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,10 @@

def get_all_versions
if Octopus.atleast_rails52?
schema = ActiveRecord::SchemaMigration
migrations_root = File.expand_path(File.join(File.dirname(__FILE__), '..', 'migrations'))
ActiveRecord::MigrationContext.new(migrations_root).get_all_versions

ActiveRecord::MigrationContext.new(migrations_root, schema).get_all_versions
else
ActiveRecord::Migrator.get_all_versions
end
Expand Down
4 changes: 2 additions & 2 deletions spec/octopus/model_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -309,7 +309,7 @@
if Octopus.atleast_rails52?
expect(User.using(:postgresql_shard).connection.adapter_name).to eq('PostgreSQL')
expect(User.using(:alone_shard).connection.adapter_name).to eq('Mysql2')
else
else
expect(User.using(:postgresql_shard).arel_engine.connection.adapter_name).to eq('PostgreSQL')
expect(User.using(:alone_shard).arel_engine.connection.adapter_name).to eq('Mysql2')
end
Expand Down Expand Up @@ -497,7 +497,7 @@
end

user = User.using(:brazil).where(:name => 'User1').first
expect(user.as_json(:except => [:created_at, :updated_at, :id])).to eq('admin' => nil, 'name' => 'User1', 'number' => nil)
expect(user.as_json(:except => [:created_at, :updated_at, :id, :current_shard])).to eq('admin' => nil, 'name' => 'User1', 'number' => nil)
end

describe 'transaction' do
Expand Down
Loading