given_core 3.0.0.beta.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/Gemfile +7 -0
- data/Gemfile.lock +27 -0
- data/MIT-LICENSE +20 -0
- data/README.md +720 -0
- data/Rakefile +232 -0
- data/TODO +13 -0
- data/doc/main.rdoc +7 -0
- data/lib/given.rb +2 -0
- data/lib/given/core.rb +11 -0
- data/lib/given/evaluator.rb +38 -0
- data/lib/given/ext/numeric.rb +31 -0
- data/lib/given/extensions.rb +242 -0
- data/lib/given/failure.rb +56 -0
- data/lib/given/failure_matcher.rb +63 -0
- data/lib/given/file_cache.rb +18 -0
- data/lib/given/fuzzy_number.rb +68 -0
- data/lib/given/fuzzy_shortcuts.rb +1 -0
- data/lib/given/line_extractor.rb +41 -0
- data/lib/given/module_methods.rb +69 -0
- data/lib/given/natural_assertion.rb +177 -0
- data/lib/given/version.rb +11 -0
- data/lib/rspec-given.rb +9 -0
- data/rakelib/bundler_fix.rb +17 -0
- data/rakelib/gemspec.rake +157 -0
- data/rakelib/metrics.rake +30 -0
- data/rakelib/preview.rake +14 -0
- data/test/before_test.rb +22 -0
- data/test/meme_test.rb +36 -0
- metadata +93 -0
data/Rakefile
ADDED
@@ -0,0 +1,232 @@
|
|
1
|
+
#!/usr/bin/ruby -wKU
|
2
|
+
|
3
|
+
require 'rake/clean'
|
4
|
+
require './lib/given/version'
|
5
|
+
require './lib/given/module_methods'
|
6
|
+
|
7
|
+
CLEAN.include("pkg/rspec-given-*").exclude("pkg/*.gem")
|
8
|
+
CLOBBER.include("*.gemspec", "html", "README", "README.old")
|
9
|
+
|
10
|
+
# README Formatting --------------------------------------------------
|
11
|
+
|
12
|
+
task :default => :examples
|
13
|
+
|
14
|
+
def version
|
15
|
+
Given::VERSION
|
16
|
+
end
|
17
|
+
|
18
|
+
def tag_name
|
19
|
+
"rspec-given-#{version}"
|
20
|
+
end
|
21
|
+
|
22
|
+
def tagged?
|
23
|
+
`git tag`.split.include?(tag_name)
|
24
|
+
end
|
25
|
+
|
26
|
+
def git_clean?
|
27
|
+
sh "git status | grep 'nothing to commit'", :verbose => false do |status|
|
28
|
+
return status
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
desc "Display the current version tag"
|
33
|
+
task :version do
|
34
|
+
puts tag_name
|
35
|
+
end
|
36
|
+
|
37
|
+
desc "Tag the current commit with #{tag_name}"
|
38
|
+
task :tag do
|
39
|
+
fail "Cannot tag, project directory is not clean" unless git_clean?
|
40
|
+
fail "Cannot tag, #{tag_name} already exists." if tagged?
|
41
|
+
sh "git tag #{tag_name}"
|
42
|
+
end
|
43
|
+
|
44
|
+
# Running examples ---------------------------------------------------
|
45
|
+
|
46
|
+
desc "Run all the examples"
|
47
|
+
task :examples => [:specs, :rs_examples]
|
48
|
+
|
49
|
+
desc "Run the RSpec 2 specs and examples"
|
50
|
+
task :examples => [:specs, :rs_examples, :mt_examples]
|
51
|
+
|
52
|
+
desc "Run the specs"
|
53
|
+
task :specs do
|
54
|
+
puts "Running specs"
|
55
|
+
sh "rspec spec"
|
56
|
+
end
|
57
|
+
|
58
|
+
EXAMPLES = FileList['examples/**/*_spec.rb'].
|
59
|
+
exclude('examples/failing/*.rb').
|
60
|
+
exclude('examples/integration/failing/*.rb')
|
61
|
+
|
62
|
+
unless Given::NATURAL_ASSERTIONS_SUPPORTED
|
63
|
+
EXAMPLES.exclude("examples/stack/*.rb")
|
64
|
+
end
|
65
|
+
|
66
|
+
FAILING_EXAMPLES = FileList['examples/failing/**/*_spec.rb']
|
67
|
+
|
68
|
+
desc "Run the RSpec specs and examples"
|
69
|
+
task :rs => [:specs, :rs_examples]
|
70
|
+
|
71
|
+
desc "Run the Minitest tests and examples"
|
72
|
+
task :mt => [:specs, :mt_examples]
|
73
|
+
|
74
|
+
desc "Run the examples in RSpec 2"
|
75
|
+
task :rs_examples => [:verify_rspec2] do
|
76
|
+
puts "Running examples (with RSpec2)"
|
77
|
+
sh "rspec #{EXAMPLES}"
|
78
|
+
end
|
79
|
+
|
80
|
+
desc "Run the examples in Minitest"
|
81
|
+
task :mt_examples do
|
82
|
+
puts "Running examples (with Minitest)"
|
83
|
+
ENV['FRAMEWORK'] = 'Minitest'
|
84
|
+
sh "ruby -Ilib:examples examples/loader.rb #{EXAMPLES}"
|
85
|
+
end
|
86
|
+
|
87
|
+
desc "Run failing examples"
|
88
|
+
task :failing => [:verify_rspec2] do
|
89
|
+
puts "Running failing examples (with RSpec2)"
|
90
|
+
sh "rspec #{FAILING_EXAMPLES}"
|
91
|
+
end
|
92
|
+
|
93
|
+
task :verify_rspec1 do
|
94
|
+
sh "type spec >/dev/null 2>&1", :verbose => false do |status|
|
95
|
+
fail "You need to install RSpec 1 in order to test against it." unless status
|
96
|
+
end
|
97
|
+
end
|
98
|
+
|
99
|
+
task :verify_rspec2 do
|
100
|
+
sh "type rspec >/dev/null 2>&1", :verbose => false do |status|
|
101
|
+
fail "You need to install RSpec 2 in order to test against it." unless status
|
102
|
+
end
|
103
|
+
end
|
104
|
+
|
105
|
+
task :load_check do
|
106
|
+
SRC_FILES = FileList['lib/rspec/given/*.rb'].exclude(%r(rspec1))
|
107
|
+
SRC_FILES.each do |fn|
|
108
|
+
sh %{ruby -Ilib -e 'load "#{fn}"'}
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
# Formatting the README ----------------------------------------------
|
113
|
+
|
114
|
+
directory 'html'
|
115
|
+
|
116
|
+
desc "Display the README file"
|
117
|
+
task :readme => ["README.md"] do
|
118
|
+
Bundler.with_clean_env do
|
119
|
+
sh "ghpreview README.md"
|
120
|
+
end
|
121
|
+
end
|
122
|
+
|
123
|
+
desc "Generate an RDoc README"
|
124
|
+
file "README.md" => ["examples/stack/stack_spec.rb", "lib/given/version.rb"] do
|
125
|
+
open("README.md") do |ins|
|
126
|
+
open("README.tmp", "w") do |outs|
|
127
|
+
state = :copy
|
128
|
+
while line = ins.gets
|
129
|
+
case state
|
130
|
+
when :copy
|
131
|
+
if line =~ /rspec-given, version +\d+(\.(\d+|beta))+/i
|
132
|
+
line.gsub!(/version +\d+(\.(\d+|beta))+/i, "version #{Given::VERSION}")
|
133
|
+
outs.puts line
|
134
|
+
elsif line =~ /^<pre>/
|
135
|
+
state = :insert
|
136
|
+
else
|
137
|
+
outs.puts line
|
138
|
+
end
|
139
|
+
when :insert
|
140
|
+
outs.puts "<pre>"
|
141
|
+
outs.puts open("examples/stack/stack_spec.rb") { |codes| codes.read }
|
142
|
+
outs.puts "</pre>"
|
143
|
+
state = :skip
|
144
|
+
when :skip
|
145
|
+
state = :copy2 if line =~ /^<\/pre>/
|
146
|
+
when :copy2
|
147
|
+
outs.puts line
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
end
|
152
|
+
mv "README.md", "README.old"
|
153
|
+
mv "README.tmp", "README.md"
|
154
|
+
end
|
155
|
+
|
156
|
+
|
157
|
+
# RDoc ---------------------------------------------------------------
|
158
|
+
begin
|
159
|
+
require 'rdoc/task'
|
160
|
+
if RDoc::VERSION > "2.4.2"
|
161
|
+
RDOC_ENABLED = true
|
162
|
+
else
|
163
|
+
puts "Version of RDoc is too old, please gem install a later version"
|
164
|
+
RDOC_ENABLED = false
|
165
|
+
end
|
166
|
+
rescue LoadError => ex
|
167
|
+
RDOC_ENABLED = false
|
168
|
+
end
|
169
|
+
|
170
|
+
begin
|
171
|
+
require 'darkfish-rdoc'
|
172
|
+
DARKFISH_ENABLED = true
|
173
|
+
rescue LoadError => ex
|
174
|
+
DARKFISH_ENABLED = false
|
175
|
+
end
|
176
|
+
|
177
|
+
if RDOC_ENABLED
|
178
|
+
def md_to_rdoc(infile, outfile)
|
179
|
+
open(infile) do |ins|
|
180
|
+
open(outfile, "w") do |outs|
|
181
|
+
state = :copy
|
182
|
+
while line = ins.gets
|
183
|
+
case state
|
184
|
+
when :ignore
|
185
|
+
if line =~ /^-->/
|
186
|
+
state = :copy
|
187
|
+
end
|
188
|
+
when :pre
|
189
|
+
if line =~ /^<\/pre>/
|
190
|
+
state = :copy
|
191
|
+
else
|
192
|
+
outs.puts " #{line}"
|
193
|
+
end
|
194
|
+
when :copy
|
195
|
+
if line =~ /^<!--/
|
196
|
+
state = :ignore
|
197
|
+
elsif line =~ /^<pre>/
|
198
|
+
state = :pre
|
199
|
+
else
|
200
|
+
line.gsub!(/^####/, '====')
|
201
|
+
line.gsub!(/^###/, '===')
|
202
|
+
line.gsub!(/^##/, '==')
|
203
|
+
line.gsub!(/^#/, '=')
|
204
|
+
outs.puts line
|
205
|
+
end
|
206
|
+
end
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
end
|
211
|
+
|
212
|
+
file "README" => ["README.md"] do
|
213
|
+
md_to_rdoc("README.md", "README")
|
214
|
+
end
|
215
|
+
|
216
|
+
RDoc::Task.new("rdoc") do |rdoc|
|
217
|
+
rdoc.rdoc_dir = 'html'
|
218
|
+
rdoc.title = "RSpec/Given -- A Given/When/Then extension for RSpec"
|
219
|
+
rdoc.options = [
|
220
|
+
'--line-numbers',
|
221
|
+
'--main' , 'doc/main.rdoc',
|
222
|
+
'--title', 'Given - Given/When/Then Extensions for RSpec'
|
223
|
+
]
|
224
|
+
rdoc.options << '-SHN' << '-f' << 'darkfish' if DARKFISH_ENABLED
|
225
|
+
|
226
|
+
rdoc.rdoc_files.include('README')
|
227
|
+
rdoc.rdoc_files.include('MIT-LICENSE')
|
228
|
+
rdoc.rdoc_files.include('lib/**/*.rb', 'doc/**/*.rdoc')
|
229
|
+
end
|
230
|
+
|
231
|
+
task :rdoc => "README"
|
232
|
+
end
|
data/TODO
ADDED
@@ -0,0 +1,13 @@
|
|
1
|
+
Things to do to improve the minitest integration
|
2
|
+
|
3
|
+
TODO:
|
4
|
+
|
5
|
+
* Make a separate gem for minitest (do we need one for given-core?)
|
6
|
+
|
7
|
+
DONE:
|
8
|
+
|
9
|
+
* Handle have_failed in minitest
|
10
|
+
* General cleanup making sure files go where they need.
|
11
|
+
* Implement assertion counting for minitest
|
12
|
+
* Figure out why the minitest example count is so low.
|
13
|
+
* Move stuff out of minitest_helper to appropriate file.
|
data/doc/main.rdoc
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
= Given/When/Then for RSpec
|
2
|
+
|
3
|
+
rspec-given is an RSpec extension to allow Given/When/Then notation in
|
4
|
+
RSpec specifications. It is a natural extension of the experimental
|
5
|
+
work done on the Given framework.
|
6
|
+
|
7
|
+
For more information see http://github.com/jimweirich/rspec-given
|
data/lib/given.rb
ADDED
data/lib/given/core.rb
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
|
2
|
+
# Require all the core features
|
3
|
+
|
4
|
+
require 'given/version'
|
5
|
+
require 'given/module_methods'
|
6
|
+
require 'given/file_cache'
|
7
|
+
require 'given/line_extractor'
|
8
|
+
require 'given/extensions'
|
9
|
+
require 'given/fuzzy_number'
|
10
|
+
require 'given/failure'
|
11
|
+
require 'given/failure_matcher'
|
@@ -0,0 +1,38 @@
|
|
1
|
+
|
2
|
+
module Given
|
3
|
+
class EvalErr
|
4
|
+
def initialize(str)
|
5
|
+
@string = str
|
6
|
+
end
|
7
|
+
def size
|
8
|
+
inspect.size
|
9
|
+
end
|
10
|
+
def to_s
|
11
|
+
@string
|
12
|
+
end
|
13
|
+
def inspect
|
14
|
+
@string
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
class Evaluator
|
19
|
+
def initialize(example, block)
|
20
|
+
@example = example
|
21
|
+
@block = block
|
22
|
+
end
|
23
|
+
|
24
|
+
def eval_string(exp_string)
|
25
|
+
eval_in_context(exp_string).inspect
|
26
|
+
rescue StandardError => ex
|
27
|
+
EvalErr.new("#{ex.class}: #{ex.message}")
|
28
|
+
end
|
29
|
+
|
30
|
+
private
|
31
|
+
|
32
|
+
def eval_in_context(exp_string)
|
33
|
+
exp_proc = "proc { #{exp_string} }"
|
34
|
+
blk = eval(exp_proc, @block.binding)
|
35
|
+
@example.instance_eval(&blk)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
# -*- coding: utf-8 -*-
|
2
|
+
|
3
|
+
module Given
|
4
|
+
module Ext
|
5
|
+
module Numeric
|
6
|
+
|
7
|
+
def ±(del=nil)
|
8
|
+
result = Given::Fuzzy::FuzzyNumber.new(self)
|
9
|
+
result.delta(del) if del
|
10
|
+
result
|
11
|
+
end
|
12
|
+
|
13
|
+
def ‰(percentage=nil)
|
14
|
+
result = Given::Fuzzy::FuzzyNumber.new(self)
|
15
|
+
result.percent(percentage) if percentage
|
16
|
+
result
|
17
|
+
end
|
18
|
+
|
19
|
+
def €(neps=nil)
|
20
|
+
result = Given::Fuzzy::FuzzyNumber.new(self)
|
21
|
+
result.epsilon(neps) if neps
|
22
|
+
result
|
23
|
+
end
|
24
|
+
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
class Numeric
|
30
|
+
include Given::Ext::Numeric
|
31
|
+
end
|
@@ -0,0 +1,242 @@
|
|
1
|
+
require 'given/module_methods'
|
2
|
+
require 'given/natural_assertion'
|
3
|
+
require 'given/failure'
|
4
|
+
|
5
|
+
module Given
|
6
|
+
|
7
|
+
# Provide run-time methods to support Given infrastructure. All the
|
8
|
+
# methods in this module are considered private and
|
9
|
+
# implementation-specific.
|
10
|
+
module InstanceExtensions # :nodoc:
|
11
|
+
|
12
|
+
# List of containing contexts in order from innermost to
|
13
|
+
# outermost.
|
14
|
+
def _gvn_inner_contexts # :nodoc:
|
15
|
+
self.class.ancestors.select { |context|
|
16
|
+
context.respond_to?(:_Gvn_givens)
|
17
|
+
}
|
18
|
+
end
|
19
|
+
|
20
|
+
# List of containing contexts in order from outermost to
|
21
|
+
# innermost.
|
22
|
+
def _gvn_contexts # :nodoc:
|
23
|
+
_gvn_inner_contexts.reverse
|
24
|
+
end
|
25
|
+
|
26
|
+
# Return the context information for keyword from the innermost
|
27
|
+
# defining context.
|
28
|
+
def _gvn_info(keyword) # :nodoc:
|
29
|
+
_gvn_inner_contexts.each do |context|
|
30
|
+
h = context._Gvn_context_info
|
31
|
+
if h.has_key?(keyword)
|
32
|
+
return h[keyword]
|
33
|
+
end
|
34
|
+
end
|
35
|
+
nil
|
36
|
+
end
|
37
|
+
|
38
|
+
# Should a natural assertion failure message be generated?
|
39
|
+
#
|
40
|
+
# A natural assertion failure message is generated if the
|
41
|
+
# assertion has non-empty content. The configuration options for
|
42
|
+
# natural assertions are checked and applied accordingly.
|
43
|
+
#
|
44
|
+
def _gvn_need_na_message?(nassert) # :nodoc:
|
45
|
+
return false unless nassert.has_content?
|
46
|
+
_gvn_na_configured?
|
47
|
+
end
|
48
|
+
|
49
|
+
# Return the configuration value for natural assertions.
|
50
|
+
#
|
51
|
+
# If natural assertions are not configured in the contexts, use
|
52
|
+
# the global configuration value.
|
53
|
+
def _gvn_na_configured? # :nodoc:
|
54
|
+
info_value = _gvn_info(:natural_assertions_enabled)
|
55
|
+
info_value.nil? ? Given.natural_assertions_enabled? : info_value
|
56
|
+
end
|
57
|
+
|
58
|
+
# Establish all the Given preconditions the current and
|
59
|
+
# surrounding describe/context blocks, starting with the
|
60
|
+
# outermost context.
|
61
|
+
def _gvn_establish_givens # :nodoc:
|
62
|
+
return if defined?(@_gvn_ran) && @_gvn_ran
|
63
|
+
@_gvn_ran = true
|
64
|
+
_gvn_contexts.each do |context|
|
65
|
+
context._Gvn_givens.each do |block|
|
66
|
+
instance_eval(&block)
|
67
|
+
end
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
# Check all the invariants in the current and surrounding
|
72
|
+
# describe/context blocks, starting with the outermost context.
|
73
|
+
def _gvn_check_invariants # :nodoc:
|
74
|
+
_gvn_contexts.each do |context|
|
75
|
+
context._Gvn_invariants.each do |block|
|
76
|
+
_gvn_evaluate("Invariant", block)
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
def _gvn_check_ands # :nodoc:
|
82
|
+
return if self.class._Gvn_context_info[:and_ran]
|
83
|
+
self.class._Gvn_and_blocks.each do |block|
|
84
|
+
_gvn_evaluate("And", block)
|
85
|
+
end
|
86
|
+
self.class._Gvn_context_info[:and_ran] = true
|
87
|
+
end
|
88
|
+
|
89
|
+
# Implement the run-time semantics of the Then clause.
|
90
|
+
def _gvn_then(&block) # :nodoc:
|
91
|
+
_gvn_establish_givens
|
92
|
+
_gvn_check_invariants
|
93
|
+
_gvn_evaluate("Then", block)
|
94
|
+
_gvn_check_ands
|
95
|
+
end
|
96
|
+
|
97
|
+
# Evaluate a Then, And, or Invariant assertion.
|
98
|
+
def _gvn_evaluate(clause_type, block) # :nodoc:
|
99
|
+
Given.framework.start_evaluation
|
100
|
+
passed = instance_eval(&block)
|
101
|
+
if ! Given.framework.explicit_assertions? && _gvn_na_configured?
|
102
|
+
_gvn_naturally_assert(clause_type, block, passed)
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
def _gvn_naturally_assert(clause_type, block, passed)
|
107
|
+
Given.framework.count_assertion
|
108
|
+
unless passed
|
109
|
+
nassert = NaturalAssertion.new(clause_type, block, self, self.class._Gvn_lines)
|
110
|
+
Given.fail_with nassert.message if _gvn_need_na_message?(nassert)
|
111
|
+
end
|
112
|
+
end
|
113
|
+
end
|
114
|
+
|
115
|
+
module ClassExtensions
|
116
|
+
|
117
|
+
# List of all givens directly in the current describe/context
|
118
|
+
# block.
|
119
|
+
def _Gvn_givens # :nodoc:
|
120
|
+
@_Gvn_givens ||= []
|
121
|
+
end
|
122
|
+
|
123
|
+
# List of all invariants directly in the current
|
124
|
+
# describe/context block.
|
125
|
+
def _Gvn_invariants # :nodoc:
|
126
|
+
@_Gvn_invariants ||= []
|
127
|
+
end
|
128
|
+
|
129
|
+
def _Gvn_and_blocks
|
130
|
+
@_Gvn_and_blocks ||= []
|
131
|
+
end
|
132
|
+
|
133
|
+
def _Gvn_context_info
|
134
|
+
@_Gvn_context_info ||= {}
|
135
|
+
end
|
136
|
+
|
137
|
+
def _Gvn_lines
|
138
|
+
@_Gvn_lines ||= LineExtractor.new
|
139
|
+
end
|
140
|
+
|
141
|
+
# Trigger the evaluation of a Given! block by referencing its
|
142
|
+
# name.
|
143
|
+
def _Gvn_trigger_given(name) # :nodoc:
|
144
|
+
Proc.new { send(name) }
|
145
|
+
end
|
146
|
+
|
147
|
+
# Declare a "given" of the current specification. If the given
|
148
|
+
# is named, the block will be lazily evaluated the first time
|
149
|
+
# the given is mentioned by name in the specification. If the
|
150
|
+
# given is unnamed, the block is evaluated for side effects
|
151
|
+
# every time the specification is executed.
|
152
|
+
#
|
153
|
+
# :call-seq:
|
154
|
+
# Given(:name) { ... code ... }
|
155
|
+
# Given { ... code ... }
|
156
|
+
#
|
157
|
+
def Given(*args, &block)
|
158
|
+
if args.first.is_a?(Symbol)
|
159
|
+
let(args.first, &block)
|
160
|
+
else
|
161
|
+
_Gvn_givens << block
|
162
|
+
end
|
163
|
+
end
|
164
|
+
|
165
|
+
# Declare a named given of the current specification. Similar
|
166
|
+
# to the named version of the "Given" command, except that the
|
167
|
+
# block is always evaluated.
|
168
|
+
#
|
169
|
+
# :call-seq:
|
170
|
+
# Given!(:name) { ... code ... }
|
171
|
+
#
|
172
|
+
def Given!(name, &block)
|
173
|
+
let(name, &block)
|
174
|
+
_Gvn_givens << _Gvn_trigger_given(name)
|
175
|
+
end
|
176
|
+
|
177
|
+
# Declare the code that is under test.
|
178
|
+
#
|
179
|
+
# :call-seq:
|
180
|
+
# When(:named_result) { ... code_under_test ... }
|
181
|
+
# When { ... code_under_test ... }
|
182
|
+
#
|
183
|
+
def When(*args, &block)
|
184
|
+
if args.first.is_a?(Symbol)
|
185
|
+
let(args.first) do
|
186
|
+
begin
|
187
|
+
_gvn_establish_givens
|
188
|
+
instance_eval(&block)
|
189
|
+
rescue Given.pending_error => ex
|
190
|
+
raise
|
191
|
+
rescue Exception => ex
|
192
|
+
Failure.new(ex)
|
193
|
+
end
|
194
|
+
end
|
195
|
+
_Gvn_before do __send__(args.first) end
|
196
|
+
else
|
197
|
+
_Gvn_before do
|
198
|
+
_gvn_establish_givens
|
199
|
+
instance_eval(&block)
|
200
|
+
end
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
# Provide an assertion about the specification.
|
205
|
+
#
|
206
|
+
# Then supplies an assertion that should be true after all the
|
207
|
+
# Given and When blocks have been run. All invariants in scope
|
208
|
+
# will be checked before the Then block is run.
|
209
|
+
#
|
210
|
+
# :call-seq:
|
211
|
+
# Then { ... assertion ... }
|
212
|
+
#
|
213
|
+
def Then(&block)
|
214
|
+
env = block.binding
|
215
|
+
file, line = eval "[__FILE__, __LINE__]", env
|
216
|
+
description = _Gvn_lines.line(file, line) unless Given.source_caching_disabled
|
217
|
+
if description
|
218
|
+
cmd = "it(description)"
|
219
|
+
else
|
220
|
+
cmd = "specify"
|
221
|
+
end
|
222
|
+
eval %{#{cmd} do _gvn_then(&block) end}, binding, file, line
|
223
|
+
_Gvn_context_info[:then_defined] = true
|
224
|
+
end
|
225
|
+
|
226
|
+
# Establish an invariant that must be true for all Then blocks
|
227
|
+
# in the current (and nested) scopes.
|
228
|
+
def Invariant(&block)
|
229
|
+
_Gvn_invariants << block
|
230
|
+
end
|
231
|
+
|
232
|
+
def And(&block)
|
233
|
+
fail "And defined without a Then" unless _Gvn_context_info[:then_defined]
|
234
|
+
_Gvn_and_blocks << block
|
235
|
+
end
|
236
|
+
|
237
|
+
def use_natural_assertions(enabled=true)
|
238
|
+
Given.ok_to_use_natural_assertions(enabled)
|
239
|
+
_Gvn_context_info[:natural_assertions_enabled] = enabled
|
240
|
+
end
|
241
|
+
end
|
242
|
+
end
|