Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Newer
Older
100644 469 lines (298 sloc) 21.649 kb
2e94ce4 @alexch capturing helper, rspec adapter
alexch authored
1 ## "Feels so right, it can't be Wrong"
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
2
47b05bc @alexch link to XKCD image
alexch authored
3 ![Someone is Wrong on the Internet](http://imgs.xkcd.com/comics/duty_calls.png)
4
49251e0 @sconover better readme
authored
5 ## Abstract ##
6
64be626 @alexch minor editing of README
alexch authored
7 Wrong provides a simple, general assert method that takes a block, and understands the code inside it, providing verbose failure messages for free.
8
9 The Wrong idea is to replace `assert_equal` and all those countless `assert\_this`, `assert\_that`, `should\_something` library methods which only exist to give a failure message that's not simply "assertion failed". Wrong replaces all of them in one fell swoop, since if you can write it in Ruby, Wrong can make a sensible failure message out of it.
0daa094 @sconover assert and deny methods that do a few things
authored
10
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
11 We'd very much appreciate feedback and bug reports. There are plenty of things left to be done to make the results look uniformly clean and beautiful. We want your feedback, and especially to give us cases where either it blows up or the output is ugly or uninformative.
49251e0 @sconover better readme
authored
12
f8ca07b @sconover readme update - jruby compatibility
authored
13 Inspired by [assert { 2.0 }](http://assert2.rubyforge.org/) but rewritten from scratch. Compatible with Ruby (MRI) 1.8, 1.9, and JRuby 1.5.
0daa094 @sconover assert and deny methods that do a few things
authored
14
a2ea516 @alexch preparing for 0.4.0 release, including wrong-jruby gem
alexch authored
15 ## Installation
16
17 gem install wrong
18
dbaf06a @alexch reads settings from a .wrong file
alexch authored
19 We have deployed gems for both Ruby and JRuby; if you get dependency issues on your platform, please let us know what Ruby interpreter and version you're using and what errors you get, and we'll try to track it down.
a2ea516 @alexch preparing for 0.4.0 release, including wrong-jruby gem
alexch authored
20
ad7e6d9 @alexch improve readme, bump version
alexch authored
21 ## Usage
49251e0 @sconover better readme
authored
22
d58901b @alexch improve docs
alexch authored
23 Wrong provides a simple assert method that takes a block:
49251e0 @sconover better readme
authored
24
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
25 require "wrong" # or require "wrong/adapters/rspec" (see below)
4e8fff3 @alexch registry for formatters
alexch authored
26
e511c4e @alexch "include Wrong" works since Wrong module now includes assert and help…
alexch authored
27 include Wrong
4e8fff3 @alexch registry for formatters
alexch authored
28
c5e9000 @alexch improve docs
alexch authored
29 assert { 1 == 1 }
49251e0 @sconover better readme
authored
30 ==> nil
4e8fff3 @alexch registry for formatters
alexch authored
31
c5e9000 @alexch improve docs
alexch authored
32 assert { 2 == 1 }
a663d37 @alexch documentation
alexch authored
33 ==> Expected (2 == 1), but 2 is not equal to 1
49251e0 @sconover better readme
authored
34
d58901b @alexch improve docs
alexch authored
35 If your assertion is more than a simple predicate, then Wrong will split it into parts and show you the values of all the relevant subexpressions.
36
37 x = 7; y = 10; assert { x == 7 && y == 11 }
38 ==>
a663d37 @alexch documentation
alexch authored
39 Expected ((x == 7) and (y == 11)), but
d58901b @alexch improve docs
alexch authored
40 (x == 7) is true
41 x is 7
42 (y == 11) is false
43 y is 10
c5e9000 @alexch improve docs
alexch authored
44
4493d7d @alexch update readme and examples
alexch authored
45 --
c5e9000 @alexch improve docs
alexch authored
46
47 age = 24
48 name = "Gaga"
49 assert { age >= 18 && ["Britney", "Snooki"].include?(name) }
50 ==>
57cfb53 @alexch examples for string and array diff
alexch authored
51 Expected ((age >= 18) and ["Britney", "Snooki"].include?(name)), but
c5e9000 @alexch improve docs
alexch authored
52 (age >= 18) is true
53 age is 24
54 ["Britney", "Snooki"].include?(name) is false
55 name is "Gaga"
56
49251e0 @sconover better readme
authored
57 And a companion, 'deny':
58
59 deny{'abc'.include?('bc')}
ae25366 @alexch docs & refactoring
alexch authored
60 ==> Didn't expect "abc".include?("bc")
b9776be @alexch 'd' takes a message
alexch authored
61
ad7e6d9 @alexch improve readme, bump version
alexch authored
62 More examples are in the file `examples.rb` <http://github.com/alexch/wrong/blob/master/examples.rb>
63
64 There's also a spreadsheet showing a translation from Test::Unit and RSpec to Wrong, with notes, at [this Google Doc](https://spreadsheets.google.com/pub?key=0AouPn6oLrimWdE0tZDVOWnFGMzVPZy0tWHZwdnhFYkE&hl=en&output=html). (Ask <alexch@gmail.com> if you want editing privileges.)
65
66 And don't miss the [slideshare presentation](http://www.slideshare.net/alexchaffee/wrong-5069976).
67
68 ## Helper methods
69
70 ### rescuing
49251e0 @sconover better readme
authored
71
d58901b @alexch improve docs
alexch authored
72 There's also a convenience method for catching errors:
49251e0 @sconover better readme
authored
73
619ff5a @alexch rename catch_raise to rescuing
alexch authored
74 assert{ rescuing{raise "vanilla"}.message == "chocolate" }
d58901b @alexch improve docs
alexch authored
75 ==>
ae25366 @alexch docs & refactoring
alexch authored
76 Expected (rescuing { raise("vanilla") }.message == "chocolate"), but
77 rescuing { raise("vanilla") }.message is "vanilla"
78 rescuing { raise("vanilla") } is #<RuntimeError: vanilla>
79 raise("vanilla") raises RuntimeError: vanilla
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
80
ad7e6d9 @alexch improve readme, bump version
alexch authored
81 ### capturing
82
2e94ce4 @alexch capturing helper, rspec adapter
alexch authored
83 And one for capturing output streams:
84
85 assert { capturing { puts "hi" } == "hi\n" }
86 assert { capturing(:stderr) { $stderr.puts "hi" } == "hi\n" }
e511c4e @alexch "include Wrong" works since Wrong module now includes assert and help…
alexch authored
87
2e94ce4 @alexch capturing helper, rspec adapter
alexch authored
88 out, err = capturing(:stdout, :stderr) { ... }
e511c4e @alexch "include Wrong" works since Wrong module now includes assert and help…
alexch authored
89 assert { out == "something standard\n" }
90 assert { err =~ /something erroneous/ }
2e94ce4 @alexch capturing helper, rspec adapter
alexch authored
91
ad7e6d9 @alexch improve readme, bump version
alexch authored
92 ### close_to?
93
c5e9000 @alexch improve docs
alexch authored
94 If you want to compare floats, try this:
95
96 assert { 5.0.close_to?(5.0001) } # default tolerance = 0.001
97 assert { 5.0.close_to?(5.1, 0.5) } # optional tolerance parameter
98
ad7e6d9 @alexch improve readme, bump version
alexch authored
99 If you don't want `close_to?` cluttering up `Float` in your test runs then use `include Wrong::Assert` instead of `include Wrong`.
100
101 ### d
e511c4e @alexch "include Wrong" works since Wrong module now includes assert and help…
alexch authored
102
f67567f @alexch behold the awesome power of d!
alexch authored
103 We also implement the most amazing debugging method ever, `d`, which gives you a sort of mini-wrong wherever you want it
104 , even in production code at runtime:
105
106 require 'wrong'
107 x = 7
108 d { x } # => prints "x is 7" to the console
109 d { x * 2 } # => prints "(x * 2) is 14" to the console
b9776be @alexch 'd' takes a message
alexch authored
110 d("math is hard") { 2 + 2 } #=> prints "math is hard: (2 + 2) is 4"
f67567f @alexch behold the awesome power of d!
alexch authored
111
ad7e6d9 @alexch improve readme, bump version
alexch authored
112 `d` was originally implemented by Rob Sanheim in LogBuddy; as with Assert2 this version is a rewrite and homage. You may also enjoy [g](https://github.com/jugyo/g) by [jugyo](http://jugyo.org/).
f67567f @alexch behold the awesome power of d!
alexch authored
113
ad7e6d9 @alexch improve readme, bump version
alexch authored
114 Remember, if you want `d` to work at runtime (e.g. in a webapp) then you must `include Wrong::D` inside your app, e.g. in your `environment.rb` file.
c5e9000 @alexch improve docs
alexch authored
115
cae852f @alexch eventually: docs, included in Wrong module
alexch authored
116 ### eventually
117
64be626 @alexch minor editing of README
alexch authored
118 If you care that something is going to be true *soon*, but maybe not *right* now, use `eventually`.
119
120 eventually { night? }
121
122 It will keep executing the block, up to 4 times a second, until either
cae852f @alexch eventually: docs, included in Wrong module
alexch authored
123
124 * the block returns true(ish)
125 * 5 seconds elapse
126
127 If the block raises an exception, then `eventually` will treat that as a false and keep trying. The last time it fails, it'll raise that exception instead of a mere `AssertionFailedError`. That way, the following are all possible:
128
129 eventually { false }
130 eventually { assert { false } }
131 eventually { false.should be_true } # in RSpec
132
133 and you should get the expected failure after time expires.
134
135 You can also send options to eventually as hash parameters.
136
137 eventually(:timeout => 10) { false } # keep trying for 10 sec
138 eventually(:delay => 1) { false } # try every 1.0 sec, not every 0.25 sec
139
140 (For now, `eventually` is in its own module, but you get it when you `include Wrong`. Maybe it should be in Helpers like the rest?)
141
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
142 ## Test Framework Adapters ##
143
144 Adapters for various test frameworks sit under wrong/adapters.
145
146 Currently we support
147
148 * Test::Unit - `require 'wrong/adapters/test_unit'`
149 * Minitest - `require 'wrong/adapters/minitest'`
150 * RSpec - `require 'wrong/adapters/rspec'` (now supports both 1.3 and 2.0)
151
152 To use these, put the appropriate `require` in your helper, **after** requiring your test framework; it should extend the framework enough that you can use `assert { }` in your test cases without extra fussing around.
153
154 For example:
155
156 require "test/unit"
157 require "wrong/adapters/test_unit"
158 class PlusTest < Test::Unit::TestCase
159 def test_adding_two_and_two
160 assert { 2 + 2 == 4 }
161 end
162 end
163
164 ---
165
166 require "rspec"
167 require "wrong/adapters/rspec"
168 describe "plus" do
169 it "adds two and two" do
170 assert { 2 + 2 == 4 }
171 end
172 end
173
2d53e78 @alexch Piecemeal Usage section
alexch authored
174 ## Piecemeal Usage ##
175
6289c7d @sconover added state change gotcha to the readme
authored
176 We know that sometimes you don't want all the little doodads from a library cluttering up your namespace. If you **don't** want to do
2d53e78 @alexch Piecemeal Usage section
alexch authored
177
178 require 'wrong'
179 include Wrong
180
181 then you can instead `require` and `include` just the bits you really want. For example:
182
183 require 'wrong/assert'
184 include Wrong::Assert
185
186 will give you the `assert` and `deny` methods but not the formatters or `rescuing` or `d` or `close_to?`. And if all you want is `d` then do:
187
188 require 'wrong/d'
189 include Wrong::D
190
ae25366 @alexch docs & refactoring
alexch authored
191 To summarize: if you do `require 'wrong'` and `include Wrong` then you will get the whole ball of wax. Most people will probably want this since it's easier, but there is an alternative, which is to `require` and `include` only what you want.
2d53e78 @alexch Piecemeal Usage section
alexch authored
192
193 And beware: if you don't `require 'wrong'`, then `include Wrong` will not do anything at all.
194
6289c7d @sconover added state change gotcha to the readme
authored
195 ## Gotcha: Side Effects Within the Assert Block ##
196
197 Be careful about making calls within the assert block that cause state changes.
198
199 @x = 1
200 def increment
201 @x += 1
202 end
203
204 assert { increment == 2 }
205 assert { increment == 2 }
206 ==> Expected (increment == 2), but
207 increment is 5
208
209 The first time increment fires the result is 2. The second time the result is 3, and then Wrong introspects the block to create a good failure message, causing increment to fire a couple more times.
210
211 Confusing, we know! A few patient Wrong users have hit this when the assert involves ActiveRecord write methods like #create! and #save.
212
2e2df43 @sconover minor correction
authored
213 The fix: introduce a variable:
6289c7d @sconover added state change gotcha to the readme
authored
214
215 value = increment
216 assert { value == 2 }
217 assert { value == 2 }
218
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
219 ## Apology ##
220
221 So does the world need another assertion framework? In fact, it does not! We actually believe the world needs **fewer** assert methods.
222
15cf806 @alexch tests for Chunk#details
alexch authored
223 The Wrong idea is to replace all those countless assert\_this, assert\_that, should\_something library methods which only exist to give a more useful failure message than "assertion failed". Wrong replaces all of them in one fell swoop, since if you can write it in Ruby, Wrong can make a sensible failure message out of it.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
224
225 Even the lowly workhorse `assert_equal` is bloated compared to Wrong: would you rather write this
226
227 assert_equal time, money
228
229 or this
230
231 assert { time == money }
232
c5e9000 @alexch improve docs
alexch authored
233 ? The Wrong way has the advantage of being plain, transparent Ruby code, not an awkward DSL that moves "equal" out of its natural place between the comparands. Plus, WYSIWYG! You know just from looking at it that "equal" means `==`, not `eql?` or `===` or `=~`.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
234
f9bf737 @alexch README improvements
alexch authored
235 Moreover, much like TDD itself, Wrong encourages you to write cleaner code. If your assertion messages are not clear and "Englishy", then maybe it's time for you to refactor a bit -- extract an informatively named variable or method, maybe push some function onto its natural object *a la* the [Law of Demeter](http://en.wikipedia.org/wiki/Law_of_Demeter)...
dbaf06a @alexch reads settings from a .wrong file
alexch authored
236 Also, try not to call any methods with side effects inside an assert. In addition to being bad form, this can cause messed-up failure messages, since the side effects may occur several times in the process of building the message.
f9bf737 @alexch README improvements
alexch authored
237
238 Wrong also lets you put the expected and actual values in any order you want! Consider the failure messages for
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
239
240 assert { current_user == "joe" } # => Expected (current_user == "joe") but current_user is "fred"
241 assert { "joe" == current_user } # => Expected ("joe" == current_user) but current_user is "fred"
242
dbaf06a @alexch reads settings from a .wrong file
alexch authored
243 You get all the information you want, and none you don't want. At least, that's the plan! :-)
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
244
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
245 ## BDD with Wrong ##
246
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
247 Wrong is compatible with RSpec and MiniTest::Spec, and probably Cucumber too, so you can use it inside your BDD framework of choice. To make your test code even BDD-er, try aliasing `assert` to either `should` or (Alex's favorite) `expect`.
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
248
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
249 Here's an RSpec example:
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
250
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
251 require "wrong"
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
252 require "wrong/adapters/rspec"
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
253 Wrong.config.alias_assert :expect_that
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
254
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
255 describe BleuCheese do
256 it "stinks" do
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
257 expect_that { BleuCheese.new.smell > 9000 }
258 end
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
259 end
260
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
261 This makes your code read like a BDD-style DSL, without RSpec's "should" syntax (which is, let's face it, pretty weird the first few hundred times you have to use it). Compare
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
262
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
263 expect_that { BleuCheese.new.smell > 9000 }
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
264
265 to
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
266
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
267 BleuCheese.new.smell.should > 9000
268
6784c00 @alexch update README to advertise 'expect' not working in RSpec https://gith…
alexch authored
269 and consider which one more clearly describes the desired behavior. The object under test doesn't really have a `should` method, so why should it magically get one during a test? And in what human language is "should greater than" a valid phrase?
0d183e6 @alexch 'BDD with Wrong' section added to readme
alexch authored
270
f8bdcc5 @alexch rspec expect fix works in rspec1, bump version to 0.5.1, fix flaky ya…
alexch authored
271 Warning: currently the use of `alias_assert :expect` is **not** compatible with RSpec, since RSpec also defines `expect` as a synonym for `lambda`. If you really want to use `expect` as an alias form `assert`, then use `Wrong.config.alias_assert :expect, :override => true`. See [issue #6](https://github.com/sconover/wrong/issues/6) for more details.
272
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
273 ## Algorithm ##
274
838bbbe @alexch wrap and indent long values
alexch authored
275 So wait a second. How do we do it? Doesn't Ruby have [poor support for AST introspection](http://blog.zenspider.com/2009/04/parsetree-eol.html)? Well, yes, it does, so we cheat: we figure out what file and line the assert block is defined in, then open the file, read the code, and parse it directly using Ryan Davis' amazing [RubyParser](http://parsetree.rubyforge.org/ruby_parser/) and [Ruby2Ruby](http://seattlerb.rubyforge.org/ruby2ruby/). You can bask in the kludge by examining `chunk.rb` and `assert.rb`. If you find some code it can't parse, please send it our way. As a failsafe we also use Sourcify, which has yet another home baked RACC parser, so we have many chances to parse your code.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
276
277 Before you get your knickers in a twist about how this is totally unacceptable because it doesn't support this or that use case, here are our caveats and excuses:
278
dbaf06a @alexch reads settings from a .wrong file
alexch authored
279 * It works! Tested in MRI 1.8.6, 1.8.7, 1.9.1, 1.9.2, and JRuby 1.5.3. (Thank you, [rvm](http://rvm.beginrescueend.com/)!)
67cdb82 @alexch make it work in IRB
alexch authored
280 * Your code needs to be in a file.
281 * If you're developing Ruby code without saving it to a mounted disk, then sorry, Wrong is not right for you.
dbaf06a @alexch reads settings from a .wrong file
alexch authored
282 * We monkey-patch IRB so if you do `irb -rwrong` it'll save off your session in memory where Wrong can read it.
838bbbe @alexch wrap and indent long values
alexch authored
283 * It'd be nice if it could work inside a `-e` block but as far as we can tell, there's no way to grab that `-e` source code from inside Ruby.
df58c10 @alexch readme
alexch authored
284 * It's a development-time testing library, not a production runtime library, so there are no security or filesystem issues.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
285 * `eval` isn't evil, it's just misunderstood.
286 * It makes a few assumptions about the structure of your code, leading to some restrictions:
dbaf06a @alexch reads settings from a .wrong file
alexch authored
287 * You can't have more than one call to `assert` per line. (This should not be a problem since even if you're nesting asserts for some bizarre reason, we assume you know where your Return key is.)
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
288 * You can't use metaprogramming to write your assert blocks.
dbaf06a @alexch reads settings from a .wrong file
alexch authored
289 * All variables and methods must be available in the binding of the assert block.
290 * Passing a proc around and eventually calling assert on it might not work in some Ruby implementations.
f9c6949 @alexch a few tweaks
alexch authored
291 * Beware of Side Effects! (See discussion elsewhere in this document.)
838bbbe @alexch wrap and indent long values
alexch authored
292 * "Doesn't all this parsing slow down my test run"? No - this applies to failure cases only. If the assert block returns true then Wrong simply moves on.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
293
294 ## Explanations ##
295
296 `assert` and `deny` can take an optional explanation, e.g.
297
298 assert("since we're on Earth") { sky.blue? }
299
838bbbe @alexch wrap and indent long values
alexch authored
300 Since the point of Wrong is to make asserts self-explanatory, you should use explanations only when they would add something that you couldn't get from reading the (failed) assertion code itself. Don't bother doing things like this:
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
301
302 assert("the sky should be blue") { sky.blue? } # redundant
303
8821fff @alexch minor readme edit
alexch authored
304 The failure message of the above would be something like "`Expected sky.blue? but sky is :green`" which is not made clearer by the addition of "`the sky should be blue`". We already know it should be blue since we see right there ("`Expected (sky.blue?)`") that we're expecting it to be blue.
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
305
f9bf737 @alexch README improvements
alexch authored
306 And if your assertion code isn't self-explanatory, then that's a hint that you might need to do some refactoring until it is. (Yes, even test code should be clean as a whistle. **Especially** test code.)
307
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
308 ## Details ##
309
310 When a failure occurs, the exception message contains all the details you might need to make sense of it. Here's the breakdown:
311
ae25366 @alexch docs & refactoring
alexch authored
312 Expected [CLAIM], but
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
313 [FORMATTER]
314 [SUBEXP] is [VALUE]
315 ...
316
4e8fff3 @alexch registry for formatters
alexch authored
317 * CLAIM is the code inside your assert block, normalized
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
318 * If there is a formatter registered for this type of predicate, its output will come next. (See below.)
319 * SUBEXP is each of the subtrees of the claim, minus duplicates and truisms (e.g. literals).
4e8fff3 @alexch registry for formatters
alexch authored
320 * The word "is" is a very nice separator since it doesn't look like code, but is short enough to be easily visually parsed.
838bbbe @alexch wrap and indent long values
alexch authored
321 * VALUE is `eval(SUBEXP).inspect`, wrapped and indented if necessary to fit your console
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
322
323 We hope this structure lets your eyes focus on the meaningful values and differences in the message, rather than glossing over with stack-trace burnout. If you have any suggestions on how to improve it, please share them.
324
325 (Why does VALUE use `inspect` and not `to_s`? Because `inspect` on standard objects like String and Array are sure to show all relevant details, such as white space, in a console-safe way, and we hope other libraries follow suit. Also, `to_s` often inserts line breaks and that messes up formatting and legibility.)
326
838bbbe @alexch wrap and indent long values
alexch authored
327 Wrong tries to maintain indentation to improve readability. If the inspected VALUE contains newlines, or is longer than will fit on your console, the succeeding lines will be indented to a pleasant level.
ae25366 @alexch docs & refactoring
alexch authored
328
b9776be @alexch 'd' takes a message
alexch authored
329 Sometimes Wrong will not be able to evaluate a detail without raising an exception. This exception will be duly noted, which might be misleading. For example,
ad7e6d9 @alexch improve readme, bump version
alexch authored
330
331 a = [1,2,3,4]
332 assert { a.all? {|i| i<4} }
b9776be @alexch 'd' takes a message
alexch authored
333
ad7e6d9 @alexch improve readme, bump version
alexch authored
334 would fail, since on the final pass, `(i < 4)` is false. But the error message is a bit vague:
335
336 Wrong::Assert::AssertionFailedError: Expected a.all? { |i| (i < 4) }, but
337 i raises NameError: undefined local variable or method `i' for main:Object
338
339 In evaluating the inner expression, Wrong does not have access to the block parameter `i`, since `i` is not in the scope of the outer expression. A better way to write the assertion would be
340
341 a = [1,2,3,4]
342 a.each {|i| assert {i < 4}}
343
344 which gives
345
346 Wrong::Assert::AssertionFailedError: Expected (i < 4), but
347 i is 4
348
4493d7d @alexch update readme and examples
alexch authored
349 ## Formatters ##
ae247de @sconover update gemspec, readme
authored
350
351 Enhancements for error messages sit under wrong/message.
352
f9bf737 @alexch README improvements
alexch authored
353 Currently we support special messages for
df58c10 @alexch readme
alexch authored
354
f9bf737 @alexch README improvements
alexch authored
355 * String ==
ae25366 @alexch docs & refactoring
alexch authored
356 * Array(ish) ==
f9bf737 @alexch README improvements
alexch authored
357 * including nested string elements
626326f @alexch wrote a lot of words, plus refactored and made depth work for 1.8 ext…
alexch authored
358
ae25366 @alexch docs & refactoring
alexch authored
359 To use the Array formatter, you may also need to `gem install diff-lcs` (it's an optional dependency).
57cfb53 @alexch examples for string and array diff
alexch authored
360
a2e5947 @alexch remove predicated sentence from failure message
alexch authored
361 require "wrong/message/string_comparison"
57cfb53 @alexch examples for string and array diff
alexch authored
362 assert { "the quick brown fox jumped over the lazy dog" ==
363 "the quick brown hamster jumped over the lazy gerbil" }
364 ==>
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
365 Expected ("the quick brown fox jumped over the lazy dog" == "the quick brown hamster jumped over the lazy gerbil"), but
366 Strings differ at position 16:
367 first: ..."quick brown fox jumped over the lazy dog"
368 second: ..."quick brown hamster jumped over the lazy gerbil"
369
370 ---
57cfb53 @alexch examples for string and array diff
alexch authored
371
372 require "wrong/message/array_diff"
373 assert { ["venus", "mars", "pluto", "saturn"] ==
374 ["venus", "earth", "pluto", "neptune"] }
375 ==>
376 Expected (["venus", "mars", "pluto", "saturn"] == ["venus", "earth", "pluto", "neptune"]), but ["venus", "mars", "pluto", "saturn"] is not equal to ["venus", "earth", "pluto", "neptune"]
377
378 array diff:
379 ["venus", "mars" , "pluto", "saturn" ]
380 ["venus", "earth", "pluto", "neptune"]
381 ^ ^
382
dbaf06a @alexch reads settings from a .wrong file
alexch authored
383 ## Config ##
384
385 These settings can either be set at runtime on the `Wrong.config` singleton, or inside a `.wrong` file in the current directory or a parent. In the `.wrong` file just pretend every line is preceded with `Wrong.config.` -- e.g. if there's a setting called `ice_cream`, you can do any of these in your `.wrong` file
386
387 ice_cream # => Wrong.config[:ice_cream] => true
388 ice_cream = true # => Wrong.config[:ice_cream] => true
389 ice_cream = "vanilla" # => Wrong.config[:ice_cream] => "vanilla"
390
391 or any of these at runtime:
392
393 Wrong.config.ice_cream # => Wrong.config[:ice_cream] => true
394 Wrong.config.ice_cream = true # => Wrong.config[:ice_cream] => true
395 Wrong.config.ice_cream = "vanilla" # => Wrong.config[:ice_cream] => "vanilla"
396
397 ### Color ###
398
838bbbe @alexch wrap and indent long values
alexch authored
399 Apparently, no test framework is successful unless and until it supports console colors. Call
dbaf06a @alexch reads settings from a .wrong file
alexch authored
400
401 Wrong.config.color
a663d37 @alexch documentation
alexch authored
402
dbaf06a @alexch reads settings from a .wrong file
alexch authored
403 in your test helper or rakefile or wherever, or put
a663d37 @alexch documentation
alexch authored
404
dbaf06a @alexch reads settings from a .wrong file
alexch authored
405 color
a663d37 @alexch documentation
alexch authored
406
dbaf06a @alexch reads settings from a .wrong file
alexch authored
407 in your `.wrong` file and get ready to be **bedazzled**. If you need custom colors, let us know.
a663d37 @alexch documentation
alexch authored
408
dbaf06a @alexch reads settings from a .wrong file
alexch authored
409 ### Aliases ###
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
410
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
411 An end to the language wars! Name your "assert" and "deny" methods anything you want.
b33ae6a @alexch refactoring: pull methods into FailureMessage object
alexch authored
412
413 * In your code, use `Wrong.config.alias_assert` and `Wrong.config.alias_deny`
414 * In your `.wrong` file, put `alias_assert :expect` on a line by itself
415
416 Here are some suggestions:
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
417
e057d83 @alexch improve documentation https://github.com/sconover/wrong/issues/8
alexch authored
418 alias_assert :expect # warning: not compatible with RSpec
dbaf06a @alexch reads settings from a .wrong file
alexch authored
419 alias_assert :should # This looks nice in RSpec
420 alias_assert :confirm
421 alias_assert :be
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
422
dbaf06a @alexch reads settings from a .wrong file
alexch authored
423 alias_assert :is
424 alias_deny :aint
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
425
dbaf06a @alexch reads settings from a .wrong file
alexch authored
426 alias_assert :assure
427 alias_deny :refute
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
428
dbaf06a @alexch reads settings from a .wrong file
alexch authored
429 alias_assert :yep
430 alias_deny :nope
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
431
dbaf06a @alexch reads settings from a .wrong file
alexch authored
432 alias_assert :yay!
433 alias_deny :boo!
80ad5d7 @alexch alias_assert and alias_deny (a truce in the language wars\!)
alexch authored
434
435 Just don't use "`aver`" since we took that one for an internal method in `Wrong::Assert`.
436
44fb83a @alexch verbose mode
alexch authored
437 ### Verbose ###
438
439 Wrong works inside frameworks like Test::Unit and RSpec, but sometimes you just want to stick a bunch of assertions in a file and run it. In that case, *verbose mode* might come in handy. It prints every *successful* assertion to the console (including explanations, if provided, and in color, if desired).
440
441 Wrong.config.verbose
442 assert("basic math") { 2 + 2 == 4}
443
444 prints
445
446 basic math: ((2 + 2) == 4)
447
448
a8ea79b @alexch minor readme cleanup
alexch authored
449 ## Helper Assert Methods ##
450
2d53e78 @alexch Piecemeal Usage section
alexch authored
451 If you really want to, you can define your proc in one method, pass it in to another method, and have that method assert it. This is a challenge for Wrong and you probably shouldn't do it. Wrong will do its best to figure out where the actual assertion code is but it might not succeed.
a8ea79b @alexch minor readme cleanup
alexch authored
452
453 If you're in Ruby 1.8, you **really** shouldn't do it! But if you do, you can use the "depth" parameter to give Wrong a better hint about how far up the stack it should crawl to find the code. See `assert_test.rb` for more details, if you dare.
454
d58901b @alexch improve docs
alexch authored
455 ## Authors ##
456
457 * Steve Conover - <sconover@gmail.com>
458 * Alex Chaffee - <alex@stinky.com> - <http://alexch.github.com>
f97bd30 @alexch adding John and Thierry to README
alexch authored
459 * John Firebaugh
460 * Thierry Henrio
d58901b @alexch improve docs
alexch authored
461
49251e0 @sconover better readme
authored
462 ## Etc ##
463
dbaf06a @alexch reads settings from a .wrong file
alexch authored
464 * Mailing list: <http://groups.google.com/group/wrong-rb>
465 * Github project: <http://github.com/sconover/wrong>
2e94ce4 @alexch capturing helper, rspec adapter
alexch authored
466 * Tracker project: <http://www.pivotaltracker.com/projects/109993>
7c20354 @alexch omit some unparsable parts; improve docs
alexch authored
467 * the [Wrong way translation table (from RSpec and Test::Unit)](https://spreadsheets.google.com/pub?key=0AouPn6oLrimWdE0tZDVOWnFGMzVPZy0tWHZwdnhFYkE&hl=en&output=html). (Ask <alexch@gmail.com> if you want editing privileges.)
468 * the [Wrong slides](http://www.slideshare.net/alexchaffee/wrong-5069976) that Alex presented at Carbon Five and GoGaRuCo
Something went wrong with that request. Please try again.