Skip to content
This repository was archived by the owner on Feb 7, 2026. It is now read-only.
Open
Show file tree
Hide file tree
Changes from all commits
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
1 change: 1 addition & 0 deletions lib/rails_async_migrations.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@
rescue LoadError
end

require 'rails_async_migrations/define_method_in'
require 'rails_async_migrations/connection/active_record'
require 'rails_async_migrations/config'
require 'rails_async_migrations/migration'
Expand Down
10 changes: 10 additions & 0 deletions lib/rails_async_migrations/define_method_in.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
module RailsAsyncMigrations
module DefineMethodIn
# `klass.define_method(...)` does not work in Ruby 2.4. Work around.
def define_method_in(klass, name, &block)
klass.class_exec {
define_method(name, &block)
}
end
end
end
4 changes: 3 additions & 1 deletion lib/rails_async_migrations/migration/give.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
module RailsAsyncMigrations
module Migration
class Give
include RailsAsyncMigrations::DefineMethodIn

attr_reader :resource_class, :method_name

def initialize(resource_class, method_name)
Expand All @@ -17,7 +19,7 @@ def perform
def restore_original_method
if valid?
Take.new(resource_class, method_name).suspend_take do
resource_class.define_method(method_name, &method_clone)
define_method_in(resource_class, method_name, &method_clone)
end
end
end
Expand Down
6 changes: 4 additions & 2 deletions lib/rails_async_migrations/migration/take.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,8 @@
module RailsAsyncMigrations
module Migration
class Take
include RailsAsyncMigrations::DefineMethodIn

attr_reader :resource_class, :method_name

def initialize(resource_class, method_name)
Expand Down Expand Up @@ -39,15 +41,15 @@ def clone_method_name
end

def preserve_method_logics
resource_class.define_method(clone_method_name, &captured_method)
define_method_in(resource_class, clone_method_name, &captured_method)
end

def captured_method
resource_class.new.method(method_name).clone
end

def overwrite_method
resource_class.define_method(method_name, &overwrite_closure)
define_method_in(resource_class, method_name, &overwrite_closure)
end

def overwrite_closure
Expand Down
4 changes: 3 additions & 1 deletion spec/rails_async_migrations/migration/take_spec.rb
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
RSpec.describe RailsAsyncMigrations::Migration::Take do
include RailsAsyncMigrations::DefineMethodIn

let(:resource_class) { FakeClass }
let(:resource_instance) { resource_class.new }
let(:method) { :free_method }
let(:instance) { described_class.new(resource_class, method) }

let(:change_to_it_passed) { resource_class.define_method(method, -> { 'it passed' }) }
let(:change_to_it_passed) { define_method_in(resource_class, method) { 'it passed' } }

before { change_to_it_passed }
subject { instance.perform }
Expand Down
6 changes: 4 additions & 2 deletions spec/rails_async_migrations/migration_spec.rb
Original file line number Diff line number Diff line change
@@ -1,9 +1,11 @@
RSpec.describe RailsAsyncMigrations::Migration do
include RailsAsyncMigrations::DefineMethodIn

let(:resource_class) { FakeClass }
let(:instance) { resource_class.new }
let(:method) { :free_method }
let(:change_to_true) { resource_class.define_method(method, -> { true }) }
let(:change_to_false) { resource_class.define_method(method, -> { false }) }
let(:change_to_true) { define_method_in(resource_class, method) { true } }
let(:change_to_false) { define_method_in(resource_class, method) { false } }

# we reset the class each time
# as RSpec won't hot-reload it
Expand Down