Skip to content

Instantly share code, notes, and snippets.

@Nondv
Last active January 28, 2019 10:10
Show Gist options
  • Save Nondv/6c3e6b584f43a0837f6b2666b33cb943 to your computer and use it in GitHub Desktop.
Save Nondv/6c3e6b584f43a0837f6b2666b33cb943 to your computer and use it in GitHub Desktop.
RSpec multiple changes
require 'rspec/autorun'
RSpec.describe 'Multiple changes' do
subject do
proc do
a << 123
a << 456
b[:key] = 789
end
end
let!(:a) { [] }
let!(:b) { {} }
let!(:c) { [] }
def expect_multiple_changes(callable, to: [], not_to: [])
message = ->(method, index) { "Matcher: #{method}[#{index}]" }
expectations = to.map.with_index { |matcher, i| [:to, matcher, message[:to, i]] }
expectations += not_to.map.with_index { |matcher, i| [:not_to, matcher, message[:not_to, i]] }
generate_multiple_changes_example(callable, expectations)
.call
end
def generate_multiple_changes_example(result_proc, expectations)
return result_proc if expectations.empty?
method, matcher, error_message = expectations.first
next_result = -> { expect(result_proc).send(method, matcher, error_message) }
generate_multiple_changes_example(next_result, expectations[1..-1])
end
describe '#expect_multiple_changes' do
it 'works but with inconvinient failure messages' do
expect_multiple_changes subject,
to: [change(a, :size).by(2),
change { b.key?(:key) }.from(false).to(true)],
not_to: [change(c, :size)]
end
# failing example
it do
expect_multiple_changes subject,
to: [change(a, :size).by(2),
change(b, :size).by(9999999999)],
not_to: [change(c, :size)]
end
end
describe '#and' do
it 'works but doesnt allow to mix #to with #not_to' do
old_c_size = c.size
# Additionally, text editor auto indentation is going crazy
expect(subject).to change(a, :size).by(2).and \
change { b.key?(:key) }.from(false).to(true)
expect(c.size).to eq(old_c_size)
end
end
describe 'block chaining' do
it 'works but pretty ugly' do
expect {
expect {
expect(subject).to change(a, :size).by(2)
}.to change { b.key?(:key) }.from(false).to(true)
}.not_to change(c, :size)
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment