aquarium 0.4.1 → 0.4.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (55) hide show
  1. data/Aquarium-IDEA.ipr +252 -0
  2. data/Aquarium-IDEA.iws +493 -0
  3. data/Aquarium.ipr +1 -1
  4. data/Aquarium.iws +133 -138
  5. data/CHANGES +63 -0
  6. data/ParseTreePlay.rb +25 -0
  7. data/README +55 -3
  8. data/RELEASE-PLAN +9 -1
  9. data/TODO.rb +175 -15
  10. data/examples/aspect_design_example.rb +13 -1
  11. data/examples/aspect_design_example_spec.rb +20 -2
  12. data/examples/introductions_example.rb +35 -0
  13. data/examples/introductions_example_spec.rb +37 -0
  14. data/examples/method_missing_example.rb +2 -1
  15. data/lib/aquarium/aspects/advice.rb +127 -74
  16. data/lib/aquarium/aspects/aspect.rb +139 -72
  17. data/lib/aquarium/aspects/default_objects_handler.rb +6 -4
  18. data/lib/aquarium/aspects/exclusion_handler.rb +15 -3
  19. data/lib/aquarium/aspects/join_point.rb +60 -55
  20. data/lib/aquarium/aspects/pointcut.rb +153 -124
  21. data/lib/aquarium/aspects/pointcut_composition.rb +1 -1
  22. data/lib/aquarium/dsl/aspect_dsl.rb +13 -5
  23. data/lib/aquarium/dsl/object_dsl.rb +4 -2
  24. data/lib/aquarium/extras/design_by_contract.rb +9 -5
  25. data/lib/aquarium/finders.rb +1 -0
  26. data/lib/aquarium/finders/finder_result.rb +13 -5
  27. data/lib/aquarium/finders/method_finder.rb +75 -70
  28. data/lib/aquarium/finders/pointcut_finder.rb +166 -0
  29. data/lib/aquarium/finders/type_finder.rb +104 -62
  30. data/lib/aquarium/utils/array_utils.rb +1 -1
  31. data/lib/aquarium/utils/invalid_options.rb +2 -0
  32. data/lib/aquarium/utils/name_utils.rb +3 -2
  33. data/lib/aquarium/utils/nil_object.rb +7 -3
  34. data/lib/aquarium/utils/options_utils.rb +38 -27
  35. data/lib/aquarium/utils/set_utils.rb +2 -2
  36. data/lib/aquarium/utils/type_utils.rb +11 -0
  37. data/lib/aquarium/version.rb +1 -1
  38. data/spec/aquarium/aspects/advice_spec.rb +147 -32
  39. data/spec/aquarium/aspects/aspect_invocation_spec.rb +252 -43
  40. data/spec/aquarium/aspects/aspect_spec.rb +148 -88
  41. data/spec/aquarium/aspects/aspect_with_nested_types_spec.rb +40 -34
  42. data/spec/aquarium/aspects/aspect_with_subtypes_spec.rb +39 -3
  43. data/spec/aquarium/aspects/join_point_spec.rb +190 -227
  44. data/spec/aquarium/aspects/pointcut_spec.rb +24 -1
  45. data/spec/aquarium/dsl/aspect_dsl_spec.rb +17 -17
  46. data/spec/aquarium/finders/method_finder_spec.rb +8 -2
  47. data/spec/aquarium/finders/pointcut_finder_spec.rb +193 -0
  48. data/spec/aquarium/finders/pointcut_finder_spec_test_classes.rb +90 -0
  49. data/spec/aquarium/finders/type_finder_spec.rb +17 -0
  50. data/spec/aquarium/finders/type_finder_with_descendents_and_ancestors_spec.rb +4 -4
  51. data/spec/aquarium/finders/type_finder_with_nested_types.rb +47 -0
  52. data/spec/aquarium/utils/nil_object_spec.rb +21 -0
  53. data/spec/aquarium/utils/type_utils_sample_nested_types.rb +51 -0
  54. data/spec/aquarium/utils/type_utils_spec.rb +18 -1
  55. metadata +13 -3
@@ -6,6 +6,22 @@ require 'logger'
6
6
 
7
7
  include Aquarium::Aspects
8
8
 
9
+ class MyError1 < StandardError; end
10
+ class MyError2 < StandardError; end
11
+ class MyError3 < StandardError; end
12
+ class ClassThatRaises
13
+ class CTRException < StandardError; end
14
+ def raises
15
+ raise CTRException
16
+ end
17
+ end
18
+ class ClassThatRaisesString
19
+ class CTRException < StandardError; end
20
+ def raises
21
+ raise "A string exception."
22
+ end
23
+ end
24
+
9
25
 
10
26
  describe Aspect, " cannot advise the private implementation methods inserted by other aspects" do
11
27
  it "should have no affect." do
@@ -69,18 +85,19 @@ describe Aspect, " with :before advice" do
69
85
 
70
86
  it "should pass the context information to the advice, including self and the method parameters." do
71
87
  watchful = Watchful.new
72
- context = nil
88
+ advice_called = false
73
89
  @aspect = Aspect.new :before, :pointcut => {:type => Watchful, :methods => :public_watchful_method} do |jp, obj, *args|
74
- context = jp.context
90
+ advice_called = true
91
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
92
+ jp.context.advice_kind.should == :before
93
+ jp.context.advised_object.should == watchful
94
+ jp.context.returned_value.should == nil
95
+ jp.context.raised_exception.should == nil
75
96
  end
76
97
  block_called = 0
77
98
  watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
78
99
  block_called.should == 1
79
- context.advice_kind.should == :before
80
- context.advised_object.should == watchful
81
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
82
- context.returned_value.should == nil
83
- context.raised_exception.should == nil
100
+ advice_called.should be_true
84
101
  end
85
102
 
86
103
  it "should evaluate the advice before the method body and its block (if any)." do
@@ -98,18 +115,19 @@ describe Aspect, " with :after advice" do
98
115
 
99
116
  it "should pass the context information to the advice, including self, the method parameters, and the return value when the method returns normally." do
100
117
  watchful = Watchful.new
101
- context = nil
118
+ advice_called = false
102
119
  @aspect = Aspect.new :after, :pointcut => {:type => Watchful, :methods => :public_watchful_method} do |jp, obj, *args|
103
- context = jp.context
120
+ advice_called = true
121
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
122
+ jp.context.advice_kind.should == :after
123
+ jp.context.advised_object.should == watchful
124
+ jp.context.returned_value.should == 1
125
+ jp.context.raised_exception.should == nil
104
126
  end
105
127
  block_called = 0
106
128
  watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
107
129
  block_called.should == 1
108
- context.advice_kind.should == :after
109
- context.advised_object.should == watchful
110
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
111
- context.returned_value.should == block_called
112
- context.raised_exception.should == nil
130
+ advice_called.should be_true
113
131
  end
114
132
 
115
133
  it "should pass the context information to the advice, including self, the method parameters, and the rescued exception when an exception is raised." do
@@ -119,10 +137,12 @@ describe Aspect, " with :after advice" do
119
137
  context = jp.context
120
138
  end
121
139
  block_called = 0
122
- lambda {watchful.public_watchful_method_that_raises(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }}.should raise_error(Watchful::WatchfulError)
140
+ lambda {watchful.public_watchful_method_that_raises(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') do |*args|
141
+ block_called += 1
142
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
143
+ end }.should raise_error(Watchful::WatchfulError)
123
144
  block_called.should == 1
124
145
  context.advised_object.should == watchful
125
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
126
146
  context.returned_value.should == nil
127
147
  context.raised_exception.kind_of?(Watchful::WatchfulError).should be_true
128
148
  end
@@ -161,6 +181,18 @@ describe Aspect, " with :after advice" do
161
181
  end
162
182
  ReturningValue.new.doit(ary).should == %w[aa a b c d e]
163
183
  end
184
+
185
+ it "should allow advice to change the exception raised" do
186
+ aspect_advice_invoked = false
187
+ @aspect = Aspect.new :after, :pointcut => {:type => ClassThatRaises, :methods => :raises} do |jp, obj, *args|
188
+ aspect_advice_invoked = true
189
+ jp.context.raised_exception = MyError1
190
+ end
191
+ aspect_advice_invoked.should be_false
192
+ ctr = ClassThatRaises.new
193
+ lambda {ctr.raises}.should raise_error(MyError1)
194
+ aspect_advice_invoked.should be_true
195
+ end
164
196
  end
165
197
 
166
198
  describe Aspect, " with :after_returning advice" do
@@ -170,18 +202,19 @@ describe Aspect, " with :after_returning advice" do
170
202
 
171
203
  it "should pass the context information to the advice, including self, the method parameters, and the return value." do
172
204
  watchful = Watchful.new
173
- context = nil
205
+ advice_called = false
174
206
  @aspect = Aspect.new :after_returning, :pointcut => {:type => Watchful, :methods => :public_watchful_method} do |jp, obj, *args|
175
- context = jp.context
207
+ advice_called = true
208
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
209
+ jp.context.advice_kind.should == :after_returning
210
+ jp.context.advised_object.should == watchful
211
+ jp.context.returned_value.should == 1
212
+ jp.context.raised_exception.should == nil
176
213
  end
177
214
  block_called = 0
178
215
  watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
179
216
  block_called.should == 1
180
- context.advice_kind.should == :after_returning
181
- context.advised_object.should == watchful
182
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
183
- context.returned_value.should == block_called
184
- context.raised_exception.should == nil
217
+ advice_called.should be_true
185
218
  end
186
219
 
187
220
  it "should evaluate the advice after the method body and its block (if any)." do
@@ -205,7 +238,7 @@ describe Aspect, " with :after_returning advice" do
205
238
  ReturningValue.new.doit(ary).should == %w[a b c d]
206
239
  end
207
240
 
208
- it "should all the advice to assign a new return value" do
241
+ it "should allow the advice to change the returned value" do
209
242
  class ReturningValue
210
243
  def doit args
211
244
  args + ["d"]
@@ -220,10 +253,6 @@ describe Aspect, " with :after_returning advice" do
220
253
  end
221
254
  end
222
255
 
223
- class MyError1 < StandardError; end
224
- class MyError2 < StandardError; end
225
- class MyError3 < StandardError; end
226
-
227
256
  describe Aspect, " with :after_raising advice" do
228
257
  after(:each) do
229
258
  @aspect.unadvise if @aspect
@@ -231,18 +260,19 @@ describe Aspect, " with :after_raising advice" do
231
260
 
232
261
  it "should pass the context information to the advice, including self, the method parameters, and the rescued exception." do
233
262
  watchful = Watchful.new
234
- context = nil
263
+ advice_called = false
235
264
  @aspect = Aspect.new :after_raising, :pointcut => {:type => Watchful, :methods => /public_watchful_method/} do |jp, obj, *args|
236
- context = jp.context
265
+ advice_called = true
266
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
267
+ jp.context.advised_object.should == watchful
268
+ jp.context.advice_kind.should == :after_raising
269
+ jp.context.returned_value.should == nil
270
+ jp.context.raised_exception.kind_of?(Watchful::WatchfulError).should be_true
237
271
  end
238
272
  block_called = 0
239
273
  lambda {watchful.public_watchful_method_that_raises(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }}.should raise_error(Watchful::WatchfulError)
240
274
  block_called.should == 1
241
- context.advised_object.should == watchful
242
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
243
- context.advice_kind.should == :after_raising
244
- context.returned_value.should == nil
245
- context.raised_exception.kind_of?(Watchful::WatchfulError).should be_true
275
+ advice_called.should be_true
246
276
  end
247
277
 
248
278
  it "should evaluate the advice after the method body and its block (if any)." do
@@ -302,6 +332,14 @@ describe Aspect, " with :after_raising advice" do
302
332
  block_invoked.should be_true
303
333
  end
304
334
 
335
+ it "should invoke advice when an exception that subclasses a specified exception type is raised" do
336
+ aspect_advice_invoked = false
337
+ @aspect = Aspect.new(:after_raising => StandardError, :pointcut => {:type => ClassThatRaises, :methods => :raises}) {|jp, obj, *args| aspect_advice_invoked = true}
338
+ ctr = ClassThatRaises.new
339
+ lambda {ctr.raises}.should raise_error(ClassThatRaises::CTRException)
340
+ aspect_advice_invoked.should be_true
341
+ end
342
+
305
343
  it "should not invoke advice when exceptions of types that don't match the specified list of exception types are raised" do
306
344
  aspect_advice_invoked = false
307
345
  @aspect = Aspect.new(:after_raising => [MyError1, MyError2], :pointcut => {:type => Watchful, :methods => /public_watchful_method/}) {|jp, obj, *args| aspect_advice_invoked = true}
@@ -339,12 +377,6 @@ describe Aspect, " with :after_raising advice" do
339
377
  end
340
378
 
341
379
  it "should advise all methods that raise exceptions when no specific exceptions are specified" do
342
- class ClassThatRaises
343
- class CTRException < Exception; end
344
- def raises
345
- raise CTRException
346
- end
347
- end
348
380
  aspect_advice_invoked = false
349
381
  @aspect = Aspect.new :after_raising, :pointcut => {:type => ClassThatRaises, :methods => :raises} do |jp, obj, *args|
350
382
  aspect_advice_invoked = true
@@ -356,12 +388,6 @@ describe Aspect, " with :after_raising advice" do
356
388
  end
357
389
 
358
390
  it "should advise all methods that raise strings (which are converted to RuntimeError) when no specific exceptions are specified" do
359
- class ClassThatRaisesString
360
- class CTRException < Exception; end
361
- def raises
362
- raise "A string exception."
363
- end
364
- end
365
391
  aspect_advice_invoked = false
366
392
  @aspect = Aspect.new :after_raising, :pointcut => {:type => ClassThatRaisesString, :methods => :raises} do |jp, obj, *args|
367
393
  aspect_advice_invoked = true
@@ -371,6 +397,18 @@ describe Aspect, " with :after_raising advice" do
371
397
  lambda {ctr.raises}.should raise_error(RuntimeError)
372
398
  aspect_advice_invoked.should be_true
373
399
  end
400
+
401
+ it "should allow advice to change the exception raised" do
402
+ aspect_advice_invoked = false
403
+ @aspect = Aspect.new :after_raising, :pointcut => {:type => ClassThatRaises, :methods => :raises} do |jp, obj, *args|
404
+ aspect_advice_invoked = true
405
+ jp.context.raised_exception = MyError1
406
+ end
407
+ aspect_advice_invoked.should be_false
408
+ ctr = ClassThatRaises.new
409
+ lambda {ctr.raises}.should raise_error(MyError1)
410
+ aspect_advice_invoked.should be_true
411
+ end
374
412
  end
375
413
 
376
414
  describe Aspect, " with :before and :after advice" do
@@ -379,22 +417,30 @@ describe Aspect, " with :before and :after advice" do
379
417
  end
380
418
 
381
419
  it "should pass the context information to the advice, including self and the method parameters, plus the return value for the after-advice case." do
420
+ # We record the contexts seen and the volatile advice kinds and returned values separately, as those values will have been
421
+ # reset in the contexts by the time we return from the advised method.
382
422
  contexts = []
423
+ advice_kinds = []
424
+ returned_values = []
383
425
  @aspect = Aspect.new :before, :after, :pointcut => {:type => Watchful, :methods => [:public_watchful_method]} do |jp, obj, *args|
384
426
  contexts << jp.context
427
+ advice_kinds << jp.context.advice_kind
428
+ returned_values << jp.context.returned_value
429
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
385
430
  end
386
431
  watchful = Watchful.new
387
432
  public_block_called = 0
388
- watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| public_block_called += 1 }
433
+ watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') do |*args|
434
+ public_block_called += 1
435
+ end
389
436
  public_block_called.should == 1
390
437
  contexts.size.should == 2
391
- contexts[0].advice_kind.should == :before
392
- contexts[1].advice_kind.should == :after
393
- contexts[0].returned_value.should == nil
394
- contexts[1].returned_value.should == 1
438
+ advice_kinds[0].should == :before
439
+ advice_kinds[1].should == :after
440
+ returned_values[0].should == nil
441
+ returned_values[1].should == 1
395
442
  contexts.each do |context|
396
443
  context.advised_object.should == watchful
397
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
398
444
  context.raised_exception.should == nil
399
445
  end
400
446
 
@@ -421,21 +467,27 @@ describe Aspect, " with :before and :after_returning advice" do
421
467
 
422
468
  it "should pass the context information to the advice, including self and the method parameters, plus the return value for the after-advice case." do
423
469
  watchful = Watchful.new
470
+ # We record the contexts seen and the volatile advice kinds and returned values separately, as those values will have been
471
+ # reset in the contexts by the time we return from the advised method.
424
472
  contexts = []
473
+ advice_kinds = []
474
+ returned_values = []
425
475
  @aspect = Aspect.new :before, :after_returning, :pointcut => {:type => Watchful, :methods => :public_watchful_method} do |jp, obj, *args|
426
476
  contexts << jp.context
477
+ advice_kinds << jp.context.advice_kind
478
+ returned_values << jp.context.returned_value
479
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
427
480
  end
428
481
  block_called = 0
429
482
  watchful.public_watchful_method(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
430
483
  block_called.should == 1
431
484
  contexts.size.should == 2
432
- contexts[0].advice_kind.should == :before
433
- contexts[1].advice_kind.should == :after_returning
434
- contexts[0].returned_value.should == nil
435
- contexts[1].returned_value.should == block_called
485
+ advice_kinds[0].should == :before
486
+ advice_kinds[1].should == :after_returning
487
+ returned_values[0].should == nil
488
+ returned_values[1].should == 1
436
489
  contexts.each do |context|
437
490
  context.advised_object.should == watchful
438
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
439
491
  context.raised_exception.should == nil
440
492
  end
441
493
  end
@@ -455,21 +507,27 @@ describe Aspect, " with :before and :after_raising advice" do
455
507
 
456
508
  it "should pass the context information to the advice, including self and the method parameters, plus the raised exception for the after-advice case." do
457
509
  watchful = Watchful.new
510
+ # We record the contexts seen and the volatile advice kinds and raised exceptions separately, as those values will have been
511
+ # reset in the contexts by the time we return from the advised method.
458
512
  contexts = []
513
+ advice_kinds = []
514
+ raised_exceptions = []
459
515
  @aspect = Aspect.new :before, :after_raising, :pointcut => {:type => Watchful, :methods => :public_watchful_method_that_raises} do |jp, obj, *args|
460
516
  contexts << jp.context
517
+ advice_kinds << jp.context.advice_kind
518
+ raised_exceptions << jp.context.raised_exception
519
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
461
520
  end
462
521
  block_called = 0
463
522
  lambda {watchful.public_watchful_method_that_raises(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }}.should raise_error(Watchful::WatchfulError)
464
523
  block_called.should == 1
465
524
  contexts.size.should == 2
466
- contexts[0].advice_kind.should == :before
467
- contexts[1].advice_kind.should == :after_raising
468
- contexts[0].raised_exception.should == nil
469
- contexts[1].raised_exception.kind_of?(Watchful::WatchfulError).should be_true
525
+ advice_kinds[0].should == :before
526
+ advice_kinds[1].should == :after_raising
527
+ raised_exceptions[0].should == nil
528
+ raised_exceptions[1].kind_of?(Watchful::WatchfulError).should be_true
470
529
  contexts.each do |context|
471
530
  context.advised_object.should == watchful
472
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
473
531
  context.returned_value.should == nil
474
532
  end
475
533
  end
@@ -488,11 +546,16 @@ describe Aspect, " with :around advice" do
488
546
  end
489
547
 
490
548
  it "should pass the context information to the advice, including the object, advice kind, the method invocation parameters, etc." do
491
- contexts = []
549
+ watchful = Watchful.new
550
+ advice_called = false
492
551
  @aspect = Aspect.new :around, :pointcut => {:type => Watchful, :methods => [:public_watchful_method]} do |jp, obj, *args|
493
- contexts << jp.context
552
+ advice_called = true
553
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
554
+ jp.context.advised_object.should == watchful
555
+ jp.context.advice_kind.should == :around
556
+ jp.context.returned_value.should == nil
557
+ jp.context.raised_exception.should == nil
494
558
  end
495
- watchful = Watchful.new
496
559
  public_block_called = false
497
560
  protected_block_called = false
498
561
  private_block_called = false
@@ -502,12 +565,7 @@ describe Aspect, " with :around advice" do
502
565
  public_block_called.should be_false # proceed is never called!
503
566
  protected_block_called.should be_true
504
567
  private_block_called.should be_true
505
- contexts.size.should == 1
506
- contexts[0].advised_object.should == watchful
507
- contexts[0].advice_kind.should == :around
508
- contexts[0].returned_value.should == nil
509
- contexts[0].parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
510
- contexts[0].raised_exception.should == nil
568
+ advice_called.should be_true
511
569
  end
512
570
 
513
571
  it "should advise subclass invocations of methods advised in the superclass." do
@@ -529,11 +587,16 @@ describe Aspect, " with :around advice" do
529
587
  end
530
588
  end
531
589
 
532
- context = nil
590
+ child = AdvisingSuperClass::SubClass.new
591
+ advice_called = false
533
592
  @aspect = Aspect.new :around, :pointcut => {:type => AdvisingSuperClass::SuperClass, :methods => [:public_method]} do |jp, obj, *args|
534
- context = jp.context
593
+ advice_called = true
594
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
595
+ jp.context.advised_object.should == child
596
+ jp.context.advice_kind.should == :around
597
+ jp.context.returned_value.should == nil
598
+ jp.context.raised_exception.should == nil
535
599
  end
536
- child = AdvisingSuperClass::SubClass.new
537
600
  public_block_called = false
538
601
  protected_block_called = false
539
602
  private_block_called = false
@@ -543,11 +606,7 @@ describe Aspect, " with :around advice" do
543
606
  public_block_called.should be_false # proceed is never called!
544
607
  protected_block_called.should be_true
545
608
  private_block_called.should be_true
546
- context.advised_object.should == child
547
- context.advice_kind.should == :around
548
- context.returned_value.should == nil
549
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
550
- context.raised_exception.should == nil
609
+ advice_called.should be_true
551
610
  end
552
611
 
553
612
  it "should advise subclass invocations of methods advised in the subclass that are defined in the superclass." do
@@ -569,11 +628,16 @@ describe Aspect, " with :around advice" do
569
628
  end
570
629
  end
571
630
 
572
- context = nil
631
+ child = AdvisingSubClass::SubClass.new
632
+ advice_called = false
573
633
  @aspect = Aspect.new :around, :pointcut => {:type => AdvisingSubClass::SuperClass, :methods => [:public_method]} do |jp, obj, *args|
574
- context = jp.context
634
+ advice_called = true
635
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
636
+ jp.context.advised_object.should == child
637
+ jp.context.advice_kind.should == :around
638
+ jp.context.returned_value.should == nil
639
+ jp.context.raised_exception.should == nil
575
640
  end
576
- child = AdvisingSubClass::SubClass.new
577
641
  public_block_called = false
578
642
  protected_block_called = false
579
643
  private_block_called = false
@@ -583,11 +647,7 @@ describe Aspect, " with :around advice" do
583
647
  public_block_called.should be_false # proceed is never called!
584
648
  protected_block_called.should be_true
585
649
  private_block_called.should be_true
586
- context.advised_object.should == child
587
- context.advice_kind.should == :around
588
- context.returned_value.should == nil
589
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
590
- context.raised_exception.should == nil
650
+ advice_called.should be_true
591
651
  end
592
652
 
593
653
  it "should not advise subclass overrides of superclass methods, when advising superclasses (but calls to superclass methods are advised)." do
@@ -30,34 +30,36 @@ describe Aspect, ".new when advising methods in a nested class" do
30
30
 
31
31
  it "should correctly advise methods in a nested class." do
32
32
  myclass = Nested1::Nested2::MyClass.new
33
- context = nil
33
+ advice_called = false
34
34
  @aspect = Aspect.new :before, :pointcut => {:type => Nested1::Nested2::MyClass, :methods => :do1} do |jp, obj, *args|
35
- context = jp.context
35
+ advice_called = true
36
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
37
+ jp.context.advice_kind.should == :before
38
+ jp.context.advised_object.should == myclass
39
+ jp.context.returned_value.should == nil
40
+ jp.context.raised_exception.should == nil
36
41
  end
37
42
  block_called = 0
38
43
  myclass.do1(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
39
44
  block_called.should == 1
40
- context.advice_kind.should == :before
41
- context.advised_object.should == myclass
42
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
43
- context.returned_value.should == nil
44
- context.raised_exception.should == nil
45
+ advice_called.should be_true
45
46
  end
46
47
 
47
48
  it "should correctly advise methods in an instance of the nested class." do
48
49
  myclass = Nested1::Nested2::MyClass.new
49
- context = nil
50
+ advice_called = false
50
51
  @aspect = Aspect.new :before, :pointcut => {:object => myclass, :methods => :do1} do |jp, obj, *args|
51
- context = jp.context
52
+ advice_called = true
53
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
54
+ jp.context.advice_kind.should == :before
55
+ jp.context.advised_object.should == myclass
56
+ jp.context.returned_value.should == nil
57
+ jp.context.raised_exception.should == nil
52
58
  end
53
59
  block_called = 0
54
60
  myclass.do1(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
55
61
  block_called.should == 1
56
- context.advice_kind.should == :before
57
- context.advised_object.should == myclass
58
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
59
- context.returned_value.should == nil
60
- context.raised_exception.should == nil
62
+ advice_called.should be_true
61
63
  end
62
64
  end
63
65
 
@@ -72,18 +74,19 @@ describe Aspect, ".new when advising methods in a nested module included by a cl
72
74
  end
73
75
 
74
76
  myclass = MyClassWithModule1.new
75
- context = nil
77
+ advice_called = false
76
78
  @aspect = Aspect.new :before, :pointcut => {:type => Nested1::Nested2::MyModule, :methods => :do2} do |jp, obj, *args|
77
- context = jp.context
79
+ advice_called = true
80
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
81
+ jp.context.advice_kind.should == :before
82
+ jp.context.advised_object.should == myclass
83
+ jp.context.returned_value.should == nil
84
+ jp.context.raised_exception.should == nil
78
85
  end
79
86
  block_called = 0
80
87
  myclass.do2(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
81
88
  block_called.should == 1
82
- context.advice_kind.should == :before
83
- context.advised_object.should == myclass
84
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
85
- context.returned_value.should == nil
86
- context.raised_exception.should == nil
89
+ advice_called.should be_true
87
90
  end
88
91
 
89
92
  it "should correctly advise the module's methods when the class is specified." do
@@ -92,18 +95,19 @@ describe Aspect, ".new when advising methods in a nested module included by a cl
92
95
  end
93
96
 
94
97
  myclass = MyClassWithModule2.new
95
- context = nil
98
+ advice_called = false
96
99
  @aspect = Aspect.new :before, :pointcut => {:type => MyClassWithModule2, :methods => :do2} do |jp, obj, *args|
97
- context = jp.context
100
+ advice_called = true
101
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
102
+ jp.context.advice_kind.should == :before
103
+ jp.context.advised_object.should == myclass
104
+ jp.context.returned_value.should == nil
105
+ jp.context.raised_exception.should == nil
98
106
  end
99
107
  block_called = 0
100
108
  myclass.do2(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
101
109
  block_called.should == 1
102
- context.advice_kind.should == :before
103
- context.advised_object.should == myclass
104
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
105
- context.returned_value.should == nil
106
- context.raised_exception.should == nil
110
+ advice_called.should be_true
107
111
  end
108
112
 
109
113
  it "should correctly advise the module's methods when an instance of the class is specified." do
@@ -113,17 +117,19 @@ describe Aspect, ".new when advising methods in a nested module included by a cl
113
117
 
114
118
  myclass = MyClassWithModule3.new
115
119
  context = nil
120
+ advice_called = false
116
121
  @aspect = Aspect.new :before, :pointcut => {:object => myclass, :methods => :do2} do |jp, obj, *args|
117
- context = jp.context
122
+ advice_called = true
123
+ args.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
124
+ jp.context.advice_kind.should == :before
125
+ jp.context.advised_object.should == myclass
126
+ jp.context.returned_value.should == nil
127
+ jp.context.raised_exception.should == nil
118
128
  end
119
129
  block_called = 0
120
130
  myclass.do2(:a1, :a2, :a3, :h1 => 'h1', :h2 => 'h2') { |*args| block_called += 1 }
121
131
  block_called.should == 1
122
- context.advice_kind.should == :before
123
- context.advised_object.should == myclass
124
- context.parameters.should == [:a1, :a2, :a3, {:h1 => 'h1', :h2 => 'h2'}]
125
- context.returned_value.should == nil
126
- context.raised_exception.should == nil
132
+ advice_called.should be_true
127
133
  end
128
134
  end
129
135