spec/rspec/its_spec.rb in rspec-its-1.3.1 vs spec/rspec/its_spec.rb in rspec-its-2.0.0
- old
+ new
@@ -1,394 +1,424 @@
+# frozen_string_literal: true
+
require 'spec_helper'
-module RSpec
- describe Its do
- describe "#its" do
- context "with implicit subject" do
- context "preserves described_class" do
- its(:symbol) { expect(described_class).to be Its }
- its([]) { expect(described_class).to be Its }
- end
- end
+RSpec.describe RSpec::Its do
+ context "with implicit subject" do
+ context "preserves described_class" do
+ its(:symbol) { expect(described_class).to be RSpec::Its }
+ its([]) { expect(described_class).to be RSpec::Its }
+ end
+ end
- context "with explicit subject" do
- subject do
- Class.new do
- def initialize
- @call_count = 0
- end
-
- def call_count
- @call_count += 1
- end
- end.new
+ context "with explicit subject" do
+ subject do
+ Class.new do
+ def initialize
+ @call_count = 0
end
- before(:each, :meta) do
- subject.call_count
+ def call_count
+ @call_count += 1
end
+ end.new
+ end
- context "with some metadata" do
- its(:call_count, :meta) { should eq(2) }
- end
+ before(:each, :meta) do
+ subject.call_count
+ end
- context "with a call counter" do
- its(:call_count) { should eq(1) }
- end
+ context "with some metadata" do
+ its(:call_count, :meta) { is_expected.to eq(2) }
+ end
- context "with nil value" do
- subject do
- Class.new do
- def nil_value
- nil
- end
- end.new
- end
- its(:nil_value) { should be_nil }
- end
+ context "with a call counter" do
+ its(:call_count) { is_expected.to eq(1) }
+ end
- context "with nested attributes" do
- subject do
- Class.new do
- def name
- "John"
- end
- end.new
+ context "with nil value" do
+ subject do
+ Class.new do
+ def nil_value
+ nil
end
- its("name") { should eq("John") }
- its("name.size") { should eq(4) }
- if RUBY_VERSION >= "2.4.0"
- its("name.size.class") { should eq(Integer) }
- else
- its("name.size.class") { should eq(Fixnum) }
- end
+ end.new
+ end
- context "using should_not" do
- its("name") { should_not eq("Paul") }
- end
+ its(:nil_value) { is_expected.to be_nil }
+ end
- context "using is_expected" do
- its("name") { is_expected.to eq("John") }
+ context "with nested attributes" do
+ subject do
+ Class.new do
+ def name
+ "John"
end
+ end.new
+ end
- context "using will_not" do
- its("name") { will_not raise_error }
+ its("name") { is_expected.to eq("John") }
+ its("name.size") { is_expected.to eq(4) }
+ its("name.size.class") { is_expected.to eq(Integer) }
+
+ context "using are_expected" do
+ its("name.chars.to_a") { are_expected.to eq(%w[J o h n]) }
+ end
+
+ context "using will_not" do
+ its("name") { will_not raise_error }
+ end
+
+ context "using should" do
+ its("name") { should eq("John") }
+ end
+
+ context "using should_not" do
+ its("name") { should_not eq("Paul") }
+ end
+ end
+
+ context "when it responds to #[]" do
+ subject do
+ Class.new do
+ def [](*objects)
+ objects.map do |object|
+ "#{object.class}: #{object}"
+ end.join("; ")
end
- context "using are_expected" do
- its("name.chars.to_a") { are_expected.to eq(%w[J o h n]) }
+ def name
+ "George"
end
- end
+ end.new
+ end
- context "when it responds to #[]" do
- subject do
- Class.new do
- def [](*objects)
- objects.map do |object|
- "#{object.class}: #{object.to_s}"
- end.join("; ")
- end
+ its([:a]) { is_expected.to eq("Symbol: a") }
+ its(['a']) { is_expected.to eq("String: a") }
+ its([:b, 'c', 4]) { is_expected.to eq("Symbol: b; String: c; Integer: 4") }
+ its(:name) { is_expected.to eq("George") }
- def name
- "George"
- end
- end.new
+ context "when referring to an attribute that doesn't exist" do
+ context "it raises an error" do
+ its(:age) do
+ expect do
+ is_expected.to eq(64)
+ end.to raise_error(NoMethodError)
end
- its([:a]) { should eq("Symbol: a") }
- its(['a']) { should eq("String: a") }
- if RUBY_VERSION >= "2.4.0"
- its([:b, 'c', 4]) { should eq("Symbol: b; String: c; Integer: 4") }
- else
- its([:b, 'c', 4]) { should eq("Symbol: b; String: c; Fixnum: 4") }
- end
- its(:name) { should eq("George") }
- context "when referring to an attribute that doesn't exist" do
- context "it raises an error" do
- its(:age) do
- expect do
- should eq(64)
- end.to raise_error(NoMethodError)
- end
- context "using will" do
- its(:age) { will raise_error(NoMethodError) }
- end
- end
+ context "using will" do
+ its(:age) { will raise_error(NoMethodError) }
end
+ end
+ end
- context "when it's a hash" do
- subject { {:a => {:deep => {:key => "value"}}} }
+ context "when it's a hash" do
+ subject { { a: { deep: { key: "value" } } } }
- its([:a]) { should eq({:deep => {:key => "value"}}) }
- its([:a, :deep]) { should eq({:key => "value"}) }
- its([:a, :deep, :key]) { should eq("value") }
+ its([:a]) { is_expected.to eq({ deep: { key: "value" } }) }
+ its(%i[a deep]) { is_expected.to eq({ key: "value" }) }
+ its(%i[a deep key]) { is_expected.to eq("value") }
- context "when referring to a key that doesn't exist" do
- its([:not_here]) { should be_nil }
- its([:a, :ghost]) { should be_nil }
- its([:deep, :ghost]) { expect { should eq("missing") }.to raise_error(NoMethodError) }
+ context "when referring to a key that doesn't exist" do
+ its([:not_here]) { is_expected.to be_nil }
+ its(%i[a ghost]) { are_expected.to be_nil }
+ its(%i[deep ghost]) { expect { is_expected.to eq("missing") }.to raise_error(NoMethodError) }
- context "using will" do
- its([:deep, :ghost]) { will raise_error(NoMethodError) }
- end
- end
+ context "using will" do
+ its(%i[deep ghost]) { will raise_error(NoMethodError) }
end
end
+ end
+ end
- context "when it does not respond to #[]" do
- subject { Object.new }
+ context "when it does not respond to #[]" do
+ subject { Object.new }
- context "it raises an error" do
- its([:a]) do
- expect do
- should eq("Symbol: a")
- end.to raise_error(NoMethodError)
- end
+ context "it raises an error" do
+ its([:a]) do
+ expect { is_expected.to eq("Symbol: a") }.to raise_error(NoMethodError)
+ end
- context "using will" do
- its([:a]) { will raise_error(NoMethodError) }
- end
- end
+ context "using will" do
+ its([:a]) { will raise_error(NoMethodError) }
end
+ end
+ end
- context "calling and overriding super" do
- it "calls to the subject defined in the parent group" do
- group = RSpec::Core::ExampleGroup.describe(Array) do
- subject { [1, 'a'] }
+ context "calling and overriding super" do
+ it "calls to the subject defined in the parent group" do
+ group = RSpec::Core::ExampleGroup.describe(Array) do
+ subject { [1, 'a'] }
- its(:last) { should eq("a") }
+ its(:last) { is_expected.to eq("a") }
- describe '.first' do
- def subject;
- super().first;
- end
-
- its(:next) { should eq(2) }
- end
+ describe '.first' do
+ def subject
+ super.first
end
- expect(group.run(NullFormatter.new)).to be_truthy
+ its(:next) { is_expected.to eq(2) }
end
end
- context "with nil subject" do
- subject do
- Class.new do
- def initialize
- @counter = -1
- end
+ expect(group.run(NullFormatter.new)).to be_truthy
+ end
+ end
- def nil_if_first_time
- @counter += 1
- @counter == 0 ? nil : true
- end
- end.new
+ context "with nil subject" do
+ subject do
+ Class.new do
+ def initialize
+ @counter = -1
end
- its(:nil_if_first_time) { should be(nil) }
- end
- context "with false subject" do
- subject do
- Class.new do
- def initialize
- @counter = -1
- end
-
- def false_if_first_time
- @counter += 1
- @counter > 0
- end
- end.new
+ def nil_if_first_time
+ @counter += 1
+ @counter == 0 ? nil : true
end
- its(:false_if_first_time) { should be(false) }
- end
+ end.new
+ end
- describe 'accessing `subject` in `before` and `let`' do
- subject { 'my subject' }
- before { @subject_in_before = subject }
- let(:subject_in_let) { subject }
- let!(:eager_loaded_subject_in_let) { subject }
+ its(:nil_if_first_time) { is_expected.to be(nil) }
+ end
- # These examples read weird, because we're actually
- # specifying the behaviour of `its` itself
- its(nil) { expect(subject).to eq('my subject') }
- its(nil) { expect(@subject_in_before).to eq('my subject') }
- its(nil) { expect(subject_in_let).to eq('my subject') }
- its(nil) { expect(eager_loaded_subject_in_let).to eq('my subject') }
- end
+ context "with false subject" do
+ subject do
+ Class.new do
+ def initialize
+ @counter = -1
+ end
- describe "in shared_context" do
- shared_context "shared stuff" do
- subject { Array }
- its(:name) { should eq "Array" }
+ def false_if_first_time
+ @counter += 1
+ @counter > 0
end
+ end.new
+ end
- include_context "shared stuff"
- end
+ its(:false_if_first_time) { is_expected.to be(false) }
+ end
- describe "when extending SharedContext" do
- it 'works with an implicit subject' do
- shared = Module.new do
- extend RSpec::SharedContext
- its(:size) { should eq 0 }
- end
- group = RSpec::Core::ExampleGroup.describe(Array) do
- include shared
- end
+ describe 'accessing `subject` in `before` and `let`' do
+ subject { 'my subject' }
- group.run(NullFormatter.new)
+ before { @subject_in_before = subject }
- result = group.children.first.examples.first.execution_result
- # Following conditional needed to work across mix of RSpec and ruby versions without warning
- status = result.respond_to?(:status) ? result.status : result[:status].to_sym
- expect(status).to eq(:passed)
- end
- end
- end
- context "with metadata" do
- context "preserves access to metadata that doesn't end in hash" do
- its([], :foo) do |example|
- expect(example.metadata[:foo]).to be(true)
- end
- end
- context "preserves access to metadata that ends in hash" do
- its([], :foo, :bar => 17) do |example|
- expect(example.metadata[:foo]).to be(true)
- expect(example.metadata[:bar]).to be(17)
- end
- end
- end
+ let(:subject_in_let) { subject }
+ let!(:eager_loaded_subject_in_let) { subject }
- context "when expecting errors" do
- subject do
- Class.new do
- def good; end
+ # These examples read weird, because we're actually
+ # specifying the behaviour of `its` itself
+ its(nil) { expect(subject).to eq('my subject') }
+ its(nil) { expect(@subject_in_before).to eq('my subject') }
+ its(nil) { expect(subject_in_let).to eq('my subject') }
+ its(nil) { expect(eager_loaded_subject_in_let).to eq('my subject') }
+ end
- def bad
- raise ArgumentError, "message"
- end
- end.new
- end
+ describe "in shared_context" do
+ shared_context "shared stuff" do
+ subject { Array }
- its(:good) { will_not raise_error }
- its(:bad) { will raise_error(ArgumentError) }
- its(:bad) { will raise_error("message") }
- its(:bad) { will raise_error(ArgumentError, "message") }
+ its(:name) { is_expected.to eq "Array" }
end
- context "when expecting throws" do
- subject do
- Class.new do
- def good; end
+ include_context "shared stuff"
+ end
- def bad
- throw :abort, "message"
- end
- end.new
+ describe "when extending SharedContext" do
+ it 'works with an implicit subject' do
+ shared = Module.new do
+ extend RSpec::SharedContext
+ its(:size) { is_expected.to eq 0 }
end
- its(:good) { will_not throw_symbol }
- its(:bad) { will throw_symbol }
- its(:bad) { will throw_symbol(:abort) }
- its(:bad) { will throw_symbol(:abort, "message") }
+ group = RSpec::Core::ExampleGroup.describe(Array) do
+ include shared
+ end
+
+ group.run(NullFormatter.new)
+
+ result = group.children.first.examples.first.execution_result
+ # Following conditional needed to work across mix of RSpec and ruby versions without warning
+ status = result.respond_to?(:status) ? result.status : result[:status].to_sym
+ expect(status).to eq(:passed)
end
+ end
+ end
- context "with change observation" do
- subject do
- Class.new do
- attr_reader :count
+ context "with metadata" do
+ context "preserves access to metadata that doesn't end in hash" do
+ its([], :foo) do |example|
+ expect(example.metadata[:foo]).to be(true)
+ end
+ end
- def initialize
- @count = 0
- end
+ context "preserves access to metadata that ends in hash" do
+ its([], :foo, bar: 17) do |example|
+ expect(example.metadata[:foo]).to be(true)
+ expect(example.metadata[:bar]).to be(17)
+ end
+ end
+ end
- def increment
- @count += 1
- end
+ context "when expecting errors" do
+ subject do
+ Class.new do
+ def good; end
- def noop; end
- end.new
+ def bad
+ raise ArgumentError, "message"
end
+ end.new
+ end
- its(:increment) { will change { subject.count }.by(1) }
- its(:increment) { will change { subject.count }.from(0) }
- its(:increment) { will change { subject.count }.from(0).to(1) }
- its(:increment) { will change { subject.count }.by_at_least(1) }
- its(:increment) { will change { subject.count }.by_at_most(1) }
+ its(:good) { will_not raise_error }
+ its(:bad) { will raise_error(ArgumentError) }
+ its(:bad) { will raise_error("message") }
+ its(:bad) { will raise_error(ArgumentError, "message") }
+ end
- its(:noop) { will_not change { subject.count } }
- its(:noop) { will_not change { subject.count }.from(0) }
+ context "when expecting throws" do
+ subject do
+ Class.new do
+ def good; end
- its(:increment) do
- expect { will_not change { subject.count }.by(0) }.to \
- raise_error(NotImplementedError, '`expect { }.not_to change { }.by()` is not supported')
+ def bad
+ throw :abort, "message"
end
+ end.new
+ end
- its(:increment) do
- expect { will_not change { subject.count }.by_at_least(2) }.to \
- raise_error(NotImplementedError, '`expect { }.not_to change { }.by_at_least()` is not supported')
+ its(:good) { will_not throw_symbol }
+ its(:bad) { will throw_symbol }
+ its(:bad) { will throw_symbol(:abort) }
+ its(:bad) { will throw_symbol(:abort, "message") }
+ end
+
+ context "with change observation" do
+ subject do
+ Class.new do
+ attr_reader :count
+
+ def initialize
+ @count = 0
end
- its(:increment) do
- expect { will_not change { subject.count }.by_at_most(3) }.to \
- raise_error(NotImplementedError, '`expect { }.not_to change { }.by_at_most()` is not supported')
+ def increment
+ @count += 1
end
- end
- context "with output capture" do
- subject do
- Class.new do
- def stdout
- print "some output"
- end
+ def noop; end
+ end.new
+ end
- def stderr
- $stderr.print "some error"
- end
+ its(:increment) { will change { subject.count }.by(1) }
+ its(:increment) { will change { subject.count }.from(0) }
+ its(:increment) { will change { subject.count }.from(0).to(1) }
+ its(:increment) { will change { subject.count }.by_at_least(1) }
+ its(:increment) { will change { subject.count }.by_at_most(1) }
- def noop; end
- end.new
- end
+ its(:noop) { will_not(change { subject.count }) }
+ its(:noop) { will_not change { subject.count }.from(0) }
- its(:stdout) { will output("some output").to_stdout }
- its(:stderr) { will output("some error").to_stderr }
+ its(:increment) do
+ expect { will_not change { subject.count }.by(0) }.to \
+ raise_error(NotImplementedError, '`expect { }.not_to change { }.by()` is not supported')
+ end
- its(:noop) { will_not output("some error").to_stderr }
- its(:noop) { will_not output("some output").to_stdout }
- end
+ its(:increment) do
+ expect { will_not change { subject.count }.by_at_least(2) }.to \
+ raise_error(NotImplementedError, '`expect { }.not_to change { }.by_at_least()` is not supported')
+ end
- context "#will with non block expectations" do
- subject do
- Class.new do
- def terminator
- "back"
- end
- end.new
+ its(:increment) do
+ expect { will_not change { subject.count }.by_at_most(3) }.to \
+ raise_error(NotImplementedError, '`expect { }.not_to change { }.by_at_most()` is not supported')
+ end
+ end
+
+ context "with output capture" do
+ subject do
+ Class.new do
+ def stdout
+ print "some output"
end
- its(:terminator) do
- expect { will be("back") }.to \
- raise_error(ArgumentError, '`will` only supports block expectations')
+ def stderr
+ $stderr.print "some error"
end
- its(:terminator) do
- expect { will_not be("back") }.to \
- raise_error(ArgumentError, '`will_not` only supports block expectations')
+ def noop; end
+ end.new
+ end
+
+ its(:stdout) { will output("some output").to_stdout }
+ its(:stderr) { will output("some error").to_stderr }
+
+ its(:noop) { will_not output("some error").to_stderr }
+ its(:noop) { will_not output("some output").to_stdout }
+ end
+
+ context "#will with non block expectations" do
+ subject do
+ Class.new do
+ def terminator
+ "back"
end
- end
+ end.new
+ end
- context "when example is redefined" do
- subject do
- Class.new do
- def will_still_work; true; end
- end.new
+ its(:terminator) do
+ expect { will be("back") }.to \
+ raise_error(ArgumentError, '`will` only supports block expectations')
+ end
+
+ its(:terminator) do
+ expect { will_not be("back") }.to \
+ raise_error(ArgumentError, '`will_not` only supports block expectations')
+ end
+ end
+
+ context "when example is redefined" do
+ subject do
+ Class.new do
+ def will_still_work
+ true
end
+ end.new
+ end
- def self.example(*_args)
- raise
+ def self.example(*_args)
+ raise
+ end
+
+ its(:will_still_work) { is_expected.to be true }
+ end
+
+ context "with private method" do
+ subject(:klass) do
+ Class.new do
+ def name
+ private_name
end
- its(:will_still_work) { is_expected.to be true }
+ private
+
+ def private_name
+ "John"
+ end
+ end.new
+ end
+
+ context "when referring indirectly" do
+ its(:name) { is_expected.to eq "John" }
+ end
+
+ context "when attempting to refer directly" do
+ context "it raises an error" do
+ its(:private_name) do
+ expect { is_expected.to eq("John") }.to raise_error(NoMethodError)
+ end
end
end
end
end