[macruby-changes] [3870] MacRuby/trunk/mspec
source_changes at macosforge.org
source_changes at macosforge.org
Sun Mar 28 10:00:15 PDT 2010
Revision: 3870
http://trac.macosforge.org/projects/ruby/changeset/3870
Author: eloy.de.enige at gmail.com
Date: 2010-03-28 10:00:14 -0700 (Sun, 28 Mar 2010)
Log Message:
-----------
Update MSpec to 88d85da83cbf2e595ec956651520ce119d429e8f
Modified Paths:
--------------
MacRuby/trunk/mspec/Rakefile
MacRuby/trunk/mspec/lib/mspec/commands/mspec-ci.rb
MacRuby/trunk/mspec/lib/mspec/guards/conflict.rb
MacRuby/trunk/mspec/lib/mspec/guards/guard.rb
MacRuby/trunk/mspec/lib/mspec/guards/platform.rb
MacRuby/trunk/mspec/lib/mspec/guards.rb
MacRuby/trunk/mspec/lib/mspec/helpers/environment.rb
MacRuby/trunk/mspec/lib/mspec/helpers/fixture.rb
MacRuby/trunk/mspec/lib/mspec/helpers/ruby_exe.rb
MacRuby/trunk/mspec/lib/mspec/helpers.rb
MacRuby/trunk/mspec/lib/mspec/matchers/equal_utf16.rb
MacRuby/trunk/mspec/lib/mspec/matchers.rb
MacRuby/trunk/mspec/lib/mspec/mocks/mock.rb
MacRuby/trunk/mspec/lib/mspec/runner/context.rb
MacRuby/trunk/mspec/lib/mspec/runner/mspec.rb
MacRuby/trunk/mspec/lib/mspec/version.rb
MacRuby/trunk/mspec/spec/commands/mspec_ci_spec.rb
MacRuby/trunk/mspec/spec/guards/conflict_spec.rb
MacRuby/trunk/mspec/spec/guards/guard_spec.rb
MacRuby/trunk/mspec/spec/helpers/environment_spec.rb
MacRuby/trunk/mspec/spec/helpers/fixture_spec.rb
MacRuby/trunk/mspec/spec/helpers/ruby_exe_spec.rb
MacRuby/trunk/mspec/spec/matchers/equal_utf16_spec.rb
MacRuby/trunk/mspec/spec/mocks/mock_spec.rb
MacRuby/trunk/mspec/spec/runner/context_spec.rb
MacRuby/trunk/mspec/spec/runner/example_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/dotted_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/file_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/html_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/method_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/spinner_spec.rb
MacRuby/trunk/mspec/spec/runner/formatters/unit_spec.rb
MacRuby/trunk/mspec/spec/runner/shared_spec.rb
MacRuby/trunk/mspec/upstream
Added Paths:
-----------
MacRuby/trunk/mspec/lib/mspec/guards/feature.rb
MacRuby/trunk/mspec/lib/mspec/guards/specified.rb
MacRuby/trunk/mspec/lib/mspec/helpers/encode.rb
MacRuby/trunk/mspec/lib/mspec/helpers/fmode.rb
MacRuby/trunk/mspec/lib/mspec/matchers/have_data.rb
MacRuby/trunk/mspec/spec/guards/feature_spec.rb
MacRuby/trunk/mspec/spec/guards/specified_spec.rb
MacRuby/trunk/mspec/spec/helpers/encode_spec.rb
MacRuby/trunk/mspec/spec/helpers/fmode_spec.rb
MacRuby/trunk/mspec/spec/matchers/have_data_spec.rb
Modified: MacRuby/trunk/mspec/Rakefile
===================================================================
--- MacRuby/trunk/mspec/Rakefile 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/Rakefile 2010-03-28 17:00:14 UTC (rev 3870)
@@ -18,7 +18,7 @@
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
s.authors = ["Brian Ford"]
- s.date = %q{2010-01-05}
+ s.date = %q{2010-02-08}
s.email = %q{bford at engineyard.com}
s.has_rdoc = true
s.extra_rdoc_files = %w[ README LICENSE ]
Modified: MacRuby/trunk/mspec/lib/mspec/commands/mspec-ci.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/commands/mspec-ci.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/commands/mspec-ci.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -66,8 +66,11 @@
def run
MSpec.register_tags_patterns config[:tags_patterns]
MSpec.register_files @files
- filter = TagFilter.new(:exclude,
- "fails", "critical", "unstable", "incomplete", "unsupported")
+
+ tags = ["fails", "critical", "unstable", "incomplete", "unsupported"]
+ tags += Array(config[:ci_xtags])
+
+ filter = TagFilter.new(:exclude, *tags)
filter.register
MSpec.process
Modified: MacRuby/trunk/mspec/lib/mspec/guards/conflict.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards/conflict.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/guards/conflict.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -2,12 +2,17 @@
class ConflictsGuard < SpecGuard
def match?
- constants = Object.constants
- @args.any? { |mod| constants.include? mod.to_s }
+ # Always convert constants to symbols regardless of version.
+ constants = Object.constants.map { |x| x.to_sym }
+ @args.any? { |mod| constants.include? mod }
end
end
class Object
+ # In some cases, libraries will modify another Ruby method's
+ # behavior. The specs for the method's behavior will then fail
+ # if that library is loaded. This guard will not run if any of
+ # the specified constants exist in Object.constants.
def conflicts_with(*modules)
g = ConflictsGuard.new(*modules)
g.name = :conflicts_with
Added: MacRuby/trunk/mspec/lib/mspec/guards/feature.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards/feature.rb (rev 0)
+++ MacRuby/trunk/mspec/lib/mspec/guards/feature.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,47 @@
+require 'mspec/guards/guard'
+
+class FeatureGuard < SpecGuard
+ def self.enabled?(*features)
+ new(*features).match?
+ end
+
+ def match?
+ @parameters.all? { |f| MSpec.feature_enabled? f }
+ end
+end
+
+class Object
+ # Provides better documentation in the specs by
+ # naming sets of features that work together as
+ # a whole. Examples include :encoding, :fiber,
+ # :continuation, :fork.
+ #
+ # Usage example:
+ #
+ # with_feature :encoding do
+ # # specs for a method that provides aspects
+ # # of the encoding feature
+ # end
+ #
+ # Multiple features must all be enabled for the
+ # guard to run:
+ #
+ # with_feature :one, :two do
+ # # these specs will run if features :one AND
+ # # :two are enabled.
+ # end
+ #
+ # The implementation must explicitly enable a feature
+ # by adding code like the following to the .mspec
+ # configuration file:
+ #
+ # MSpec.enable_feature :encoding
+ #
+ def with_feature(*features)
+ g = FeatureGuard.new(*features)
+ g.name = :with_feature
+ yield if g.yield?
+ ensure
+ g.unregister
+ end
+end
Modified: MacRuby/trunk/mspec/lib/mspec/guards/guard.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards/guard.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/guards/guard.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,6 +1,8 @@
require 'mspec/runner/mspec'
require 'mspec/runner/actions/tally'
+require 'rbconfig'
+
class SpecGuard
def self.report
@report ||= Hash.new { |h,k| h[k] = [] }
@@ -56,10 +58,6 @@
version.split('.')[0,n].join('.')
end
- def self.windows?(key = RUBY_PLATFORM)
- !!key.match(/(mswin|mingw)/)
- end
-
attr_accessor :name, :parameters
def initialize(*args)
@@ -136,7 +134,7 @@
end
def windows?(sym, key)
- sym == :windows && SpecGuard.windows?(key)
+ sym == :windows && !key.match(/(mswin|mingw)/).nil?
end
def platform?(*args)
@@ -154,7 +152,6 @@
end
def os?(*oses)
- require 'rbconfig'
oses.any? do |os|
host_os = Config::CONFIG['host_os'] || RUBY_PLATFORM
host_os.downcase!
Modified: MacRuby/trunk/mspec/lib/mspec/guards/platform.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards/platform.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/guards/platform.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,6 +1,10 @@
require 'mspec/guards/guard'
class PlatformGuard < SpecGuard
+ def self.windows?
+ PlatformGuard.new(:os => :windows).match?
+ end
+
def initialize(*args)
if args.last.is_a?(Hash)
@options, @platforms = args.last, args[0..-2]
Added: MacRuby/trunk/mspec/lib/mspec/guards/specified.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards/specified.rb (rev 0)
+++ MacRuby/trunk/mspec/lib/mspec/guards/specified.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,66 @@
+require 'mspec/guards/guard'
+
+class UnspecifiedGuard < SpecGuard
+ def match?
+ not standard?
+ end
+end
+
+class SpecifiedOnGuard < SpecGuard
+ def match?
+ if @args.include? :ruby
+ raise Exception, "improper use of specified_on guard"
+ end
+ not standard? and implementation?(*@args)
+ end
+end
+
+class Object
+ # This guard wraps one or more #specified_on guards to group them and
+ # document the specs. The purpose of the guard is for situations where MRI
+ # either does not specify Ruby behavior or where MRI's behavior is all but
+ # impossible to spec, for example due to relying on platform-specific
+ # behavior that is not easily testable from Ruby code. In such cases, it
+ # may be desirable for implementations to explore a specified set of
+ # behaviors that are explicitly documented in the specs.
+ #
+ # unspecified do
+ # specified_on :rubinius, :ironruby do
+ # it "returns true when passed :foo" do
+ # # ...
+ # end
+ #
+ # it "returns false when passed :bar" do
+ # # ...
+ # end
+ # end
+ #
+ # specified_on :jruby do
+ # it "returns true when passed :bar" do
+ # # ...
+ # end
+ # end
+ # end
+ #
+ # Note that these guards do not change the policy of the #compliant_on,
+ # #not_compliant_on, #deviates_on, #extended_on, and #not_supported_on
+ # guards.
+ #
+ def unspecified
+ g = UnspecifiedGuard.new
+ g.name = :unspecified
+ yield if g.yield?
+ ensure
+ g.unregister
+ end
+
+ # This guard wraps specs for one or more particular implementations. See the
+ # #unspecified guard for further documentation.
+ def specified_on(*args)
+ g = SpecifiedOnGuard.new(*args)
+ g.name = :specified_on
+ yield if g.yield?
+ ensure
+ g.unregister
+ end
+end
Modified: MacRuby/trunk/mspec/lib/mspec/guards.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/guards.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/guards.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -5,11 +5,13 @@
require 'mspec/guards/conflict'
require 'mspec/guards/endian'
require 'mspec/guards/extensions'
+require 'mspec/guards/feature'
require 'mspec/guards/guard'
require 'mspec/guards/noncompliance'
require 'mspec/guards/platform'
require 'mspec/guards/quarantine'
require 'mspec/guards/runner'
+require 'mspec/guards/specified'
require 'mspec/guards/support'
require 'mspec/guards/superuser'
require 'mspec/guards/tty'
Added: MacRuby/trunk/mspec/lib/mspec/helpers/encode.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers/encode.rb (rev 0)
+++ MacRuby/trunk/mspec/lib/mspec/helpers/encode.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,21 @@
+require 'mspec/guards/feature'
+
+class Object
+ # Helper to handle String encodings. The +str+ and +encoding+ parameters
+ # must be Strings and an ArgumentError will be raised if not. This ensures
+ # that the encode() helper can be used regardless of whether Encoding exits.
+ # The helper is a no-op (i.e. passes through +str+ unmodified) if the
+ # :encoding feature is not enabled (see with_feature guard). If the
+ # :encoding feature is enabled, +str+.force_encoding(+encoding+) is called.
+ def encode(str, encoding)
+ unless str.is_a? String and encoding.is_a? String
+ raise ArgumentError, "encoding name must be a String"
+ end
+
+ if FeatureGuard.enabled? :encoding
+ str.force_encoding encoding
+ end
+
+ str
+ end
+end
Modified: MacRuby/trunk/mspec/lib/mspec/helpers/environment.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers/environment.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/helpers/environment.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -3,7 +3,7 @@
class Object
def env
env = ""
- if SpecGuard.windows?
+ if PlatformGuard.windows?
env = Hash[*`cmd.exe /C set`.split("\n").map { |e| e.split("=", 2) }.flatten]
else
env = Hash[*`env`.split("\n").map { |e| e.split("=", 2) }.flatten]
@@ -17,7 +17,7 @@
def username
user = ""
- if SpecGuard.windows?
+ if PlatformGuard.windows?
user = windows_env_echo('USERNAME')
else
user = `whoami`.strip
@@ -26,7 +26,7 @@
end
def home_directory
- return ENV['HOME'] unless SpecGuard.windows?
+ return ENV['HOME'] unless PlatformGuard.windows?
windows_env_echo('HOMEDRIVE') + windows_env_echo('HOMEPATH')
end
end
Modified: MacRuby/trunk/mspec/lib/mspec/helpers/fixture.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers/fixture.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/helpers/fixture.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -15,6 +15,7 @@
def fixture(dir, *args)
path = File.dirname(dir)
path = path[0..-7] if path[-7..-1] == "/shared"
- File.expand_path(File.join(path, "fixtures", args))
+ dir = path[-9..-1] == "/fixtures" ? "" : "fixtures"
+ File.expand_path(File.join(path, dir, args))
end
end
Added: MacRuby/trunk/mspec/lib/mspec/helpers/fmode.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers/fmode.rb (rev 0)
+++ MacRuby/trunk/mspec/lib/mspec/helpers/fmode.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,15 @@
+require 'mspec/guards/feature'
+
+class Object
+ # This helper simplifies passing file access modes regardless of
+ # whether the :encoding feature is enabled. Only the access specifier
+ # itself will be returned if :encoding is not enabled. Otherwise,
+ # the full mode string will be returned (i.e. the helper is a no-op).
+ def fmode(mode)
+ if FeatureGuard.enabled? :encoding
+ mode
+ else
+ mode.split(':').first
+ end
+ end
+end
Modified: MacRuby/trunk/mspec/lib/mspec/helpers/ruby_exe.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers/ruby_exe.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/helpers/ruby_exe.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,5 +1,5 @@
require 'mspec/utils/ruby_name'
-require 'mspec/guards/guard'
+require 'mspec/guards/platform'
# The ruby_exe helper provides a wrapper for invoking the
# same Ruby interpreter as the one running the specs and
@@ -99,7 +99,7 @@
# It has been reported that File.executable is not reliable
# on Windows platforms (see commit 56bc555c). So, we check the
# platform.
- if File.exists?(exe) and (SpecGuard.windows? or File.executable?(exe))
+ if File.exists?(exe) and (PlatformGuard.windows? or File.executable?(exe))
return cmd
end
end
Modified: MacRuby/trunk/mspec/lib/mspec/helpers.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/helpers.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/helpers.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -2,10 +2,12 @@
require 'mspec/helpers/bignum'
require 'mspec/helpers/const_lookup'
require 'mspec/helpers/ducktype'
+require 'mspec/helpers/encode'
require 'mspec/helpers/enumerator_class'
require 'mspec/helpers/environment'
require 'mspec/helpers/fixture'
require 'mspec/helpers/flunk'
+require 'mspec/helpers/fmode'
require 'mspec/helpers/fs'
require 'mspec/helpers/hash'
require 'mspec/helpers/infinity'
Modified: MacRuby/trunk/mspec/lib/mspec/matchers/equal_utf16.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/matchers/equal_utf16.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/matchers/equal_utf16.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,19 +1,17 @@
+require 'mspec/helpers/encode'
+
class EqualUtf16Matcher
def initialize(expected)
- @expected = expected
+ @expected = Array(expected).map { |x| encode x, "binary" }
end
def matches?(actual)
- @actual = actual
+ @actual = Array(actual).map { |x| encode x, "binary" }
@actual == @expected || @actual == expected_swapped
end
def expected_swapped
- if @expected.respond_to?(:to_str)
- @expected_swapped ||= @expected.to_str.gsub(/(.)(.)/, '\2\1')
- else
- @expected_swapped ||= @expected.collect { |s| s.to_str.gsub(/(.)(.)/, '\2\1') }
- end
+ @expected_swapped ||= @expected.map { |x| x.to_str.gsub(/(.)(.)/, '\2\1') }
end
def failure_message
Added: MacRuby/trunk/mspec/lib/mspec/matchers/have_data.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/matchers/have_data.rb (rev 0)
+++ MacRuby/trunk/mspec/lib/mspec/matchers/have_data.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,48 @@
+require 'mspec/guards/feature'
+require 'mspec/helpers/fmode'
+
+class HaveDataMatcher
+ def initialize(data)
+ @data = data
+ end
+
+ def matches?(name)
+ @name = name
+
+ if FeatureGuard.enabled? :encoding
+ size = @data.bytesize
+ else
+ size = @data.size
+ end
+
+ File.open @name, fmode("rb:binary") do |f|
+ return f.read(size) == @data
+ end
+ end
+
+ def failure_message
+ ["Expected #{@name}",
+ "to have data #{@data.pretty_inspect}"]
+ end
+
+ def negative_failure_message
+ ["Expected #{@name}",
+ "not to have data #{@data.pretty_inspect}"]
+ end
+end
+
+class Object
+ # Opens a file specified by the string the matcher is called on
+ # and compares the +data+ passed to the matcher with the contents
+ # of the file. Expects to match the first N bytes of the file
+ # with +data+. For example, suppose @name is the name of a file:
+ #
+ # @name.should have_data("123")
+ #
+ # passes if the file @name has "123" as the first 3 bytes. The
+ # file can contain more bytes than +data+. The extra bytes do not
+ # affect the result.
+ def have_data(data)
+ HaveDataMatcher.new(data)
+ end
+end
Modified: MacRuby/trunk/mspec/lib/mspec/matchers.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/matchers.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/matchers.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -14,6 +14,7 @@
require 'mspec/matchers/equal_utf16'
require 'mspec/matchers/have_constant'
require 'mspec/matchers/have_class_variable'
+require 'mspec/matchers/have_data'
require 'mspec/matchers/have_instance_method'
require 'mspec/matchers/have_instance_variable'
require 'mspec/matchers/have_method'
Modified: MacRuby/trunk/mspec/lib/mspec/mocks/mock.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/mocks/mock.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/mocks/mock.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -38,6 +38,11 @@
has_key?(mocks.keys, sym) or has_key?(stubs.keys, sym)
end
+ def self.clear_replaced(key)
+ mocks.delete key
+ stubs.delete key
+ end
+
def self.mock_respond_to?(obj, sym)
name = replaced_name(obj, :respond_to?)
if replaced? name
@@ -176,7 +181,10 @@
else
meta.__send__ :remove_method, sym
end
+
+ clear_replaced key
end
+ ensure
reset
end
end
Modified: MacRuby/trunk/mspec/lib/mspec/runner/context.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/runner/context.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/runner/context.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -37,6 +37,12 @@
@expectation_missing = Proc.new { raise SpecExpectationNotFoundError }
end
+ # Remove caching when a ContextState is dup'd for shared specs.
+ def initialize_copy(other)
+ @pre = {}
+ @post = {}
+ end
+
# Returns true if this is a shared +ContextState+. Essentially, when
# created with: describe "Something", :shared => true { ... }
def shared?
@@ -47,28 +53,51 @@
# the +parents+ list.
def parent=(parent)
@description = nil
- @parent = parent
- parent.child self if parent and not shared?
- state = parent
- while state
- parents.unshift state
- state = state.parent
+ if shared?
+ @parent = nil
+ else
+ @parent = parent
+ parent.child self if parent
+
+ @parents = [self]
+ state = parent
+ while state
+ @parents.unshift state
+ state = state.parent
+ end
end
end
- def replace_parent(parent)
- @parents[0] = parent
-
- children.each { |child| child.replace_parent parent }
- end
-
# Add the ContextState instance +child+ to the list of nested
# describe blocks.
def child(child)
@children << child
end
+ # Adds a nested ContextState in a shared ContextState to a containing
+ # ContextState.
+ #
+ # Normal adoption is from the parent's perspective. But adopt is a good
+ # verb and it's reasonable for the child to adopt the parent as well. In
+ # this case, manipulating state from inside the child avoids needlessly
+ # exposing the state to manipulate it externally in the dup. (See
+ # #it_should_behave_like)
+ def adopt(parent)
+ self.parent = parent
+
+ @examples = @examples.map do |example|
+ example = example.dup
+ example.context = self
+ example
+ end
+
+ children = @children
+ @children = []
+
+ children.each { |child| child.dup.adopt self }
+ end
+
# Returns a list of all before(+what+) blocks from self and any parents.
def pre(what)
@pre[what] ||= parents.inject([]) { |l, s| l.push(*s.before(what)) }
@@ -113,7 +142,7 @@
# Returns a description string generated from self and all parents
def description
- @description ||= parents.map { |p| p.to_s }.join(" ")
+ @description ||= parents.map { |p| p.to_s }.compact.join(" ")
end
# Injects the before/after blocks and examples from the shared
@@ -125,18 +154,19 @@
raise Exception, "Unable to find shared 'describe' for #{desc}"
end
- state.examples.each { |ex| ex.context = self; @examples << ex }
state.before(:all).each { |b| before :all, &b }
state.before(:each).each { |b| before :each, &b }
state.after(:each).each { |b| after :each, &b }
state.after(:all).each { |b| after :all, &b }
- # There is a potential race here if mspec ever implements concurrency
- # in process. Right now, the only way to run specs concurrently is
- # with multiple processes, so we ignore this for the sake of simplicity.
+ state.examples.each do |example|
+ example = example.dup
+ example.context = self
+ @examples << example
+ end
+
state.children.each do |child|
- child.replace_parent self
- @children << child
+ child.dup.adopt self
end
end
Modified: MacRuby/trunk/mspec/lib/mspec/runner/mspec.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/runner/mspec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/runner/mspec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -21,6 +21,7 @@
@modes = []
@shared = {}
@guarded = []
+ @features = {}
@exception = nil
@randomize = nil
@expectation = nil
@@ -162,6 +163,18 @@
retrieve(:modes).include? mode
end
+ def self.enable_feature(feature)
+ retrieve(:features)[feature] = true
+ end
+
+ def self.disable_feature(feature)
+ retrieve(:features)[feature] = false
+ end
+
+ def self.feature_enabled?(feature)
+ retrieve(:features)[feature] || false
+ end
+
def self.retrieve(symbol)
instance_variable_get :"@#{symbol}"
end
Modified: MacRuby/trunk/mspec/lib/mspec/version.rb
===================================================================
--- MacRuby/trunk/mspec/lib/mspec/version.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/lib/mspec/version.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,5 +1,5 @@
require 'mspec/utils/version'
module MSpec
- VERSION = SpecVersion.new "1.5.14"
+ VERSION = SpecVersion.new "1.5.16"
end
Modified: MacRuby/trunk/mspec/spec/commands/mspec_ci_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/commands/mspec_ci_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/commands/mspec_ci_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -107,6 +107,8 @@
TagFilter.stub!(:new).and_return(@filter)
@filter.stub!(:register)
+ @tags = ["fails", "critical", "unstable", "incomplete", "unsupported"]
+
@config = { :ci_files => ["one", "two"] }
@script = MSpecCI.new
@script.stub!(:exit)
@@ -128,8 +130,24 @@
it "registers a tag filter for 'fails', 'unstable', 'incomplete', 'critical', 'unsupported'" do
filter = mock("fails filter")
+ TagFilter.should_receive(:new).with(:exclude, *@tags).and_return(filter)
+ filter.should_receive(:register)
+ @script.run
+ end
+
+ it "registers an additional exclude tag specified by :ci_xtags" do
+ @config[:ci_xtags] = "windows"
+ filter = mock("fails filter")
+ TagFilter.should_receive(:new).with(:exclude, *(@tags + ["windows"])).and_return(filter)
+ filter.should_receive(:register)
+ @script.run
+ end
+
+ it "registers additional exclude tags specified by a :ci_xtags array" do
+ @config[:ci_xtags] = ["windows", "windoze"]
+ filter = mock("fails filter")
TagFilter.should_receive(:new).with(:exclude,
- "fails", "critical", "unstable", "incomplete", "unsupported").and_return(filter)
+ *(@tags + ["windows", "windoze"])).and_return(filter)
filter.should_receive(:register)
@script.run
end
Modified: MacRuby/trunk/mspec/spec/guards/conflict_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/guards/conflict_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/guards/conflict_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -12,11 +12,23 @@
ScratchPad.recorded.should_not == :yield
end
+ it "does not yield if Object.constants (as Symbols) includes any of the arguments" do
+ Object.stub!(:constants).and_return([:SomeClass, :OtherClass])
+ conflicts_with(:SomeClass, :AClass, :BClass) { ScratchPad.record :yield }
+ ScratchPad.recorded.should_not == :yield
+ end
+
it "yields if Object.constants does not include any of the arguments" do
Object.stub!(:constants).and_return(["SomeClass", "OtherClass"])
conflicts_with(:AClass, :BClass) { ScratchPad.record :yield }
ScratchPad.recorded.should == :yield
end
+
+ it "yields if Object.constants (as Symbols) does not include any of the arguments" do
+ Object.stub!(:constants).and_return([:SomeClass, :OtherClass])
+ conflicts_with(:AClass, :BClass) { ScratchPad.record :yield }
+ ScratchPad.recorded.should == :yield
+ end
end
describe Object, "#conflicts_with" do
Added: MacRuby/trunk/mspec/spec/guards/feature_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/guards/feature_spec.rb (rev 0)
+++ MacRuby/trunk/mspec/spec/guards/feature_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,80 @@
+require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/guards/feature'
+
+describe FeatureGuard, ".enabled?" do
+ it "returns true if the feature is enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:encoding).and_return(true)
+ FeatureGuard.enabled?(:encoding).should be_true
+ end
+
+ it "returns false if the feature is not enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:encoding).and_return(false)
+ FeatureGuard.enabled?(:encoding).should be_false
+ end
+
+ it "returns true if all the features are enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:one).and_return(true)
+ MSpec.should_receive(:feature_enabled?).with(:two).and_return(true)
+ FeatureGuard.enabled?(:one, :two).should be_true
+ end
+
+ it "returns false if any of the features are not enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:one).and_return(true)
+ MSpec.should_receive(:feature_enabled?).with(:two).and_return(false)
+ FeatureGuard.enabled?(:one, :two).should be_false
+ end
+end
+
+describe Object, "#with_feature" do
+ before :each do
+ ScratchPad.clear
+
+ @guard = FeatureGuard.new :encoding
+ FeatureGuard.stub!(:new).and_return(@guard)
+ end
+
+ it "sets the name of the guard to :with_feature" do
+ with_feature(:encoding) { }
+ @guard.name.should == :with_feature
+ end
+
+ it "calls #unregister even when an exception is raised in the guard block" do
+ @guard.should_receive(:match?).and_return(true)
+ @guard.should_receive(:unregister)
+ lambda do
+ with_feature { raise Exception }
+ end.should raise_error(Exception)
+ end
+end
+
+describe Object, "#with_feature" do
+ before :each do
+ ScratchPad.clear
+ end
+
+ it "yields if the feature is enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:encoding).and_return(true)
+ with_feature(:encoding) { ScratchPad.record :yield }
+ ScratchPad.recorded.should == :yield
+ end
+
+ it "yields if all the features are enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:one).and_return(true)
+ MSpec.should_receive(:feature_enabled?).with(:two).and_return(true)
+ with_feature(:one, :two) { ScratchPad.record :yield }
+ ScratchPad.recorded.should == :yield
+ end
+
+ it "does not yield if the feature is not enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:encoding).and_return(false)
+ with_feature(:encoding) { ScratchPad.record :yield }
+ ScratchPad.recorded.should be_nil
+ end
+
+ it "does not yield if any of the features are not enabled" do
+ MSpec.should_receive(:feature_enabled?).with(:one).and_return(true)
+ MSpec.should_receive(:feature_enabled?).with(:two).and_return(false)
+ with_feature(:one, :two) { ScratchPad.record :yield }
+ ScratchPad.recorded.should be_nil
+ end
+end
Modified: MacRuby/trunk/mspec/spec/guards/guard_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/guards/guard_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/guards/guard_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -47,33 +47,6 @@
end
end
-describe SpecGuard, ".windows?" do
- before :all do
- @ruby_platform = Object.const_get :RUBY_PLATFORM
- end
-
- after :all do
- Object.const_set :RUBY_PLATFORM, @ruby_platform
- end
-
- it "returns true if key is mswin32" do
- SpecGuard.windows?("mswin32").should be_true
- end
-
- it "returns true if key is mingw" do
- SpecGuard.windows?("mingw").should be_true
- end
-
- it "returns false for non-windows" do
- SpecGuard.windows?("notwindows").should be_false
- end
-
- it "uses RUBY_PLATFORM by default" do
- Object.const_set :RUBY_PLATFORM, "mswin32"
- SpecGuard.windows?.should be_true
- end
-end
-
describe SpecGuard, "#yield?" do
before :each do
MSpec.clear_modes
@@ -367,7 +340,7 @@
end
end
-describe SpecGuard, "windows?" do
+describe SpecGuard, "#windows?" do
before :each do
@guard = SpecGuard.new
end
Added: MacRuby/trunk/mspec/spec/guards/specified_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/guards/specified_spec.rb (rev 0)
+++ MacRuby/trunk/mspec/spec/guards/specified_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,102 @@
+require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/guards/specified'
+
+describe Object, "#unspecified" do
+ before :each do
+ ScratchPad.clear
+
+ @guard = UnspecifiedGuard.new
+ UnspecifiedGuard.stub!(:new).and_return(@guard)
+ end
+
+ it "does not yield if #standard? returns true" do
+ @guard.should_receive(:standard?).and_return(true)
+ unspecified { ScratchPad.record :yield }
+ ScratchPad.recorded.should be_nil
+ end
+
+ it "yields if #standard? returns false" do
+ @guard.should_receive(:standard?).and_return(false)
+ unspecified { ScratchPad.record :yield }
+ ScratchPad.recorded.should == :yield
+ end
+
+ it "sets the name of the guard to :unspecified" do
+ @guard.should_receive(:standard?).and_return(true)
+ unspecified { }
+ @guard.name.should == :unspecified
+ end
+
+ it "calls #unregister even when an exception is raised in the guard block" do
+ guard = UnspecifiedGuard.new :rubinius
+ UnspecifiedGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:match?).and_return(true)
+ guard.should_receive(:unregister)
+
+ lambda do
+ unspecified { raise Exception }
+ end.should raise_error(Exception)
+ end
+end
+
+describe Object, "#specified_on" do
+ before :each do
+ ScratchPad.clear
+ end
+
+ it "raises an Exception when passed :ruby" do
+ lambda {
+ specifed_on(:ruby) { ScratchPad.record :yield }
+ }.should raise_error(Exception)
+ ScratchPad.recorded.should_not == :yield
+ end
+
+ it "does not yield when #standard? returns true" do
+ guard = SpecifiedOnGuard.new
+ SpecifiedOnGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:standard?).and_return(true)
+
+ specified_on(:rubinius) { ScratchPad.record :yield }
+ ScratchPad.recorded.should be_nil
+ end
+
+ it "does not yield when #standard? returns false and #implementation? returns false" do
+ guard = SpecifiedOnGuard.new :rubinius
+ SpecifiedOnGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:standard?).and_return(false)
+ guard.should_receive(:implementation?).with(:rubinius).and_return(false)
+
+ specified_on(:rubinius) { ScratchPad.record :yield }
+ ScratchPad.recorded.should be_nil
+ end
+
+ it "yields when #standard? returns false and #implementation? returns true" do
+ guard = SpecifiedOnGuard.new :rubinius
+ SpecifiedOnGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:standard?).and_return(false)
+ guard.should_receive(:implementation?).with(:rubinius).and_return(true)
+
+ specified_on(:rubinius) { ScratchPad.record :yield }
+ ScratchPad.recorded.should == :yield
+ end
+
+ it "sets the name of the guard to :specified_on" do
+ guard = SpecifiedOnGuard.new :rubinius
+ SpecifiedOnGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:match?).and_return(false)
+
+ specified_on(:rubinius) { }
+ guard.name.should == :specified_on
+ end
+
+ it "calls #unregister even when an exception is raised in the guard block" do
+ guard = SpecifiedOnGuard.new :rubinius
+ SpecifiedOnGuard.stub!(:new).and_return(guard)
+ guard.should_receive(:match?).and_return(true)
+ guard.should_receive(:unregister)
+
+ lambda do
+ specified_on(:rubinius) { raise Exception }
+ end.should raise_error(Exception)
+ end
+end
Added: MacRuby/trunk/mspec/spec/helpers/encode_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/helpers/encode_spec.rb (rev 0)
+++ MacRuby/trunk/mspec/spec/helpers/encode_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,26 @@
+require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/helpers/encode'
+
+describe Object, "#encode" do
+ it "raises an ArgumentError if the str parameter is not a String" do
+ lambda { encode(Object.new, "utf-8") }.should raise_error(ArgumentError)
+ end
+
+ it "raises an ArgumentError if the encoding parameter is not a String" do
+ lambda { encode("some str", Object.new) }.should raise_error(ArgumentError)
+ end
+
+ it "calls #force_encoding if the :encoding feature is enabled" do
+ FeatureGuard.should_receive(:enabled?).with(:encoding).and_return(true)
+ str = "some text"
+ str.should_receive(:force_encoding).with("utf-8")
+ encode(str, "utf-8")
+ end
+
+ it "does not call #force_encoding if the :encoding feature is not enabled" do
+ FeatureGuard.should_receive(:enabled?).with(:encoding).and_return(false)
+ str = "some text"
+ str.should_not_receive(:force_encoding)
+ encode(str, "utf-8")
+ end
+end
Modified: MacRuby/trunk/mspec/spec/helpers/environment_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/helpers/environment_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/helpers/environment_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,43 +1,30 @@
require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/guards/platform'
require 'mspec/helpers/environment'
describe "#env" do
- before(:all) do
- @ruby_platform = Object.const_get :RUBY_PLATFORM
- end
-
- after(:all) do
- Object.const_set :RUBY_PLATFORM, @ruby_platform
- end
-
it "returns a hash of variables" do
env.class.should == Hash
end
-
+
it "calls `env` on non-Windows" do
- Object.const_set :RUBY_PLATFORM, "notwindows"
+ PlatformGuard.stub!(:windows?).and_return(false)
should_receive(:`).with("env").and_return("one=two\nthree=four")
env
end
- it "calls `cmd.exe /C set` on Windows (mswin32)" do
- Object.const_set :RUBY_PLATFORM, "mswin32"
+ it "calls `cmd.exe /C set` on Windows" do
+ PlatformGuard.stub!(:windows?).and_return(true)
should_receive(:`).with("cmd.exe /C set").and_return("one=two\nthree=four")
env
end
- it "calls `cmd.exe /C set` on Windows (mingw)" do
- Object.const_set :RUBY_PLATFORM, "mingw"
- should_receive(:`).with("cmd.exe /C set").and_return("one=two\nthree=four")
- env
- end
-
it "returns the current user's environment variables" do
- Object.const_set :RUBY_PLATFORM, "notwindows"
+ PlatformGuard.stub!(:windows?).and_return(false)
should_receive(:`).with("env").and_return("one=two\nthree=four")
env.should == {"one" => "two", "three" => "four"}
- Object.const_set :RUBY_PLATFORM, "mswin32"
+ PlatformGuard.stub!(:windows?).and_return(true)
should_receive(:`).with("cmd.exe /C set").and_return("five=six\nseven=eight")
env.should == {"five" => "six", "seven" => "eight"}
end
@@ -52,30 +39,24 @@
Object.const_set :RUBY_PLATFORM, @ruby_platform
end
- it "calls `cmd.exe /C ECHO %USERNAME%` on Windows (mswin32)" do
- Object.const_set :RUBY_PLATFORM, "mswin32"
+ it "calls `cmd.exe /C ECHO %USERNAME%` on Windows" do
+ PlatformGuard.stub!(:windows?).and_return(true)
should_receive(:`).with("cmd.exe /C ECHO %USERNAME%").and_return("john")
username
end
- it "calls `cmd.exe /C ECHO %USERNAME%` on Windows (mingw)" do
- Object.const_set :RUBY_PLATFORM, "mingw"
- should_receive(:`).with("cmd.exe /C ECHO %USERNAME%").and_return("john")
- username
- end
-
it "calls `env` on non-Windows" do
- Object.const_set :RUBY_PLATFORM, "notwindows"
+ PlatformGuard.stub!(:windows?).and_return(false)
should_receive(:`).with("whoami").and_return("john")
username
end
it "returns the user's username" do
- Object.const_set :RUBY_PLATFORM, "mswin32"
+ PlatformGuard.stub!(:windows?).and_return(true)
should_receive(:`).with("cmd.exe /C ECHO %USERNAME%").and_return("johnonwin")
username.should == "johnonwin"
- Object.const_set :RUBY_PLATFORM, "notwindows"
+ PlatformGuard.stub!(:windows?).and_return(false)
should_receive(:`).with("whoami").and_return("john")
username.should == "john"
end
Modified: MacRuby/trunk/mspec/spec/helpers/fixture_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/helpers/fixture_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/helpers/fixture_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -15,4 +15,9 @@
name = fixture("some/path/shared/file.rb", "dir", "file.txt")
name.should == "#{@dir}/some/path/fixtures/dir/file.txt"
end
+
+ it "does not append '/fixtures' if it is the suffix of the directory string" do
+ name = fixture("some/path/fixtures/file.rb", "dir", "file.txt")
+ name.should == "#{@dir}/some/path/fixtures/dir/file.txt"
+ end
end
Added: MacRuby/trunk/mspec/spec/helpers/fmode_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/helpers/fmode_spec.rb (rev 0)
+++ MacRuby/trunk/mspec/spec/helpers/fmode_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,14 @@
+require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/helpers/fmode'
+
+describe Object, "#fmode" do
+ it "returns the argument unmodified if :encoding feature is enabled" do
+ FeatureGuard.should_receive(:enabled?).with(:encoding).and_return(true)
+ fmode("rb:binary:utf-8").should == "rb:binary:utf-8"
+ end
+
+ it "returns only the file access mode if :encoding feature is not enabled" do
+ FeatureGuard.should_receive(:enabled?).with(:encoding).and_return(false)
+ fmode("rb:binary:utf-8").should == "rb"
+ end
+end
Modified: MacRuby/trunk/mspec/spec/helpers/ruby_exe_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/helpers/ruby_exe_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/helpers/ruby_exe_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -73,21 +73,15 @@
end
before :each do
- @ruby_platform = Object.const_get :RUBY_PLATFORM
-
@script = RubyExeSpecs.new
end
- after :each do
- Object.const_set :RUBY_PLATFORM, @ruby_platform
- end
-
after :all do
$VERBOSE = @verbose
end
it "returns the value returned by #ruby_exe_options if it exists and is executable" do
- Object.const_set :RUBY_PLATFORM, "notwindows"
+ PlatformGuard.stub!(:windows?).and_return(false)
@script.should_receive(:ruby_exe_options).and_return(@name)
File.should_receive(:exists?).with(@name).and_return(true)
File.should_receive(:executable?).with(@name).and_return(true)
@@ -95,7 +89,7 @@
end
it "returns the value returned by #ruby_exe_options if it exists on Windows platforms" do
- Object.const_set :RUBY_PLATFORM, "mswin"
+ PlatformGuard.stub!(:windows?).and_return(true)
@script.should_receive(:ruby_exe_options).and_return(@name)
File.should_receive(:exists?).with(@name).and_return(true)
File.should_not_receive(:executable?)
Modified: MacRuby/trunk/mspec/spec/matchers/equal_utf16_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/matchers/equal_utf16_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/matchers/equal_utf16_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -43,15 +43,15 @@
matcher = EqualUtf16Matcher.new("a\0b\0")
matcher.matches?("a\0b\0c\0")
matcher.failure_message.should == [
- "Expected \"a#{@null}b#{@null}c#{@null}\"\n",
- "to equal \"a#{@null}b#{@null}\"\n or \"#{@null}a#{@null}b\"\n"]
+ "Expected [\"a#{@null}b#{@null}c#{@null}\"]\n",
+ "to equal [\"a#{@null}b#{@null}\"]\n or [\"#{@null}a#{@null}b\"]\n"]
end
it "provides a useful negative failure message" do
matcher = EqualUtf16Matcher.new("a\0b\0")
matcher.matches?("\0a\0b")
matcher.negative_failure_message.should == [
- "Expected \"#{@null}a#{@null}b\"\n",
- "not to equal \"a#{@null}b#{@null}\"\n nor \"#{@null}a#{@null}b\"\n"]
+ "Expected [\"#{@null}a#{@null}b\"]\n",
+ "not to equal [\"a#{@null}b#{@null}\"]\n nor [\"#{@null}a#{@null}b\"]\n"]
end
end
Added: MacRuby/trunk/mspec/spec/matchers/have_data_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/matchers/have_data_spec.rb (rev 0)
+++ MacRuby/trunk/mspec/spec/matchers/have_data_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -0,0 +1,51 @@
+require File.dirname(__FILE__) + '/../spec_helper'
+require 'mspec/expectations/expectations'
+require 'mspec/matchers/have_data'
+require 'mspec/helpers/tmp'
+require 'mspec/helpers/fs'
+
+describe HaveDataMatcher do
+ before :each do
+ @name = tmp "have_data_matcher"
+ touch(@name) { |f| f.puts "123abc" }
+ end
+
+ after :each do
+ rm_r @name
+ end
+
+ it "raises an IOError if the named file does not exist" do
+ lambda do
+ HaveDataMatcher.new("123").matches?("no_file.txt")
+ end.should raise_error(Errno::ENOENT)
+ end
+
+ it "matches when the named file begins with the same bytes as data" do
+ HaveDataMatcher.new("123a").matches?(@name).should be_true
+ end
+
+ it "does not match when the named file begins with fewer bytes than data" do
+ HaveDataMatcher.new("123abcPQR").matches?(@name).should be_false
+
+ end
+
+ it "does not match when the named file begins with different bytes than data" do
+ HaveDataMatcher.new("abc1").matches?(@name).should be_false
+ end
+
+ it "provides a useful failure message" do
+ matcher = HaveDataMatcher.new("abc1")
+ matcher.matches?(@name)
+ matcher.failure_message.should == [
+ "Expected #{@name}", "to have data \"abc1\"\n"
+ ]
+ end
+
+ it "provides a useful negative failure message" do
+ matcher = HaveDataMatcher.new("123abc")
+ matcher.matches?(@name)
+ matcher.negative_failure_message.should == [
+ "Expected #{@name}", "not to have data \"123abc\"\n"
+ ]
+ end
+end
Modified: MacRuby/trunk/mspec/spec/mocks/mock_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/mocks/mock_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/mocks/mock_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -446,4 +446,15 @@
Mock.cleanup
Mock.stubs.should == {}
end
+
+ it "removes the replaced name for mocks" do
+ replaced_key = Mock.replaced_key(@mock, :method_call)
+ Mock.should_receive(:clear_replaced).with(replaced_key)
+
+ replaced_name = Mock.replaced_name(@mock, :method_call)
+ Mock.replaced?(replaced_name).should be_true
+
+ Mock.cleanup
+ Mock.replaced?(replaced_name).should be_false
+ end
end
Modified: MacRuby/trunk/mspec/spec/runner/context_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/context_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/context_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -262,6 +262,12 @@
state.parent = @parent
end
+ it "does not set parents if shared" do
+ state = ContextState.new "", :shared => true
+ state.parent = @parent
+ state.parents.should == [state]
+ end
+
it "sets self as a child of parent" do
@parent.should_receive(:child).with(@state)
@state.parent = @parent
@@ -910,11 +916,11 @@
describe ContextState, "#it_should_behave_like" do
before :each do
- @shared_desc = "shared context"
+ @shared_desc = :shared_context
@shared = ContextState.new(@shared_desc, :shared => true)
MSpec.stub!(:retrieve_shared).and_return(@shared)
- @state = ContextState.new ""
+ @state = ContextState.new "Top level"
@a = lambda { }
@b = lambda { }
end
@@ -926,36 +932,57 @@
describe "for nested ContextState instances" do
before :each do
- @nested = ContextState.new ""
+ @nested = ContextState.new "nested context"
@nested.parents.unshift @shared
+
@shared.children << @nested
+
+ @nested_dup = @nested.dup
+ @nested.stub!(:dup).and_return(@nested_dup)
end
- it "adds nested describe blocks to the invoking ContextState" do
+ it "duplicates the nested ContextState" do
@state.it_should_behave_like @shared_desc
- @shared.children.should_not be_empty
- @state.children.should include(*@shared.children)
+ @state.children.first.should equal(@nested_dup)
end
- it "changes the parent ContextState" do
- @shared.children.first.parents.first.should equal(@shared)
+ it "sets the parent of the nested ContextState to the containing ContextState" do
@state.it_should_behave_like @shared_desc
- @shared.children.first.parents.first.should equal(@state)
+ @nested_dup.parent.should equal(@state)
end
+
+ it "sets the context for nested examples to the nested ContextState's dup" do
+ @shared.it "an example", &@a
+ @shared.it "another example", &@b
+ @state.it_should_behave_like @shared_desc
+ @nested_dup.examples.each { |x| x.context.should equal(@nested_dup) }
+ end
+
+ it "omits the shored ContextState's description" do
+ @nested.it "an example", &@a
+ @nested.it "another example", &@b
+ @state.it_should_behave_like @shared_desc
+
+ @nested_dup.description.should == "Top level nested context"
+ @nested_dup.examples.first.description.should == "Top level nested context an example"
+ @nested_dup.examples.last.description.should == "Top level nested context another example"
+ end
end
- it "adds examples from the shared ContextState" do
- @shared.it "some", &@a
- @shared.it "thing", &@b
+ it "adds duped examples from the shared ContextState" do
+ @shared.it "some method", &@a
+ ex_dup = @shared.examples.first.dup
+ @shared.examples.first.stub!(:dup).and_return(ex_dup)
+
@state.it_should_behave_like @shared_desc
- @state.examples.should include(*@shared.examples)
+ @state.examples.should == [ex_dup]
end
- it "sets the containing ContextState for the examples" do
- @shared.it "some", &@a
- @shared.it "thing", &@b
- @shared.examples.each { |ex| ex.should_receive(:context=).with(@state) }
+ it "sets the context for examples to the containing ContextState" do
+ @shared.it "an example", &@a
+ @shared.it "another example", &@b
@state.it_should_behave_like @shared_desc
+ @state.examples.each { |x| x.context.should equal(@state) }
end
it "adds before(:all) blocks from the shared ContextState" do
Modified: MacRuby/trunk/mspec/spec/runner/example_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/example_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/example_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -71,6 +71,11 @@
@filter = mock("filter")
end
+ after :each do
+ MSpec.store :include, nil
+ MSpec.store :exclude, nil
+ end
+
it "returns false if MSpec include filters list is empty" do
@state.filtered?.should == false
end
Modified: MacRuby/trunk/mspec/spec/runner/formatters/dotted_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/dotted_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/dotted_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -2,6 +2,7 @@
require 'mspec/runner/formatters/dotted'
require 'mspec/runner/mspec'
require 'mspec/runner/example'
+require 'mspec/utils/script'
describe DottedFormatter, "#initialize" do
it "permits zero arguments" do
@@ -16,10 +17,10 @@
describe DottedFormatter, "#register" do
before :each do
@formatter = DottedFormatter.new
+ MSpec.stub!(:register)
end
it "registers self with MSpec for appropriate actions" do
- MSpec.stub!(:register)
MSpec.should_receive(:register).with(:exception, @formatter)
MSpec.should_receive(:register).with(:before, @formatter)
MSpec.should_receive(:register).with(:after, @formatter)
Modified: MacRuby/trunk/mspec/spec/runner/formatters/file_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/file_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/file_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -6,17 +6,17 @@
describe FileFormatter, "#register" do
before :each do
@formatter = FileFormatter.new
+ MSpec.stub!(:register)
+ MSpec.stub!(:unregister)
end
it "registers self with MSpec for :load, :unload actions" do
- MSpec.stub!(:register)
MSpec.should_receive(:register).with(:load, @formatter)
MSpec.should_receive(:register).with(:unload, @formatter)
@formatter.register
end
it "unregisters self with MSpec for :before, :after actions" do
- MSpec.stub!(:unregister)
MSpec.should_receive(:unregister).with(:before, @formatter)
MSpec.should_receive(:unregister).with(:after, @formatter)
@formatter.register
Modified: MacRuby/trunk/mspec/spec/runner/formatters/html_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/html_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/html_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -4,6 +4,7 @@
require 'mspec/runner/formatters/html'
require 'mspec/runner/mspec'
require 'mspec/runner/example'
+require 'mspec/utils/script'
describe HtmlFormatter do
before :each do
Modified: MacRuby/trunk/mspec/spec/runner/formatters/method_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/method_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/method_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -2,6 +2,7 @@
require 'mspec/runner/formatters/method'
require 'mspec/runner/mspec'
require 'mspec/runner/example'
+require 'mspec/utils/script'
describe MethodFormatter, "#method_type" do
before :each do
Modified: MacRuby/trunk/mspec/spec/runner/formatters/spinner_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/spinner_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/spinner_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -16,10 +16,10 @@
describe SpinnerFormatter, "#register" do
before :each do
@formatter = SpinnerFormatter.new
+ MSpec.stub!(:register)
end
it "registers self with MSpec for appropriate actions" do
- MSpec.stub!(:register)
MSpec.should_receive(:register).with(:start, @formatter)
MSpec.should_receive(:register).with(:load, @formatter)
MSpec.should_receive(:register).with(:after, @formatter)
Modified: MacRuby/trunk/mspec/spec/runner/formatters/unit_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/formatters/unit_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/formatters/unit_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,6 +1,7 @@
require File.dirname(__FILE__) + '/../../spec_helper'
require 'mspec/runner/formatters/unit'
require 'mspec/runner/example'
+require 'mspec/utils/script'
describe UnitdiffFormatter, "#finish" do
before :each do
Modified: MacRuby/trunk/mspec/spec/runner/shared_spec.rb
===================================================================
--- MacRuby/trunk/mspec/spec/runner/shared_spec.rb 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/spec/runner/shared_spec.rb 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1,27 +1,78 @@
require File.dirname(__FILE__) + '/../spec_helper'
require 'mspec/runner/shared'
+require 'mspec/runner/context'
+require 'mspec/runner/example'
describe Object, "#it_behaves_like" do
before :each do
- @recv = Object.new
- def @recv.before(what)
- yield
- end
- @recv.stub!(:it_should_behave_like)
+ ScratchPad.clear
+
+ @state = ContextState.new "Top level"
+ @state.instance_variable_set :@parsed, true
+
+ @shared = ContextState.new :shared_spec, :shared => true
+ MSpec.stub!(:retrieve_shared).and_return(@shared)
end
it "creates @method set to the name of the aliased method" do
- @recv.it_behaves_like "something", :some_method
- @recv.instance_variable_get(:@method).should == :some_method
+ @shared.it("an example") { ScratchPad.record @method }
+ @state.it_behaves_like :shared_spec, :some_method
+ @state.process
+ ScratchPad.recorded.should == :some_method
end
- it "creates @object if the passed object is not nil" do
- @recv.it_behaves_like "something", :some_method, :some_object
- @recv.instance_variable_get(:@object).should == :some_object
+ it "creates @object if the passed object" do
+ object = Object.new
+ @shared.it("an example") { ScratchPad.record @object }
+ @state.it_behaves_like :shared_spec, :some_method, object
+ @state.process
+ ScratchPad.recorded.should == object
end
it "sends :it_should_behave_like" do
- @recv.should_receive(:it_should_behave_like)
- @recv.it_behaves_like "something", :some_method
+ @state.should_receive(:it_should_behave_like)
+ @state.it_behaves_like :shared_spec, :some_method
end
+
+ describe "with multiple shared contexts" do
+ before :each do
+ @obj = Object.new
+ @obj2 = Object.new
+
+ @state2 = ContextState.new "Second top level"
+ @state2.instance_variable_set :@parsed, true
+ end
+
+ it "ensures the shared spec state is distinct" do
+ @shared.it("an example") { ScratchPad.record [@method, @object] }
+
+ @state.it_behaves_like :shared_spec, :some_method, @obj
+
+ @state.process
+ ScratchPad.recorded.should == [:some_method, @obj]
+
+ @state2.it_behaves_like :shared_spec, :another_method, @obj2
+
+ @state2.process
+ ScratchPad.recorded.should == [:another_method, @obj2]
+ end
+
+ it "ensures the shared spec state is distinct for nested shared specs" do
+ nested = ContextState.new "nested context"
+ nested.instance_variable_set :@parsed, true
+ nested.parent = @shared
+
+ nested.it("another example") { ScratchPad.record [:shared, @method, @object] }
+
+ @state.it_behaves_like :shared_spec, :some_method, @obj
+
+ @state.process
+ ScratchPad.recorded.should == [:shared, :some_method, @obj]
+
+ @state2.it_behaves_like :shared_spec, :another_method, @obj2
+
+ @state2.process
+ ScratchPad.recorded.should == [:shared, :another_method, @obj2]
+ end
+ end
end
Modified: MacRuby/trunk/mspec/upstream
===================================================================
--- MacRuby/trunk/mspec/upstream 2010-03-28 04:26:06 UTC (rev 3869)
+++ MacRuby/trunk/mspec/upstream 2010-03-28 17:00:14 UTC (rev 3870)
@@ -1 +1 @@
-ddf4bd5a4c29e36caad2504749a7bfb5dc8eadf5
\ No newline at end of file
+88d85da83cbf2e595ec956651520ce119d429e8f
\ No newline at end of file
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.macosforge.org/pipermail/macruby-changes/attachments/20100328/ca8eac9b/attachment-0001.html>
More information about the macruby-changes
mailing list