模块: RSpec::Matchers::DSL::Macros

包含于
Matcher
定义于
lib/rspec/matchers/dsl.rb

概述

包含在 RSpec::Matchers.define DSL 中用于创建自定义匹配器的可用方法。

定义于命名空间下

模块: Deprecated

实例方法摘要 收起

实例方法详情

#chain(method_name, *attr_names, &definition) ⇒Object

方便在该匹配器上定义方法以创建流畅的接口。流畅接口的技巧是每个方法必须返回 self 以便将方法链接在一起。chain 会为您处理此操作。如果调用了该方法,并且 include_chain_clauses_in_custom_matcher_descriptions 配置选项哈希已被启用,则链接方法名称和参数将被添加到默认描述和失败消息中。

在您只想让链接方法为以后使用(例如在 match 中)存储一些值(例如)的常见情况下,您可以提供一个或多个属性名称而不是代码块;链接方法将把其参数存储在具有这些名称的实例变量中,并且这些值将通过 getter 暴露。

示例


RSpec::Matchers.define :have_errors_on do |key|
  chain :with do |message|
    @message = message
  end
  match do |actual|
    actual.errors[key] == @message
  end
end
expect(minor).to have_errors_on(:age).with("Not old enough to participate")
298
299
300
301
302
303
304
305
306
307
308
309
310
# File 'lib/rspec/matchers/dsl.rb', line 298
def chain(method_name, *attr_names, &definition)
  unless block_given? ^ attr_names.any?
    raise ArgumentError, "You must pass either a block or some attribute names (but not both) to `chain`."
  end
  definition = assign_attributes(attr_names) if attr_names.any?
  define_user_override(method_name, definition) do |*args, &block|
    super(*args, &block)
    @chained_method_clauses.push([method_name, args])
    self
  end
end

#description {|Object| ... } ⇒Object

自定义用于单行描述的描述。仅当默认生成的描述不适合您的需要时才使用此方法。

示例


RSpec::Matchers.define :qualify_for do |expected|
  match { your_match_logic }
  description do
    "qualify for #{expected}"
  end
end

产量

  • (Object)

    actual 实际对象(即 expect 包裹的值)

253
254
255
# File 'lib/rspec/matchers/dsl.rb', line 253
def description(&definition)
  define_user_override(__method__, definition)
end

#diffableObject

告诉匹配器在失败消息中对实际值和预期值进行差异比较。

259
260
261
# File 'lib/rspec/matchers/dsl.rb', line 259
def diffable
  define_method(:diffable?) { true }
end

#failure_message {|Object| ... } ⇒Object

自定义当要求该匹配器进行正向匹配时使用的失败消息。仅当默认生成的消息不适合您的需要时才使用此方法。

示例


RSpec::Matchers.define :have_strength do |expected|
  match { your_match_logic }
  failure_message do |actual|
    "Expected strength of #{expected}, but had #{actual.strength}"
  end
end

产量

  • (Object)

    actual 实际对象(即 expect 包裹的值)

216
217
218
# File 'lib/rspec/matchers/dsl.rb', line 216
def failure_message(&definition)
  define_user_override(__method__, definition)
end

#failure_message_when_negated {|Object| ... } ⇒Object

自定义当要求该匹配器进行负向匹配时使用的失败消息。仅当默认生成的消息不适合您的需要时才使用此方法。

示例


RSpec::Matchers.define :have_strength do |expected|
  match { your_match_logic }
  failure_message_when_negated do |actual|
    "Expected not to have strength of #{expected}, but did"
  end
end

产量

  • (Object)

    actual 实际对象(即 expect 包裹的值)

235
236
237
# File 'lib/rspec/matchers/dsl.rb', line 235
def failure_message_when_negated(&definition)
  define_user_override(__method__, definition)
end

#match(options = {}) {|Object| ... } ⇒Object

存储用于确定该匹配器是否通过或失败的代码块。代码块应返回布尔值。当匹配器传递给 expect(...).to 并且代码块返回 true 时,则期望通过。类似地,当匹配器传递给 expect(...).not_to 并且代码块返回 false 时,则期望通过。

默认情况下,匹配代码块将吞并期望错误(例如由使用期望(例如 expect(1).to eq 2)引起的),如果您希望允许这些错误冒泡,请传递选项 :notify_expectation_failures => true

示例


RSpec::Matchers.define :be_even do
  match do |actual|
    actual.even?
  end
end
expect(4).to be_even     # passes
expect(3).not_to be_even # passes
expect(3).to be_even     # fails
expect(4).not_to be_even # fails

参数

  • options (Hash) (defaults to: {})

    用于定义匹配代码块的行为。

产量

  • (Object)

    actual 实际值(即 expect 包裹的值)

131
132
133
134
135
136
137
138
139
140
141
142
143
# File 'lib/rspec/matchers/dsl.rb', line 131
def match(options={}, &match_block)
  define_user_override(:matches?, match_block) do |actual|
    @actual = actual
    RSpec::Support.with_failure_notifier(RAISE_NOTIFIER) do
      begin
        super(*actual_arg_for(match_block))
      rescue RSpec::Expectations::ExpectationNotMetError
        raise if options[:notify_expectation_failures]
        false
      end
    end
  end
end

#match_unless_raises(expected_exception = Exception) {|Object| ... } ⇒Object

当代码块引发异常而不是返回 false 以指示失败时,请使用它代替 match

示例


RSpec::Matchers.define :accept_as_valid do |candidate_address|
  match_unless_raises ValidationException do |validator|
    validator.validate(candidate_address)
  end
end
expect(email_validator).to accept_as_valid("person@company.com")

产量

  • (Object)

    actual 实际对象(即 expect 包裹的值)

188
189
190
191
192
193
194
195
196
197
198
199
# File 'lib/rspec/matchers/dsl.rb', line 188
def match_unless_raises(expected_exception=Exception, &match_block)
  define_user_override(:matches?, match_block) do |actual|
    @actual = actual
    begin
      super(*actual_arg_for(match_block))
    rescue expected_exception => @rescued_exception
      false
    else
      true
    end
  end
end

#match_when_negated(options = {}) {|Object| ... } ⇒Object

当正向和负向形式需要不同的处理时,使用它来定义负向期望 (expect(...).not_to) 的代码块。这很少需要,但可能很有用,例如在指定需要不同超时时间的异步进程时。

默认情况下,匹配代码块将吞并期望错误(例如由使用期望(例如 expect(1).to eq 2)引起的),如果您希望允许这些错误冒泡,请传递选项 :notify_expectation_failures => true

参数

  • options (Hash) (defaults to: {})

    用于定义匹配代码块的行为。

产量

  • (Object)

    actual 实际值(即 expect 包裹的值)

160
161
162
163
164
165
166
167
168
169
170
171
172
# File 'lib/rspec/matchers/dsl.rb', line 160
def match_when_negated(options={}, &match_block)
  define_user_override(:does_not_match?, match_block) do |actual|
    begin
      @actual = actual
      RSpec::Support.with_failure_notifier(RAISE_NOTIFIER) do
        super(*actual_arg_for(match_block))
      end
    rescue RSpec::Expectations::ExpectationNotMetError
      raise if options[:notify_expectation_failures]
      false
    end
  end
end

#supports_block_expectationsObject

声明该匹配器可以在代码块期望中使用。在未声明此方法的情况下,用户将无法在代码块期望中使用您的匹配器。(例如 expect { do_something }.to matcher)。

267
268
269
# File 'lib/rspec/matchers/dsl.rb', line 267
def supports_block_expectations
  define_method(:supports_block_expectations?) { true }
end