set_builder 2.0.0.beta2 → 2.0.0.beta3

Sign up to get free protection for your applications and to get access to all the features.
Files changed (48) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +6 -6
  3. data/Rakefile +2 -2
  4. data/init.rb +1 -1
  5. data/lib/assets/javascripts/set_builder.js +122 -125
  6. data/lib/set_builder/constraint.rb +66 -50
  7. data/lib/set_builder/errors/trait_not_found.rb +3 -0
  8. data/lib/set_builder/modifier/adverb.rb +4 -4
  9. data/lib/set_builder/modifier/base.rb +74 -67
  10. data/lib/set_builder/modifier/verb.rb +1 -16
  11. data/lib/set_builder/modifier.rb +49 -49
  12. data/lib/set_builder/modifier_collection.rb +16 -16
  13. data/lib/set_builder/modifiers/date_preposition.rb +6 -48
  14. data/lib/set_builder/modifiers/number_preposition.rb +4 -25
  15. data/lib/set_builder/modifiers/string_preposition.rb +9 -43
  16. data/lib/set_builder/modifiers.rb +3 -3
  17. data/lib/set_builder/set.rb +48 -8
  18. data/lib/set_builder/trait.rb +75 -49
  19. data/lib/set_builder/traits.rb +13 -4
  20. data/lib/set_builder/value_map.rb +30 -30
  21. data/lib/set_builder/version.rb +1 -1
  22. data/lib/set_builder.rb +8 -7
  23. data/set_builder.gemspec +4 -2
  24. data/spec/commands/example_command.rb +2 -2
  25. data/spec/lib/jspec.css +4 -4
  26. data/spec/lib/jspec.growl.js +11 -11
  27. data/spec/lib/jspec.jquery.js +14 -14
  28. data/spec/lib/jspec.js +210 -210
  29. data/spec/lib/jspec.nodejs.js +2 -2
  30. data/spec/lib/jspec.shell.js +11 -11
  31. data/spec/lib/jspec.timers.js +23 -23
  32. data/spec/rhino.js +1 -1
  33. data/spec/server.rb +1 -1
  34. data/spec/unit/array.spec.js +9 -9
  35. data/spec/unit/set_builder.spec.js +71 -82
  36. data/spec/unit/spec.helper.js +1 -0
  37. data/test/constraint_test.rb +84 -0
  38. data/test/date_preposition_test.rb +17 -7
  39. data/test/modifier_test.rb +26 -1
  40. data/test/set_test.rb +51 -28
  41. data/test/string_preposition_test.rb +10 -9
  42. data/test/test_helper.rb +17 -15
  43. data/test/trait_test.rb +49 -30
  44. data/test/traits_test.rb +35 -30
  45. data/test/value_map_test.rb +1 -1
  46. metadata +37 -15
  47. data/lib/set_builder/query_builders/string.rb +0 -0
  48. data/test/inflector_test.rb +0 -27
data/spec/lib/jspec.js CHANGED
@@ -35,9 +35,9 @@
35
35
  */
36
36
 
37
37
  defaultContext : {
38
-
38
+
39
39
  /**
40
- * Return an object used for proxy assertions.
40
+ * Return an object used for proxy assertions.
41
41
  * This object is used to indicate that an object
42
42
  * should be an instance of _object_, not the constructor
43
43
  * itself.
@@ -46,11 +46,11 @@
46
46
  * @return {hash}
47
47
  * @api public
48
48
  */
49
-
49
+
50
50
  an_instance_of : function(constructor) {
51
51
  return { an_instance_of : constructor }
52
52
  },
53
-
53
+
54
54
  /**
55
55
  * Load fixture at _path_.
56
56
  *
@@ -63,14 +63,14 @@
63
63
  * @return {string}
64
64
  * @api public
65
65
  */
66
-
66
+
67
67
  fixture : function(path) {
68
68
  if (JSpec.cache[path]) return JSpec.cache[path]
69
- return JSpec.cache[path] =
69
+ return JSpec.cache[path] =
70
70
  JSpec.tryLoading(JSpec.options.fixturePath + '/' + path) ||
71
71
  JSpec.tryLoading(JSpec.options.fixturePath + '/' + path + '.html')
72
72
  },
73
-
73
+
74
74
  /**
75
75
  * Load json fixture at _path_.
76
76
  *
@@ -83,7 +83,7 @@
83
83
  * @return {object}
84
84
  * @api public
85
85
  */
86
-
86
+
87
87
  json_fixture: function(path) {
88
88
  if (!JSpec.cache['json:' + path])
89
89
  JSpec.cache['json:' + path] =
@@ -98,12 +98,12 @@
98
98
  },
99
99
 
100
100
  // --- Objects
101
-
101
+
102
102
  reporters : {
103
-
103
+
104
104
  /**
105
105
  * Report to server.
106
- *
106
+ *
107
107
  * Options:
108
108
  * - uri specific uri to report to.
109
109
  * - verbose weither or not to output messages
@@ -111,7 +111,7 @@
111
111
  *
112
112
  * @api public
113
113
  */
114
-
114
+
115
115
  Server : function(results, options) {
116
116
  var uri = options.uri || 'http://' + window.location.host + '/results'
117
117
  JSpec.post(uri, {
@@ -130,7 +130,7 @@
130
130
  'fail',
131
131
  assertions: map(spec.assertions, function(assertion){
132
132
  return {
133
- passed: assertion.passed
133
+ passed: assertion.passed
134
134
  }
135
135
  })
136
136
  }
@@ -157,14 +157,14 @@
157
157
  failuresOnly = option('failuresOnly'),
158
158
  classes = results.stats.failures ? 'has-failures' : ''
159
159
  if (!report) throw 'JSpec requires the element #' + id + ' to output its reports'
160
-
160
+
161
161
  function bodyContents(body) {
162
162
  return JSpec.
163
163
  escape(JSpec.contentsOf(body)).
164
164
  replace(/^ */gm, function(a){ return (new Array(Math.round(a.length / 3))).join(' ') }).
165
165
  replace(/\r\n|\r|\n/gm, '<br/>')
166
166
  }
167
-
167
+
168
168
  report.innerHTML = '<div id="jspec-report" class="' + classes + '"><div class="heading"> \
169
169
  <span class="passes">Passes: <em>' + results.stats.passes + '</em></span> \
170
170
  <span class="failures">Failures: <em>' + results.stats.failures + '</em></span> \
@@ -180,7 +180,7 @@
180
180
  (spec.passed() && !failuresOnly) ?
181
181
  '<td class="pass">' + escape(spec.description)+ '</td><td>' + spec.assertionsGraph() + '</td>' :
182
182
  !spec.passed() ?
183
- '<td class="fail">' + escape(spec.description) +
183
+ '<td class="fail">' + escape(spec.description) +
184
184
  map(spec.failures(), function(a){ return '<em>' + escape(a.message) + '</em>' }).join('') +
185
185
  '</td><td>' + spec.assertionsGraph() + '</td>' :
186
186
  '') +
@@ -188,23 +188,23 @@
188
188
  }).join('') + '</tr>'
189
189
  }).join('') + '</table></div>'
190
190
  },
191
-
191
+
192
192
  /**
193
193
  * Terminal reporter.
194
194
  *
195
195
  * @api public
196
196
  */
197
-
197
+
198
198
  Terminal : function(results, options) {
199
199
  var failuresOnly = option('failuresOnly')
200
- print(color("\n Passes: ", 'bold') + color(results.stats.passes, 'green') +
200
+ print(color("\n Passes: ", 'bold') + color(results.stats.passes, 'green') +
201
201
  color(" Failures: ", 'bold') + color(results.stats.failures, 'red') +
202
202
  color(" Duration: ", 'bold') + color(results.duration, 'green') + " ms \n")
203
-
203
+
204
204
  function indent(string) {
205
205
  return string.replace(/^(.)/gm, ' $1')
206
206
  }
207
-
207
+
208
208
  each(results.allSuites, function(suite) {
209
209
  var displaySuite = failuresOnly ? suite.ran && !suite.passed() : suite.ran
210
210
  if (displaySuite && suite.isExecutable()) {
@@ -218,17 +218,17 @@
218
218
  else if (spec.passed() && !failuresOnly)
219
219
  print(color(' ' + spec.description, 'green') + assertionsGraph)
220
220
  else if (!spec.passed())
221
- print(color(' ' + spec.description, 'red') + assertionsGraph +
221
+ print(color(' ' + spec.description, 'red') + assertionsGraph +
222
222
  "\n" + indent(map(spec.failures(), function(a){ return a.message }).join("\n")) + "\n")
223
223
  })
224
224
  print("")
225
225
  }
226
226
  })
227
-
227
+
228
228
  quit(results.stats.failures)
229
229
  }
230
230
  },
231
-
231
+
232
232
  Assertion : function(matcher, actual, expected, negate) {
233
233
  extend(this, {
234
234
  message: '',
@@ -237,19 +237,19 @@
237
237
  negate: negate,
238
238
  matcher: matcher,
239
239
  expected: expected,
240
-
240
+
241
241
  // Report assertion results
242
-
242
+
243
243
  report : function() {
244
- if (JSpec.assert)
244
+ if (JSpec.assert)
245
245
  this.passed ? JSpec.stats.passes++ : JSpec.stats.failures++
246
246
  return this
247
247
  },
248
-
248
+
249
249
  // Run the assertion
250
-
250
+
251
251
  run : function() {
252
- // TODO: remove unshifting
252
+ // TODO: remove unshifting
253
253
  expected.unshift(actual)
254
254
  this.result = matcher.match.apply(this, expected)
255
255
  this.passed = negate ? !this.result : this.result
@@ -258,27 +258,27 @@
258
258
  }
259
259
  })
260
260
  },
261
-
261
+
262
262
  ProxyAssertion : function(object, method, times, negate) {
263
263
  var self = this,
264
264
  old = object[method]
265
-
265
+
266
266
  // Proxy
267
-
267
+
268
268
  object[method] = function(){
269
269
  var args = toArray(arguments),
270
270
  result = old.apply(object, args)
271
271
  self.calls.push({ args : args, result : result })
272
272
  return result
273
273
  }
274
-
274
+
275
275
  // Times
276
-
276
+
277
277
  this.times = {
278
278
  once : 1,
279
279
  twice : 2
280
280
  }[times] || times || 1
281
-
281
+
282
282
  extend(this, {
283
283
  calls: [],
284
284
  message: '',
@@ -287,23 +287,23 @@
287
287
  negate: negate,
288
288
  object: object,
289
289
  method: method,
290
-
290
+
291
291
  // Proxy return value
292
-
292
+
293
293
  and_return : function(result) {
294
294
  this.expectedResult = result
295
295
  return this
296
296
  },
297
-
297
+
298
298
  // Proxy arguments passed
299
-
299
+
300
300
  with_args : function() {
301
301
  this.expectedArgs = toArray(arguments)
302
302
  return this
303
303
  },
304
-
304
+
305
305
  // Check if any calls have failing results
306
-
306
+
307
307
  anyResultsFail : function() {
308
308
  return any(this.calls, function(call){
309
309
  return self.expectedResult.an_instance_of ?
@@ -311,9 +311,9 @@
311
311
  !equal(self.expectedResult, call.result)
312
312
  })
313
313
  },
314
-
314
+
315
315
  // Check if any calls have passing results
316
-
316
+
317
317
  anyResultsPass : function() {
318
318
  return any(this.calls, function(call){
319
319
  return self.expectedResult.an_instance_of ?
@@ -321,21 +321,21 @@
321
321
  equal(self.expectedResult, call.result)
322
322
  })
323
323
  },
324
-
324
+
325
325
  // Return the passing result
326
-
326
+
327
327
  passingResult : function() {
328
328
  return this.anyResultsPass().result
329
329
  },
330
330
 
331
331
  // Return the failing result
332
-
332
+
333
333
  failingResult : function() {
334
334
  return this.anyResultsFail().result
335
335
  },
336
-
336
+
337
337
  // Check if any arguments fail
338
-
338
+
339
339
  anyArgsFail : function() {
340
340
  return any(this.calls, function(call){
341
341
  return any(self.expectedArgs, function(i, arg){
@@ -343,73 +343,73 @@
343
343
  return arg.an_instance_of ?
344
344
  call.args[i].constructor != arg.an_instance_of:
345
345
  !equal(arg, call.args[i])
346
-
346
+
347
347
  })
348
348
  })
349
349
  },
350
-
350
+
351
351
  // Check if any arguments pass
352
-
352
+
353
353
  anyArgsPass : function() {
354
354
  return any(this.calls, function(call){
355
355
  return any(self.expectedArgs, function(i, arg){
356
356
  return arg.an_instance_of ?
357
357
  call.args[i].constructor == arg.an_instance_of:
358
358
  equal(arg, call.args[i])
359
-
359
+
360
360
  })
361
361
  })
362
362
  },
363
-
363
+
364
364
  // Return the passing args
365
-
365
+
366
366
  passingArgs : function() {
367
367
  return this.anyArgsPass().args
368
368
  },
369
-
369
+
370
370
  // Return the failing args
371
-
371
+
372
372
  failingArgs : function() {
373
373
  return this.anyArgsFail().args
374
374
  },
375
-
375
+
376
376
  // Report assertion results
377
-
377
+
378
378
  report : function() {
379
- if (JSpec.assert)
379
+ if (JSpec.assert)
380
380
  this.passed ? ++JSpec.stats.passes : ++JSpec.stats.failures
381
381
  return this
382
382
  },
383
-
383
+
384
384
  // Run the assertion
385
-
385
+
386
386
  run : function() {
387
387
  var methodString = 'expected ' + object.toString() + '.' + method + '()' + (negate ? ' not' : '' )
388
-
388
+
389
389
  function times(n) {
390
390
  return n > 2 ? n + ' times' : { 1: 'once', 2: 'twice' }[n]
391
391
  }
392
-
392
+
393
393
  if (this.expectedResult != null && (negate ? this.anyResultsPass() : this.anyResultsFail()))
394
- this.message = methodString + ' to return ' + puts(this.expectedResult) +
395
- ' but ' + (negate ? 'it did' : 'got ' + puts(this.failingResult()))
394
+ this.message = methodString + ' to return ' + puts(this.expectedResult) +
395
+ ' but ' + (negate ? 'it did' : 'got ' + puts(this.failingResult()))
396
396
 
397
397
  if (this.expectedArgs && (negate ? !this.expectedResult && this.anyArgsPass() : this.anyArgsFail()))
398
398
  this.message = methodString + ' to be called with ' + puts.apply(this, this.expectedArgs) +
399
399
  ' but was' + (negate ? '' : ' called with ' + puts.apply(this, this.failingArgs()))
400
400
 
401
401
  if (negate ? !this.expectedResult && !this.expectedArgs && this.calls.length >= this.times : this.calls.length != this.times)
402
- this.message = methodString + ' to be called ' + times(this.times) +
402
+ this.message = methodString + ' to be called ' + times(this.times) +
403
403
  ', but ' + (this.calls.length == 0 ? ' was not called' : ' was called ' + times(this.calls.length))
404
-
405
- if (!this.message.length)
404
+
405
+ if (!this.message.length)
406
406
  this.passed = true
407
-
407
+
408
408
  return this
409
409
  }
410
410
  })
411
411
  },
412
-
412
+
413
413
  /**
414
414
  * Specification Suite block object.
415
415
  *
@@ -427,11 +427,11 @@
427
427
  sharedBehaviors: [],
428
428
  specs: [],
429
429
  ran: false,
430
- shared: isShared,
431
- hooks: { 'before' : [], 'after' : [],
430
+ shared: isShared,
431
+ hooks: { 'before' : [], 'after' : [],
432
432
  'before_each' : [], 'after_each' : [],
433
433
  'before_nested' : [], 'after_nested' : []},
434
-
434
+
435
435
  // Add a spec to the suite
436
436
 
437
437
  addSpec : function(description, body) {
@@ -456,7 +456,7 @@
456
456
  },
457
457
 
458
458
  // Add a hook to the suite
459
-
459
+
460
460
  addHook : function(hook, body) {
461
461
  this.hooks[hook].push(body)
462
462
  },
@@ -486,7 +486,7 @@
486
486
  // Check if nested suites are present
487
487
 
488
488
  hasSuites : function() {
489
- return this.suites.length
489
+ return this.suites.length
490
490
  },
491
491
 
492
492
  // Check if this suite has specs
@@ -499,7 +499,7 @@
499
499
 
500
500
  passed : function() {
501
501
  return !any(this.specs, function(spec){
502
- return !spec.passed()
502
+ return !spec.passed()
503
503
  })
504
504
  },
505
505
 
@@ -512,7 +512,7 @@
512
512
  }
513
513
  })
514
514
  },
515
-
515
+
516
516
  /**
517
517
  * Specification block object.
518
518
  *
@@ -526,29 +526,29 @@
526
526
  body: body,
527
527
  description: description,
528
528
  assertions: [],
529
-
529
+
530
530
  // Add passing assertion
531
-
531
+
532
532
  pass : function(message) {
533
533
  this.assertions.push({ passed: true, message: message })
534
534
  if (JSpec.assert) ++JSpec.stats.passes
535
535
  },
536
-
536
+
537
537
  // Add failing assertion
538
-
538
+
539
539
  fail : function(message) {
540
540
  this.assertions.push({ passed: false, message: message })
541
541
  if (JSpec.assert) ++JSpec.stats.failures
542
542
  },
543
-
543
+
544
544
  // Run deferred assertions
545
-
545
+
546
546
  runDeferredAssertions : function() {
547
547
  each(this.assertions, function(assertion){
548
548
  if (assertion.defer) assertion.run().report(), hook('afterAssertion', assertion)
549
549
  })
550
550
  },
551
-
551
+
552
552
  // Find first failing assertion
553
553
 
554
554
  failure : function() {
@@ -586,17 +586,17 @@
586
586
  }
587
587
  })
588
588
  },
589
-
589
+
590
590
  Module : function(methods) {
591
591
  extend(this, methods)
592
592
  },
593
-
593
+
594
594
  JSON : {
595
-
595
+
596
596
  /**
597
597
  * Generic sequences.
598
598
  */
599
-
599
+
600
600
  meta : {
601
601
  '\b' : '\\b',
602
602
  '\t' : '\\t',
@@ -606,13 +606,13 @@
606
606
  '"' : '\\"',
607
607
  '\\' : '\\\\'
608
608
  },
609
-
609
+
610
610
  /**
611
611
  * Escapable sequences.
612
612
  */
613
-
613
+
614
614
  escapable : /[\\"\x00-\x1f\x7f-\x9f\u00ad\u0600-\u0604\u070f\u17b4\u17b5\u200c-\u200f\u2028-\u202f\u2060-\u206f\ufeff\ufff0-\uffff]/g,
615
-
615
+
616
616
  /**
617
617
  * JSON encode _object_.
618
618
  *
@@ -620,7 +620,7 @@
620
620
  * @return {string}
621
621
  * @api private
622
622
  */
623
-
623
+
624
624
  encode : function(object) {
625
625
  var self = this
626
626
  if (object == undefined || object == null) return 'null'
@@ -634,7 +634,7 @@
634
634
  '\\u' + ('0000' + a.charCodeAt(0).toString(16)).slice(-4)
635
635
  }) + '"' :
636
636
  '"' + object + '"'
637
- case 'object':
637
+ case 'object':
638
638
  if (object.constructor == Array)
639
639
  return '[' + map(object, function(val){
640
640
  return self.encode(val)
@@ -647,9 +647,9 @@
647
647
  return 'null'
648
648
  }
649
649
  },
650
-
650
+
651
651
  // --- DSLs
652
-
652
+
653
653
  DSLs : {
654
654
  snake : {
655
655
  expect : function(actual){
@@ -667,15 +667,15 @@
667
667
  before : function(body) {
668
668
  return JSpec.currentSuite.addHook('before', body)
669
669
  },
670
-
670
+
671
671
  after : function(body) {
672
672
  return JSpec.currentSuite.addHook('after', body)
673
673
  },
674
-
674
+
675
675
  before_each : function(body) {
676
676
  return JSpec.currentSuite.addHook('before_each', body)
677
677
  },
678
-
678
+
679
679
  after_each : function(body) {
680
680
  return JSpec.currentSuite.addHook('after_each', body)
681
681
  },
@@ -687,7 +687,7 @@
687
687
  after_nested : function(body){
688
688
  return JSpec.currentSuite.addhook('after_nested', body)
689
689
  },
690
-
690
+
691
691
  shared_behaviors_for : function(description, body){
692
692
  return JSpec.currentSuite.addSuite(description, body, true)
693
693
  },
@@ -699,7 +699,7 @@
699
699
  },
700
700
 
701
701
  // --- Methods
702
-
702
+
703
703
  /**
704
704
  * Check if _value_ is 'stop'. For use as a
705
705
  * utility callback function.
@@ -708,11 +708,11 @@
708
708
  * @return {bool}
709
709
  * @api public
710
710
  */
711
-
711
+
712
712
  haveStopped : function(value) {
713
713
  return value === 'stop'
714
714
  },
715
-
715
+
716
716
  /**
717
717
  * Include _object_ which may be a hash or Module instance.
718
718
  *
@@ -720,7 +720,7 @@
720
720
  * @return {JSpec}
721
721
  * @api public
722
722
  */
723
-
723
+
724
724
  include : function(object) {
725
725
  var module = object.constructor == JSpec.Module ? object : new JSpec.Module(object)
726
726
  this.modules.push(module)
@@ -735,7 +735,7 @@
735
735
  })
736
736
  return this
737
737
  },
738
-
738
+
739
739
  /**
740
740
  * Add a module hook _name_, which is immediately
741
741
  * called per module with the _args_ given. An array of
@@ -746,7 +746,7 @@
746
746
  * @return {array}
747
747
  * @api private
748
748
  */
749
-
749
+
750
750
  hook : function(name, args) {
751
751
  args = toArray(arguments, 1)
752
752
  return inject(JSpec.modules, [], function(results, module){
@@ -754,7 +754,7 @@
754
754
  results.push(JSpec.evalHook(module, name, args))
755
755
  })
756
756
  },
757
-
757
+
758
758
  /**
759
759
  * Eval _module_ hook _name_ with _args_. Evaluates in context
760
760
  * to the module itself, JSpec, and JSpec.context.
@@ -765,31 +765,31 @@
765
765
  * @return {mixed}
766
766
  * @api private
767
767
  */
768
-
768
+
769
769
  evalHook : function(module, name, args) {
770
770
  hook('evaluatingHookBody', module, name)
771
771
  return module[name].apply(module, args)
772
772
  },
773
-
773
+
774
774
  /**
775
775
  * Same as hook() however accepts only one _arg_ which is
776
776
  * considered immutable. This function passes the arg
777
777
  * to the first module, then passes the return value of the last
778
- * module called, to the following module.
778
+ * module called, to the following module.
779
779
  *
780
780
  * @param {string} name
781
781
  * @param {mixed} arg
782
782
  * @return {mixed}
783
783
  * @api private
784
784
  */
785
-
785
+
786
786
  hookImmutable : function(name, arg) {
787
787
  return inject(JSpec.modules, arg, function(result, module){
788
788
  if (typeof module[name] == 'function')
789
789
  return JSpec.evalHook(module, name, [result])
790
790
  })
791
791
  },
792
-
792
+
793
793
  /**
794
794
  * Find a shared example suite by its description or name.
795
795
  * First searches parent tree of suites for shared behavior
@@ -799,7 +799,7 @@
799
799
  * @return {Suite}
800
800
  * @api private
801
801
  */
802
-
802
+
803
803
  findSharedBehavior : function(description) {
804
804
  var behavior
805
805
  return (behavior = JSpec.findLocalSharedBehavior(description))
@@ -815,7 +815,7 @@
815
815
  * @return {Suite}
816
816
  * @api private
817
817
  */
818
-
818
+
819
819
  findLocalSharedBehavior : function(description) {
820
820
  var behavior,
821
821
  currentSuite = JSpec.currentSuite.suite
@@ -834,11 +834,11 @@
834
834
  * @return {Suite}
835
835
  * @api private
836
836
  */
837
-
837
+
838
838
  findGlobalSharedBehavior : function(description) {
839
839
  return find(JSpec.suites, JSpec.suiteDescriptionPredicate(description))
840
840
  },
841
-
841
+
842
842
  /**
843
843
  * Build a predicate that will match a suite based on name or description
844
844
  *
@@ -846,7 +846,7 @@
846
846
  * @return {function}
847
847
  * @api private
848
848
  */
849
-
849
+
850
850
  suiteDescriptionPredicate : function(description) {
851
851
  return function(suite){
852
852
  return suite.name === description ||
@@ -861,7 +861,7 @@
861
861
  * @param {string} description
862
862
  * @api public
863
863
  */
864
-
864
+
865
865
  shareBehaviorsOf : function(description) {
866
866
  var suite = JSpec.findSharedBehavior(description)
867
867
  if (suite)
@@ -869,8 +869,8 @@
869
869
  else
870
870
  throw new Error("failed to find shared behaviors named `" + description + "'")
871
871
  },
872
-
873
-
872
+
873
+
874
874
  /**
875
875
  * Convert arguments to an array.
876
876
  *
@@ -879,11 +879,11 @@
879
879
  * @return {array}
880
880
  * @api public
881
881
  */
882
-
882
+
883
883
  toArray : function(arguments, offset) {
884
884
  return Array.prototype.slice.call(arguments, offset || 0)
885
885
  },
886
-
886
+
887
887
  /**
888
888
  * Return ANSI-escaped colored string.
889
889
  *
@@ -892,7 +892,7 @@
892
892
  * @return {string}
893
893
  * @api public
894
894
  */
895
-
895
+
896
896
  color : function(string, color) {
897
897
  if (option('disableColors')) {
898
898
  return string
@@ -910,22 +910,22 @@
910
910
  }[color] + 'm' + string + "\u001B[0m"
911
911
  }
912
912
  },
913
-
913
+
914
914
  /**
915
915
  * Default matcher message callback.
916
916
  *
917
917
  * @api private
918
918
  */
919
-
919
+
920
920
  defaultMatcherMessage : function(actual, expected, negate, name) {
921
- return 'expected ' + puts(actual) + ' to ' +
922
- (negate ? 'not ' : '') +
921
+ return 'expected ' + puts(actual) + ' to ' +
922
+ (negate ? 'not ' : '') +
923
923
  name.replace(/_/g, ' ') +
924
924
  ' ' + (expected.length > 1 ?
925
925
  puts.apply(this, expected.slice(1)) :
926
926
  '')
927
927
  },
928
-
928
+
929
929
  /**
930
930
  * Normalize a matcher message.
931
931
  *
@@ -936,45 +936,45 @@
936
936
  * @return {hash}
937
937
  * @api public
938
938
  */
939
-
939
+
940
940
  normalizeMatcherMessage : function(matcher) {
941
- if (typeof matcher.message != 'function')
941
+ if (typeof matcher.message != 'function')
942
942
  matcher.message = this.defaultMatcherMessage
943
943
  return matcher
944
944
  },
945
-
945
+
946
946
  /**
947
947
  * Normalize a matcher body
948
- *
948
+ *
949
949
  * This process allows the following conversions until
950
950
  * the matcher is in its final normalized hash state.
951
951
  *
952
952
  * - '==' becomes 'actual == expected'
953
953
  * - 'actual == expected' becomes 'return actual == expected'
954
- * - function(actual, expected) { return actual == expected } becomes
954
+ * - function(actual, expected) { return actual == expected } becomes
955
955
  * { match : function(actual, expected) { return actual == expected }}
956
956
  *
957
957
  * @param {mixed} body
958
958
  * @return {hash}
959
959
  * @api public
960
960
  */
961
-
961
+
962
962
  normalizeMatcherBody : function(body) {
963
963
  var captures
964
964
  switch (body.constructor) {
965
965
  case String:
966
966
  if (captures = body.match(/^alias (\w+)/)) return JSpec.matchers[last(captures)]
967
967
  if (body.length < 4) body = 'actual ' + body + ' expected'
968
- return { match: function(actual, expected) { return eval(body) }}
969
-
968
+ return { match: function(actual, expected) { return eval(body) }}
969
+
970
970
  case Function:
971
971
  return { match: body }
972
-
972
+
973
973
  default:
974
974
  return body
975
975
  }
976
976
  },
977
-
977
+
978
978
  /**
979
979
  * Get option value. This method first checks if
980
980
  * the option key has been set via the query string,
@@ -984,12 +984,12 @@
984
984
  * @return {mixed}
985
985
  * @api public
986
986
  */
987
-
987
+
988
988
  option : function(key) {
989
989
  return (value = query(key)) !== null ? value :
990
990
  JSpec.options[key] || null
991
991
  },
992
-
992
+
993
993
  /**
994
994
  * Check if object _a_, is equal to object _b_.
995
995
  *
@@ -998,7 +998,7 @@
998
998
  * @return {bool}
999
999
  * @api private
1000
1000
  */
1001
-
1001
+
1002
1002
  equal: function(a, b) {
1003
1003
  if (typeof a != typeof b) return
1004
1004
  if (a === b) return true
@@ -1057,14 +1057,14 @@
1057
1057
  if (object.nodeName && object.outerHTML) return object.outerHTML
1058
1058
  if (object.nodeName) return document.createElement('div').appendChild(object).parentNode.innerHTML
1059
1059
  switch (object.constructor) {
1060
- case Function: return object.name || object
1061
- case String:
1060
+ case Function: return object.name || object
1061
+ case String:
1062
1062
  return '"' + object
1063
1063
  .replace(/"/g, '\\"')
1064
1064
  .replace(/\n/g, '\\n')
1065
1065
  .replace(/\t/g, '\\t')
1066
1066
  + '"'
1067
- case Array:
1067
+ case Array:
1068
1068
  return inject(object, '[', function(b, v){
1069
1069
  return b + ', ' + puts(v)
1070
1070
  }).replace('[,', '[') + ' ]'
@@ -1074,7 +1074,7 @@
1074
1074
  if (k == '__hit__') return b
1075
1075
  return b + ', ' + k + ': ' + (v && v.__hit__ ? '<circular reference>' : puts(v))
1076
1076
  }).replace('{,', '{') + ' }'
1077
- default:
1077
+ default:
1078
1078
  return object.toString()
1079
1079
  }
1080
1080
  },
@@ -1114,12 +1114,12 @@
1114
1114
  .replace(/>/gmi, '&gt;')
1115
1115
  .replace(/</gmi, '&lt;')
1116
1116
  },
1117
-
1117
+
1118
1118
  /**
1119
1119
  * Perform an assertion without reporting.
1120
1120
  *
1121
1121
  * This method is primarily used for internal
1122
- * matchers in order retain DRYness. May be invoked
1122
+ * matchers in order retain DRYness. May be invoked
1123
1123
  * like below:
1124
1124
  *
1125
1125
  * does('foo', 'eql', 'foo')
@@ -1134,7 +1134,7 @@
1134
1134
  * @return {mixed}
1135
1135
  * @api private
1136
1136
  */
1137
-
1137
+
1138
1138
  does : function(actual, matcher, expected) {
1139
1139
  var assertion = new JSpec.Assertion(JSpec.matchers[matcher], actual, toArray(arguments, 2))
1140
1140
  return assertion.run().result
@@ -1155,22 +1155,22 @@
1155
1155
  expect : function(actual) {
1156
1156
  function assert(matcher, args, negate) {
1157
1157
  var expected = toArray(args, 1)
1158
- matcher.negate = negate
1158
+ matcher.negate = negate
1159
1159
  var assertion = new JSpec.Assertion(matcher, actual, expected, negate)
1160
1160
  hook('beforeAssertion', assertion)
1161
1161
  if (matcher.defer) assertion.run()
1162
1162
  else JSpec.currentSpec.assertions.push(assertion.run().report()), hook('afterAssertion', assertion)
1163
1163
  return assertion.result
1164
1164
  }
1165
-
1165
+
1166
1166
  function to(matcher) {
1167
1167
  return assert(matcher, arguments, false)
1168
1168
  }
1169
-
1169
+
1170
1170
  function not_to(matcher) {
1171
1171
  return assert(matcher, arguments, true)
1172
1172
  }
1173
-
1173
+
1174
1174
  return {
1175
1175
  to : to,
1176
1176
  should : to,
@@ -1193,7 +1193,7 @@
1193
1193
  replace(new RegExp('[' + (chars || '\\s') + ']*$'), '').
1194
1194
  replace(new RegExp('^[' + (chars || '\\s') + ']*'), '')
1195
1195
  },
1196
-
1196
+
1197
1197
  /**
1198
1198
  * Call an iterator callback with arguments a, or b
1199
1199
  * depending on the arity of the callback.
@@ -1204,11 +1204,11 @@
1204
1204
  * @return {mixed}
1205
1205
  * @api private
1206
1206
  */
1207
-
1207
+
1208
1208
  callIterator : function(callback, a, b) {
1209
1209
  return callback.length == 1 ? callback(b) : callback(a, b)
1210
1210
  },
1211
-
1211
+
1212
1212
  /**
1213
1213
  * Extend an object with another.
1214
1214
  *
@@ -1216,13 +1216,13 @@
1216
1216
  * @param {object} other
1217
1217
  * @api public
1218
1218
  */
1219
-
1219
+
1220
1220
  extend : function(object, other) {
1221
1221
  each(other, function(property, value){
1222
1222
  object[property] = value
1223
1223
  })
1224
1224
  },
1225
-
1225
+
1226
1226
  /**
1227
1227
  * Iterate an object, invoking the given callback.
1228
1228
  *
@@ -1237,7 +1237,7 @@
1237
1237
  for (var i = 0, len = object.length; i < len; ++i)
1238
1238
  callIterator(callback, i, object[i])
1239
1239
  else
1240
- for (var key in object)
1240
+ for (var key in object)
1241
1241
  if (object.hasOwnProperty(key))
1242
1242
  callIterator(callback, key, object[key])
1243
1243
  },
@@ -1261,7 +1261,7 @@
1261
1261
  })
1262
1262
  return memo
1263
1263
  },
1264
-
1264
+
1265
1265
  /**
1266
1266
  * Destub _object_'s _method_. When no _method_ is passed
1267
1267
  * all stubbed methods are destubbed. When no arguments
@@ -1272,7 +1272,7 @@
1272
1272
  * @param {string} method
1273
1273
  * @api public
1274
1274
  */
1275
-
1275
+
1276
1276
  destub : function(object, method) {
1277
1277
  var captures
1278
1278
  if (method) {
@@ -1293,9 +1293,9 @@
1293
1293
  while (JSpec.stubbed.length)
1294
1294
  destub(JSpec.stubbed.shift())
1295
1295
  },
1296
-
1296
+
1297
1297
  /**
1298
- * Stub _object_'s _method_.
1298
+ * Stub _object_'s _method_.
1299
1299
  *
1300
1300
  * stub(foo, 'toString').and_return('bar')
1301
1301
  *
@@ -1304,10 +1304,10 @@
1304
1304
  * @return {hash}
1305
1305
  * @api public
1306
1306
  */
1307
-
1307
+
1308
1308
  stub : function(object, method) {
1309
1309
  hook('stubbing', object, method)
1310
-
1310
+
1311
1311
  //unbind any stub already present on this method
1312
1312
  JSpec.destub(object, method);
1313
1313
  JSpec.stubbed.push(object)
@@ -1322,7 +1322,7 @@
1322
1322
  }
1323
1323
  }
1324
1324
  },
1325
-
1325
+
1326
1326
  /**
1327
1327
  * Map callback return values.
1328
1328
  *
@@ -1337,7 +1337,7 @@
1337
1337
  memo.push(callIterator(callback, key, value))
1338
1338
  })
1339
1339
  },
1340
-
1340
+
1341
1341
  /**
1342
1342
  * Returns the first matching expression or null.
1343
1343
  *
@@ -1346,14 +1346,14 @@
1346
1346
  * @return {mixed}
1347
1347
  * @api public
1348
1348
  */
1349
-
1349
+
1350
1350
  any : function(object, callback) {
1351
1351
  return inject(object, null, function(state, key, value){
1352
1352
  if (state == undefined)
1353
1353
  return callIterator(callback, key, value) ? value : state
1354
1354
  })
1355
1355
  },
1356
-
1356
+
1357
1357
  /**
1358
1358
  * Returns an array of values collected when the callback
1359
1359
  * given evaluates to true.
@@ -1363,7 +1363,7 @@
1363
1363
  * @return {array}
1364
1364
  * @api public
1365
1365
  */
1366
-
1366
+
1367
1367
  select : function(object, callback) {
1368
1368
  return inject(object, [], function(selected, key, value){
1369
1369
  if (callIterator(callback, key, value))
@@ -1380,10 +1380,10 @@
1380
1380
 
1381
1381
  addMatchers : function(matchers) {
1382
1382
  each(matchers, function(name, body){
1383
- JSpec.addMatcher(name, body)
1383
+ JSpec.addMatcher(name, body)
1384
1384
  })
1385
1385
  },
1386
-
1386
+
1387
1387
  /**
1388
1388
  * Define a matcher.
1389
1389
  *
@@ -1391,7 +1391,7 @@
1391
1391
  * @param {hash, function, string} body
1392
1392
  * @api public
1393
1393
  */
1394
-
1394
+
1395
1395
  addMatcher : function(name, body) {
1396
1396
  hook('addingMatcher', name, body)
1397
1397
  if (name.indexOf(' ') != -1) {
@@ -1404,7 +1404,7 @@
1404
1404
  this.matchers[name] = this.normalizeMatcherMessage(this.normalizeMatcherBody(body))
1405
1405
  this.matchers[name].name = name
1406
1406
  },
1407
-
1407
+
1408
1408
  /**
1409
1409
  * Add a root suite to JSpec.
1410
1410
  *
@@ -1412,14 +1412,14 @@
1412
1412
  * @param {body} function
1413
1413
  * @api public
1414
1414
  */
1415
-
1415
+
1416
1416
  describe : function(description, body) {
1417
1417
  var suite = new JSpec.Suite(description, body, false)
1418
1418
  hook('addingSuite', suite)
1419
1419
  this.allSuites.push(suite)
1420
1420
  this.suites.push(suite)
1421
1421
  },
1422
-
1422
+
1423
1423
  /**
1424
1424
  * Add a shared example suite to JSpec.
1425
1425
  *
@@ -1427,7 +1427,7 @@
1427
1427
  * @param {body} function
1428
1428
  * @api public
1429
1429
  */
1430
-
1430
+
1431
1431
  shared_behaviors_for : function(description, body) {
1432
1432
  var suite = new JSpec.Suite(description, body, true)
1433
1433
  hook('addingSuite', suite)
@@ -1442,7 +1442,7 @@
1442
1442
  * @return {string}
1443
1443
  * @api public
1444
1444
  */
1445
-
1445
+
1446
1446
  contentsOf : function(body) {
1447
1447
  return body.toString().match(/^[^\{]*{((.*\n*)*)}/m)[1]
1448
1448
  },
@@ -1511,7 +1511,7 @@
1511
1511
  },
1512
1512
 
1513
1513
  /**
1514
- * Report on the results.
1514
+ * Report on the results.
1515
1515
  *
1516
1516
  * @api public
1517
1517
  */
@@ -1538,7 +1538,7 @@
1538
1538
  each(this.suites, function(suite) { JSpec.runSuite(suite) })
1539
1539
  return this
1540
1540
  },
1541
-
1541
+
1542
1542
  /**
1543
1543
  * Run a suite.
1544
1544
  *
@@ -1569,25 +1569,25 @@
1569
1569
  this.stats.suitesFinished++
1570
1570
  }
1571
1571
  },
1572
-
1572
+
1573
1573
  /**
1574
1574
  * Report a failure for the current spec.
1575
1575
  *
1576
1576
  * @param {string} message
1577
1577
  * @api public
1578
1578
  */
1579
-
1579
+
1580
1580
  fail : function(message) {
1581
1581
  JSpec.currentSpec.fail(message)
1582
1582
  },
1583
-
1583
+
1584
1584
  /**
1585
1585
  * Report a passing assertion for the current spec.
1586
1586
  *
1587
1587
  * @param {string} message
1588
1588
  * @api public
1589
1589
  */
1590
-
1590
+
1591
1591
  pass : function(message) {
1592
1592
  JSpec.currentSpec.pass(message)
1593
1593
  },
@@ -1650,7 +1650,7 @@
1650
1650
  * @param {string} data
1651
1651
  * @api private
1652
1652
  */
1653
-
1653
+
1654
1654
  post : function(uri, data) {
1655
1655
  if (any(hook('posting', uri, data), haveStopped)) return
1656
1656
  var request = this.xhr()
@@ -1669,18 +1669,18 @@
1669
1669
  * @return {XMLHttpRequest, ActiveXObject}
1670
1670
  * @api private
1671
1671
  */
1672
-
1672
+
1673
1673
  xhr : function() {
1674
1674
  return this.ieXhr() || new JSpec.request
1675
1675
  },
1676
-
1676
+
1677
1677
  /**
1678
1678
  * Return Microsoft piece of crap ActiveXObject.
1679
1679
  *
1680
1680
  * @return {ActiveXObject}
1681
1681
  * @api public
1682
1682
  */
1683
-
1683
+
1684
1684
  ieXhr : function() {
1685
1685
  function object(str) {
1686
1686
  try { return new ActiveXObject(str) } catch(e) {}
@@ -1690,18 +1690,18 @@
1690
1690
  object('Msxml2.XMLHTTP') ||
1691
1691
  object('Microsoft.XMLHTTP')
1692
1692
  },
1693
-
1693
+
1694
1694
  /**
1695
1695
  * Check for HTTP request support.
1696
1696
  *
1697
1697
  * @return {bool}
1698
1698
  * @api private
1699
1699
  */
1700
-
1700
+
1701
1701
  hasXhr : function() {
1702
1702
  return JSpec.request || 'ActiveXObject' in main
1703
1703
  },
1704
-
1704
+
1705
1705
  /**
1706
1706
  * Try loading _file_ returning the contents
1707
1707
  * string or null. Chain to locate / read a file.
@@ -1710,7 +1710,7 @@
1710
1710
  * @return {string}
1711
1711
  * @api public
1712
1712
  */
1713
-
1713
+
1714
1714
  tryLoading : function(file) {
1715
1715
  try { return JSpec.load(file) } catch (e) {}
1716
1716
  },
@@ -1732,9 +1732,9 @@
1732
1732
  var request = this.xhr()
1733
1733
  request.open('GET', file, false)
1734
1734
  request.send(null)
1735
- if (request.readyState == 4 &&
1736
- (request.status == 0 ||
1737
- request.status.toString().charAt(0) == 2))
1735
+ if (request.readyState == 4 &&
1736
+ (request.status == 0 ||
1737
+ request.status.toString().charAt(0) == 2))
1738
1738
  return request.responseText
1739
1739
  }
1740
1740
  else
@@ -1755,9 +1755,9 @@
1755
1755
  return this
1756
1756
  }
1757
1757
  }
1758
-
1758
+
1759
1759
  // --- Node.js support
1760
-
1760
+
1761
1761
  if (typeof GLOBAL === 'object' && typeof exports === 'object') {
1762
1762
  var fs = require('fs')
1763
1763
  quit = process.exit
@@ -1772,7 +1772,7 @@
1772
1772
  if (typeof Johnson === 'object') {
1773
1773
  quit = function () {}
1774
1774
  }
1775
-
1775
+
1776
1776
  // --- Utility functions
1777
1777
 
1778
1778
  var main = this,
@@ -1805,13 +1805,13 @@
1805
1805
  have_length : "actual.length == expected",
1806
1806
  be_within : "actual >= expected[0] && actual <= last(expected)",
1807
1807
  have_length_within : "actual.length >= expected[0] && actual.length <= last(expected)",
1808
-
1808
+
1809
1809
  receive : { defer : true, match : function(actual, method, times) {
1810
1810
  var proxy = new JSpec.ProxyAssertion(actual, method, times, this.negate)
1811
1811
  JSpec.currentSpec.assertions.push(proxy)
1812
1812
  return proxy
1813
1813
  }},
1814
-
1814
+
1815
1815
  be_empty : function(actual) {
1816
1816
  if (actual.constructor == Object && actual.length == undefined)
1817
1817
  for (var key in actual)
@@ -1823,18 +1823,18 @@
1823
1823
  for (var state = true, i = 1; i < arguments.length; i++) {
1824
1824
  var arg = arguments[i]
1825
1825
  switch (actual.constructor) {
1826
- case String:
1826
+ case String:
1827
1827
  case Number:
1828
1828
  case RegExp:
1829
1829
  case Function:
1830
1830
  state = actual.toString().indexOf(arg) !== -1
1831
1831
  break
1832
-
1832
+
1833
1833
  case Object:
1834
1834
  state = arg in actual
1835
1835
  break
1836
-
1837
- case Array:
1836
+
1837
+ case Array:
1838
1838
  state = any(actual, function(value){ return equal(value, arg) })
1839
1839
  break
1840
1840
  }
@@ -1872,31 +1872,31 @@
1872
1872
  return 'expected ' + exception + (negate ? ' not ' : '' ) +
1873
1873
  ' to be thrown, but ' + (this.e ? 'got ' + puts(this.e) : 'nothing was')
1874
1874
  }},
1875
-
1875
+
1876
1876
  have : function(actual, length, property) {
1877
1877
  return actual[property] == null ? false : actual[property].length == length
1878
1878
  },
1879
-
1879
+
1880
1880
  have_at_least : function(actual, length, property) {
1881
1881
  return actual[property] == null ? (length === 0) : actual[property].length >= length
1882
1882
  },
1883
-
1883
+
1884
1884
  have_at_most :function(actual, length, property) {
1885
1885
  return actual[property] == null || actual[property].length <= length
1886
1886
  },
1887
-
1887
+
1888
1888
  have_within : function(actual, range, property) {
1889
1889
  var length = actual[property] == undefined ? 0 : actual[property].length
1890
1890
  return length >= range.shift() && length <= range.pop()
1891
1891
  },
1892
-
1892
+
1893
1893
  have_prop : function(actual, property, value) {
1894
1894
  var actualVal = actual[property], actualType = typeof actualVal
1895
1895
  return (actualType == 'function' || actualType == 'undefined') ? false :
1896
1896
  typeof value === 'undefined' ||
1897
1897
  does(actual[property],'eql',value)
1898
1898
  },
1899
-
1899
+
1900
1900
  have_property : function(actual, property, value) {
1901
1901
  var actualVal = actual[property], actualType = typeof actualVal
1902
1902
  return (actualType == 'function' || actualType == 'undefined') ? false :
@@ -1904,5 +1904,5 @@
1904
1904
  value === actualVal
1905
1905
  }
1906
1906
  })
1907
-
1907
+
1908
1908
  })()