Module: Cucumber::StepMother

Defined in:
lib/cucumber/step_mother.rb

Overview

This is the main interface for registering step definitions, which is done from *_steps.rb files. This module is included right at the top-level so #register_step_definition (and more interestingly - its aliases) are available from the top-level.

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#options=(value) ⇒ Object

Sets the attribute options

Parameters:

  • value

    the value to set the attribute options to.



77
78
79
# File 'lib/cucumber/step_mother.rb', line 77

def options=(value)
  @options = value
end

#snippet_generator=(value) ⇒ Object (writeonly)

Sets the attribute snippet_generator

Parameters:

  • value

    the value to set the attribute snippet_generator to.



77
78
79
# File 'lib/cucumber/step_mother.rb', line 77

def snippet_generator=(value)
  @snippet_generator = value
end

#visitor=(value) ⇒ Object (writeonly)

Sets the attribute visitor

Parameters:

  • value

    the value to set the attribute visitor to.



77
78
79
# File 'lib/cucumber/step_mother.rb', line 77

def visitor=(value)
  @visitor = value
end

Class Method Details

.alias_adverb(adverb) ⇒ Object



71
72
73
74
# File 'lib/cucumber/step_mother.rb', line 71

def alias_adverb(adverb)
  adverb = adverb.gsub(/\s/, '')
  alias_method adverb, :register_step_definition
end

Instance Method Details

#after(scenario) ⇒ Object



212
213
214
# File 'lib/cucumber/step_mother.rb', line 212

def after(scenario)
  execute_after(scenario)
end

#After(&proc) ⇒ Object



121
122
123
# File 'lib/cucumber/step_mother.rb', line 121

def After(&proc)
  (@after_procs ||= []).unshift(proc)
end

#Before(&proc) ⇒ Object

Registers a Before proc. You can call this method as many times as you want (typically from ruby scripts under support).



117
118
119
# File 'lib/cucumber/step_mother.rb', line 117

def Before(&proc)
  (@before_procs ||= []) << proc
end

#before_and_after(scenario, skip = false) ⇒ Object



199
200
201
202
203
204
205
206
207
208
209
210
# File 'lib/cucumber/step_mother.rb', line 199

def before_and_after(scenario, skip=false)
  unless current_world || skip
    new_world!
    execute_before(scenario)
  end
  if block_given?
    yield
    execute_after(scenario) unless skip
    nil_world!
    scenario_visited(scenario)
  end
end

#best_matches(step_name, step_matches) ⇒ Object



179
180
181
182
183
184
185
186
187
188
189
# File 'lib/cucumber/step_mother.rb', line 179

def best_matches(step_name, step_matches)
  max_arg_length = step_matches.map {|step_match| step_match.args.length }.max
  top_groups     = step_matches.select {|step_match| step_match.args.length == max_arg_length }

  if top_groups.length > 1
    shortest_capture_length = top_groups.map {|step_match| step_match.args.inject(0) {|sum, c| sum + c.length } }.min
    top_groups.select {|step_match| step_match.args.inject(0) {|sum, c| sum + c.length } == shortest_capture_length }
  else
    top_groups
  end
end

#current_worldObject



167
168
169
# File 'lib/cucumber/step_mother.rb', line 167

def current_world
  @current_world
end

#register_step_definition(regexp, &proc) ⇒ Object

Registers a new StepDefinition. This method is aliased to Given, When and Then.

See Cucumber#alias_steps for details on how to create your own aliases.

The &proc gets executed in the context of a world object, which is defined by #World. A new world object is created for each scenario and is shared across step definitions within that scenario.



106
107
108
109
110
111
112
113
# File 'lib/cucumber/step_mother.rb', line 106

def register_step_definition(regexp, &proc)
  step_definition = StepDefinition.new(regexp, &proc)
  step_definitions.each do |already|
    raise Redundant.new(already, step_definition) if already.match(regexp)
  end
  step_definitions << step_definition
  step_definition
end

#scenariosObject



92
93
94
# File 'lib/cucumber/step_mother.rb', line 92

def scenarios
  @scenarios ||= []
end

#snippet_text(step_keyword, step_name, multiline_arg_class) ⇒ Object



195
196
197
# File 'lib/cucumber/step_mother.rb', line 195

def snippet_text(step_keyword, step_name, multiline_arg_class)
  @snippet_generator.snippet_text(step_keyword, step_name, multiline_arg_class)
end

#step_definitionsObject



191
192
193
# File 'lib/cucumber/step_mother.rb', line 191

def step_definitions
  @step_definitions ||= []
end

#step_match(step_name, formatted_step_name = nil) ⇒ Object

Raises:



171
172
173
174
175
176
177
# File 'lib/cucumber/step_mother.rb', line 171

def step_match(step_name, formatted_step_name=nil)
  matches = step_definitions.map { |d| d.step_match(step_name, formatted_step_name) }.compact
  raise Undefined.new(step_name) if matches.empty?
  matches = best_matches(step_name, matches) if matches.size > 1 && options[:guess]
  raise Ambiguous.new(step_name, matches, options[:guess]) if matches.size > 1
  matches[0]
end

#step_visited(step) ⇒ Object



79
80
81
# File 'lib/cucumber/step_mother.rb', line 79

def step_visited(step)
  steps << step unless steps.index(step)
end

#steps(status = nil) ⇒ Object



83
84
85
86
87
88
89
90
# File 'lib/cucumber/step_mother.rb', line 83

def steps(status = nil)
  @steps ||= []
  if(status)
    @steps.select{|step| step.status == status}
  else
    @steps
  end
end

#World(*world_modules, &proc) ⇒ Object

Registers any number of world_modules (Ruby Modules) and/or a Proc. The proc will be executed once before each scenario to create an Object that the scenario’s steps will run within. Any world_modules will be mixed into this Object (via Object#extend).

This method is typically called from one or more Ruby scripts under features/support. You can call this method as many times as you like (to register more modules), but if you try to register more than one Proc you will get an error.

Cucumber will not yield anything to the proc (like it used to do before v0.3).

In earlier versions of Cucumber (before 0.3) you could not register any world_modules. Instead you would register several Proc objects (by calling the method several times). The result of each proc would be yielded to the next proc. Example:

World do |world| # NOT SUPPORTED FROM 0.3
  MyClass.new
end

World do |world| # NOT SUPPORTED FROM 0.3
  world.extend(MyModule)
end

From Cucumber 0.3 the recommended way to do this is:

World do
  MyClass.new
end

World(MyModule)


158
159
160
161
162
163
164
165
# File 'lib/cucumber/step_mother.rb', line 158

def World(*world_modules, &proc)
  if(proc)
    raise MultipleWorld.new(@world_proc, proc) if @world_proc
    @world_proc = proc
  end
  @world_modules ||= []
  @world_modules += world_modules
end