rack-unreloader 1.6.0 → 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,449 +0,0 @@
1
- require File.join(File.dirname(File.expand_path(__FILE__)), 'spec_helper')
2
-
3
- describe Rack::Unreloader do
4
- it "should not reload files automatically if cooldown option is nil" do
5
- ru(:cooldown => nil).call({}).must_equal [1]
6
- update_app(code(2))
7
- ru.call({}).must_equal [1]
8
- @ru.reload!
9
- ru.call({}).must_equal [2]
10
- end
11
-
12
- it "should not setup a reloader if reload option is false" do
13
- @filename = 'spec/app_no_reload.rb'
14
- ru(:reload => false).call({}).must_equal [1]
15
- file = 'spec/app_no_reload2.rb'
16
- File.open(file, 'wb'){|f| f.write('ANR2 = 2')}
17
- ru.require 'spec/app_no_*2.rb'
18
- ANR2.must_equal 2
19
- end
20
-
21
- it "should unload constants contained in file and reload file if file changes" do
22
- ru.call({}).must_equal [1]
23
- update_app(code(2))
24
- ru.call({}).must_equal [2]
25
- log_match %r{\ALoading.*spec/app\.rb\z},
26
- %r{\ANew classes in .*spec/app\.rb: App\z},
27
- %r{\AUnloading.*spec/app\.rb\z},
28
- "Removed constant App",
29
- %r{\ALoading.*spec/app\.rb\z},
30
- %r{\ANew classes in .*spec/app\.rb: App\z}
31
- end
32
-
33
- it "should stop monitoring file for changes if it is deleted constants contained in file and reload file if file changes" do
34
- ru.call({}).must_equal [1]
35
- File.delete('spec/app.rb')
36
- proc{ru.call({})}.must_raise NameError
37
- log_match %r{\ALoading.*spec/app\.rb\z},
38
- %r{\ANew classes in .*spec/app\.rb: App\z},
39
- %r{\AUnloading.*spec/app\.rb\z},
40
- "Removed constant App"
41
- end
42
-
43
- it "should check constants using ObjectSpace if require proc returns :ObjectSpace" do
44
- base_ru
45
- update_app(code(1))
46
- @ru.require(@filename){|f| :ObjectSpace}
47
- ru.call({}).must_equal [1]
48
- update_app(code(2))
49
- ru.call({}).must_equal [2]
50
- log_match %r{\ALoading.*spec/app\.rb\z},
51
- %r{\ANew classes in .*spec/app\.rb: App\z},
52
- %r{\AUnloading.*spec/app\.rb\z},
53
- "Removed constant App",
54
- %r{\ALoading.*spec/app\.rb\z},
55
- %r{\ANew classes in .*spec/app\.rb: App\z}
56
- end
57
-
58
- it "should pickup files added as dependencies" do
59
- ru.call({}).must_equal [1]
60
- update_app("RU.require 'spec/app2.rb'; class App; def self.call(env) [@a, App2.call(env)] end; @a ||= []; @a << 2; end")
61
- update_app("class App2; def self.call(env) @a end; @a ||= []; @a << 3; end", 'spec/app2.rb')
62
- ru.call({}).must_equal [[2], [3]]
63
- update_app("class App2; def self.call(env) @a end; @a ||= []; @a << 4; end", 'spec/app2.rb')
64
- ru.call({}).must_equal [[2], [4]]
65
- log_match %r{\ALoading.*spec/app\.rb\z},
66
- %r{\ANew classes in .*spec/app\.rb: App\z},
67
- %r{\AUnloading.*spec/app\.rb\z},
68
- "Removed constant App",
69
- %r{\ALoading.*spec/app\.rb\z},
70
- %r{\ALoading.*spec/app2\.rb\z},
71
- %r{\ANew classes in .*spec/app2\.rb: App2\z},
72
- %r{\ANew classes in .*spec/app\.rb: (App App2|App2 App)\z},
73
- %r{\ANew features in .*spec/app\.rb: .*spec/app2\.rb\z},
74
- %r{\AUnloading.*spec/app2\.rb\z},
75
- "Removed constant App2",
76
- %r{\ALoading.*spec/app2\.rb\z},
77
- %r{\ANew classes in .*spec/app2\.rb: App2\z}
78
- end
79
-
80
- it "should support :subclasses option and only unload subclasses of given class" do
81
- ru(:subclasses=>'App').call({}).must_equal [1]
82
- update_app("RU.require 'spec/app2.rb'; class App; def self.call(env) [@a, App2.call(env)] end; @a ||= []; @a << 2; end")
83
- update_app("class App2 < App; def self.call(env) @a end; @a ||= []; @a << 3; end", 'spec/app2.rb')
84
- ru.call({}).must_equal [[1, 2], [3]]
85
- update_app("class App2 < App; def self.call(env) @a end; @a ||= []; @a << 4; end", 'spec/app2.rb')
86
- ru.call({}).must_equal [[1, 2], [4]]
87
- update_app("RU.require 'spec/app2.rb'; class App; def self.call(env) [@a, App2.call(env)] end; @a ||= []; @a << 2; end")
88
- log_match %r{\ALoading.*spec/app\.rb\z},
89
- %r{\AUnloading.*spec/app\.rb\z},
90
- %r{\ALoading.*spec/app\.rb\z},
91
- %r{\ALoading.*spec/app2\.rb\z},
92
- %r{\ANew classes in .*spec/app2\.rb: App2\z},
93
- %r{\ANew classes in .*spec/app\.rb: App2\z},
94
- %r{\ANew features in .*spec/app\.rb: .*spec/app2\.rb\z},
95
- %r{\AUnloading.*spec/app2\.rb\z},
96
- "Removed constant App2",
97
- %r{\ALoading.*spec/app2\.rb\z},
98
- %r{\ANew classes in .*spec/app2\.rb: App2\z}
99
- end
100
-
101
- it "should log invalid constant names in :subclasses options" do
102
- ru(:subclasses=>%w'1 Object').call({}).must_equal [1]
103
- logger.uniq!
104
- log_match 'Invalid constant name: 1',
105
- %r{\ALoading.*spec/app\.rb\z},
106
- %r{\ANew classes in .*spec/app\.rb: App\z}
107
- end
108
-
109
- it "should unload modules before reloading similar to classes" do
110
- ru(:code=>"module App; def self.call(env) @a end; @a ||= []; @a << 1; end").call({}).must_equal [1]
111
- update_app("module App; def self.call(env) @a end; @a ||= []; @a << 2; end")
112
- ru.call({}).must_equal [2]
113
- log_match %r{\ALoading.*spec/app\.rb\z},
114
- %r{\ANew classes in .*spec/app\.rb: App\z},
115
- %r{\AUnloading.*spec/app\.rb\z},
116
- "Removed constant App",
117
- %r{\ALoading.*spec/app\.rb\z},
118
- %r{\ANew classes in .*spec/app\.rb: App\z}
119
- end
120
-
121
- it "should unload specific modules by name via :subclasses option" do
122
- ru(:subclasses=>'App', :code=>"module App; def self.call(env) @a end; @a ||= []; @a << 1; end").call({}).must_equal [1]
123
- update_app("module App; def self.call(env) @a end; @a ||= []; @a << 2; end")
124
- ru.call({}).must_equal [2]
125
- log_match %r{\ALoading.*spec/app\.rb\z},
126
- %r{\ANew classes in .*spec/app\.rb: App\z},
127
- %r{\AUnloading.*spec/app\.rb\z},
128
- "Removed constant App",
129
- %r{\ALoading.*spec/app\.rb\z},
130
- %r{\ANew classes in .*spec/app\.rb: App\z}
131
- end
132
-
133
- it "should not unload modules by name if :subclasses option used and module not present" do
134
- ru(:subclasses=>'Foo', :code=>"module App; def self.call(env) @a end; @a ||= []; @a << 1; end").call({}).must_equal [1]
135
- update_app("module App; def self.call(env) @a end; @a ||= []; @a << 2; end")
136
- ru.call({}).must_equal [1, 2]
137
- log_match %r{\ALoading.*spec/app\.rb\z},
138
- %r{\AUnloading.*spec/app\.rb\z},
139
- %r{\ALoading.*spec/app\.rb\z}
140
- end
141
-
142
- it "should unload partially loaded modules if loading fails, and allow future loading" do
143
- ru.call({}).must_equal [1]
144
- update_app("module App; def self.call(env) @a end; @a ||= []; raise 'foo'; end")
145
- proc{ru.call({})}.must_raise RuntimeError
146
- defined?(::App).must_be_nil
147
- update_app(code(2))
148
- ru.call({}).must_equal [2]
149
- log_match %r{\ALoading.*spec/app\.rb\z},
150
- %r{\ANew classes in .*spec/app\.rb: App\z},
151
- %r{\AUnloading.*spec/app\.rb\z},
152
- "Removed constant App",
153
- %r{\ALoading.*spec/app\.rb\z},
154
- %r{\AFailed to load .*spec/app\.rb; removing partially defined constants\z},
155
- "Removed constant App",
156
- %r{\ALoading.*spec/app\.rb\z},
157
- %r{\ANew classes in .*spec/app\.rb: App\z}
158
- end
159
-
160
- it "should unload classes in namespaces" do
161
- ru(:code=>"class Array::App; def self.call(env) @a end; @a ||= []; @a << 1; end", :block=>proc{Array::App}).call({}).must_equal [1]
162
- update_app("class Array::App; def self.call(env) @a end; @a ||= []; @a << 2; end")
163
- ru.call({}).must_equal [2]
164
- log_match %r{\ALoading.*spec/app\.rb\z},
165
- %r{\ANew classes in .*spec/app\.rb: Array::App\z},
166
- %r{\AUnloading.*spec/app\.rb\z},
167
- "Removed constant Array::App",
168
- %r{\ALoading.*spec/app\.rb\z},
169
- %r{\ANew classes in .*spec/app\.rb: Array::App\z}
170
- end
171
-
172
- it "should not unload class defined in dependency if already defined in parent" do
173
- base_ru
174
- update_app("class App; def self.call(env) @a end; @a ||= []; @a << 2; RU.require 'spec/app2.rb'; end")
175
- update_app("class App; @a << 3 end", 'spec/app2.rb')
176
- @ru.require 'spec/app.rb'
177
- ru.call({}).must_equal [2, 3]
178
- update_app("class App; @a << 4 end", 'spec/app2.rb')
179
- ru.call({}).must_equal [2, 3, 4]
180
- update_app("class App; def self.call(env) @a end; @a ||= []; @a << 2; RU.require 'spec/app2.rb'; end")
181
- ru.call({}).must_equal [2, 4]
182
- log_match %r{\ALoading.*spec/app\.rb\z},
183
- %r{\ALoading.*spec/app2\.rb\z},
184
- %r{\ANew classes in .*spec/app\.rb: App\z},
185
- %r{\ANew features in .*spec/app\.rb: .*spec/app2\.rb\z},
186
- %r{\AUnloading.*spec/app2\.rb\z},
187
- %r{\ALoading.*spec/app2\.rb\z},
188
- %r{\AUnloading.*spec/app\.rb\z},
189
- %r{\AUnloading.*spec/app2\.rb\z},
190
- "Removed constant App",
191
- %r{\ALoading.*spec/app\.rb\z},
192
- %r{\ALoading.*spec/app2\.rb\z},
193
- %r{\ANew classes in .*spec/app\.rb: App\z},
194
- %r{\ANew features in .*spec/app\.rb: .*spec/app2\.rb\z}
195
- end
196
-
197
- it "should allow specifying proc for which constants get removed" do
198
- base_ru
199
- update_app("class App; def self.call(env) [@a, App2.a] end; @a ||= []; @a << 1; end; class App2; def self.a; @a end; @a ||= []; @a << 2; end")
200
- @ru.require('spec/app.rb'){|f| File.basename(f).sub(/\.rb/, '').capitalize}
201
- ru.call({}).must_equal [[1], [2]]
202
- update_app("class App; def self.call(env) [@a, App2.a] end; @a ||= []; @a << 3; end; class App2; def self.a; @a end; @a ||= []; @a << 4; end")
203
- ru.call({}).must_equal [[3], [2, 4]]
204
- log_match %r{\ALoading.*spec/app\.rb\z},
205
- %r{\ANew classes in .*spec/app\.rb: App\z},
206
- %r{\AUnloading.*spec/app\.rb\z},
207
- "Removed constant App",
208
- %r{\ALoading.*spec/app\.rb\z},
209
- %r{\ANew classes in .*spec/app\.rb: App\z}
210
- end
211
-
212
- it "should handle anonymous classes" do
213
- base_ru(:block=>proc{$app})
214
- update_app("$app = Class.new do def self.call(env) @a end; @a ||= []; @a << 1; end")
215
- @ru.require('spec/app.rb')
216
- ru.call({}).must_equal [1]
217
- update_app("$app = Class.new do def self.call(env) @a end; @a ||= []; @a << 2; end")
218
- ru.call({}).must_equal [2]
219
- log_match %r{\ALoading.*spec/app\.rb\z},
220
- %r{\AUnloading.*spec/app\.rb\z},
221
- %r{\ALoading.*spec/app\.rb\z}
222
- end
223
-
224
- it "should log when attempting to remove a class that doesn't exist" do
225
- base_ru
226
- update_app(code(1))
227
- @ru.require('spec/app.rb'){|f| 'Foo'}
228
- ru.call({}).must_equal [1]
229
- update_app(code(2))
230
- ru.call({}).must_equal [1, 2]
231
- log_match %r{\ALoading.*spec/app\.rb\z},
232
- %r{\AConstants not defined after loading .*spec/app\.rb: Foo\z},
233
- %r{\AUnloading.*spec/app\.rb\z},
234
- "Error removing constant: Foo",
235
- %r{\ALoading.*spec/app\.rb\z},
236
- %r{\AConstants not defined after loading .*spec/app\.rb: Foo\z}
237
- end
238
-
239
- it "should log when specifying a constant that already exists" do
240
- base_ru
241
- update_app(code(1))
242
- ::App2 = 1
243
- @ru.require('spec/app.rb'){|f| 'App2'}
244
- ru.call({}).must_equal [1]
245
- log_match %r{\AConstants already defined before loading .*spec/app\.rb: App2\z},
246
- %r{\ALoading.*spec/app\.rb\z},
247
- %r{\ANew classes in .*spec/app\.rb: App2\z}
248
- end
249
-
250
- it "should handle recorded dependencies" do
251
- base_ru
252
- update_app("module A; B = 1; end", 'spec/app_mod.rb')
253
- update_app("class App; A = ::A; def self.call(env) A::B end; end")
254
- ru.require 'spec/app_mod.rb'
255
- ru.require 'spec/app.rb'
256
- ru.record_dependency 'spec/app_mod.rb', 'spec/app.rb'
257
- ru.call({}).must_equal 1
258
- update_app("module A; B = 2; end", 'spec/app_mod.rb')
259
- ru.call({}).must_equal 2
260
- update_app("module A; include C; end", 'spec/app_mod.rb')
261
- update_app("module C; B = 3; end", 'spec/app_mod2.rb')
262
- ru.record_dependency 'spec/app_mod2.rb', 'spec/app_mod.rb'
263
- ru.require 'spec/app_mod2.rb'
264
- ru.call({}).must_equal 3
265
- update_app("module C; B = 4; end", 'spec/app_mod2.rb')
266
- ru.call({}).must_equal 4
267
- end
268
-
269
- describe "with a directory" do
270
- include Minitest::Hooks
271
-
272
- before(:all) do
273
- Dir.mkdir('spec/dir')
274
- Dir.mkdir('spec/dir/subdir')
275
- Dir.mkdir('spec/dir/subdir2')
276
- end
277
-
278
- after do
279
- Dir['spec/dir/**/*.rb'].each{|f| File.delete(f)}
280
- end
281
-
282
- after(:all) do
283
- Dir.rmdir('spec/dir/subdir')
284
- Dir.rmdir('spec/dir/subdir2')
285
- Dir.rmdir('spec/dir')
286
- end
287
-
288
- it "should have unreloader require with directories if reload option is false" do
289
- file = 'spec/dir/app_no_reload3.rb'
290
- File.open(file, 'wb'){|f| f.write('ANR3 = 3')}
291
- base_ru(:reload => false)
292
- ru.require 'spec/dir'
293
- ANR3.must_equal 3
294
- end
295
-
296
- it "should handle recorded dependencies in directories" do
297
- base_ru
298
- update_app("module A; B = 1; end", 'spec/dir/subdir/app_mod.rb')
299
- update_app("class App; A = ::A; def self.call(env) A::B end; end")
300
- ru.require 'spec/dir/subdir'
301
- ru.require 'spec/app.rb'
302
- ru.record_dependency 'spec/dir/subdir', 'spec/app.rb'
303
- ru.call({}).must_equal 1
304
- update_app("module A; B = 2; end", 'spec/dir/subdir/app_mod.rb')
305
- ru.call({}).must_equal 2
306
- update_app("module A; include C; end", 'spec/dir/subdir/app_mod.rb')
307
- update_app("module C; B = 3; end", 'spec/dir/subdir2/app_mod2.rb')
308
- ru.require 'spec/dir/subdir2/app_mod2.rb'
309
- ru.record_dependency 'spec/dir/subdir2/app_mod2.rb', 'spec/dir/subdir'
310
- ru.call({}).must_equal 3
311
- update_app("module C; B = 4; end", 'spec/dir/subdir2/app_mod2.rb')
312
- ru.call({}).must_equal 4
313
- end
314
-
315
- it "should handle recorded dependencies in directories when files are added or removed later" do
316
- base_ru
317
- update_app("class App; A = defined?(::A) ? ::A : Module.new{self::B = 0}; def self.call(env) A::B end; end")
318
- ru.record_dependency 'spec/dir/subdir', 'spec/app.rb'
319
- ru.record_dependency 'spec/dir/subdir2', 'spec/dir/subdir'
320
- ru.require 'spec/app.rb'
321
- ru.require 'spec/dir/subdir'
322
- ru.require 'spec/dir/subdir2'
323
- ru.call({}).must_equal 0
324
- update_app("module A; B = 1; end", 'spec/dir/subdir/app_mod.rb')
325
- ru.call({}).must_equal 1
326
- update_app("module A; B = 2; end", 'spec/dir/subdir/app_mod.rb')
327
- ru.call({}).must_equal 2
328
- update_app("module C; B = 3; end", 'spec/dir/subdir2/app_mod2.rb')
329
- ru.call({}).must_equal 2
330
- update_app("module A; include C; end", 'spec/dir/subdir/app_mod.rb')
331
- ru.call({}).must_equal 3
332
- update_app("module C; B = 4; end", 'spec/dir/subdir2/app_mod2.rb')
333
- ru.call({}).must_equal 4
334
- File.delete 'spec/dir/subdir/app_mod.rb'
335
- ru.call({}).must_equal 0
336
- end
337
-
338
- it "should handle classes split into multiple files" do
339
- base_ru
340
- update_app("class App; RU.require('spec/dir'); def self.call(env) \"\#{a if respond_to?(:a)}\#{b if respond_to?(:b)}1\".to_i end; end")
341
- ru.require 'spec/app.rb'
342
- ru.record_split_class 'spec/app.rb', 'spec/dir'
343
- ru.call({}).must_equal 1
344
- update_app("class App; def self.a; 2 end end", 'spec/dir/appa.rb')
345
- ru.call({}).must_equal 21
346
- update_app("class App; def self.a; 3 end end", 'spec/dir/appa.rb')
347
- ru.call({}).must_equal 31
348
- update_app("class App; def self.b; 4 end end", 'spec/dir/appb.rb')
349
- ru.call({}).must_equal 341
350
- update_app("class App; def self.a; 5 end end", 'spec/dir/appa.rb')
351
- update_app("class App; def self.b; 6 end end", 'spec/dir/appb.rb')
352
- ru.call({}).must_equal 561
353
- update_app("class App; end", 'spec/dir/appa.rb')
354
- ru.call({}).must_equal 61
355
- File.delete 'spec/dir/appb.rb'
356
- ru.call({}).must_equal 1
357
- end
358
-
359
- it "should pick up changes to files in that directory" do
360
- base_ru
361
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
362
- update_app("App.call[:foo] = 1", 'spec/dir/a.rb')
363
- @ru.require('spec/app.rb')
364
- ru.call({}).must_equal(:foo=>1)
365
- update_app("App.call[:foo] = 2", 'spec/dir/a.rb')
366
- ru.call({}).must_equal(:foo=>2)
367
- log_match %r{\ALoading.*spec/app\.rb\z},
368
- %r{\ALoading.*spec/dir/a\.rb\z},
369
- %r{\ANew classes in .*spec/app\.rb: App\z},
370
- %r{\ANew features in .*spec/app\.rb: .*spec/dir/a\.rb\z},
371
- %r{\AUnloading .*/spec/dir/a.rb\z},
372
- %r{\ALoading .*/spec/dir/a.rb\z}
373
- end
374
-
375
- it "should pick up changes to files in subdirectories" do
376
- base_ru
377
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
378
- update_app("App.call[:foo] = 1", 'spec/dir/subdir/a.rb')
379
- @ru.require('spec/app.rb')
380
- ru.call({}).must_equal(:foo=>1)
381
- update_app("App.call[:foo] = 2", 'spec/dir/subdir/a.rb')
382
- ru.call({}).must_equal(:foo=>2)
383
- log_match %r{\ALoading.*spec/app\.rb\z},
384
- %r{\ALoading.*spec/dir/subdir/a\.rb\z},
385
- %r{\ANew classes in .*spec/app\.rb: App\z},
386
- %r{\ANew features in .*spec/app\.rb: .*spec/dir/subdir/a\.rb\z},
387
- %r{\AUnloading .*/spec/dir/subdir/a.rb\z},
388
- %r{\ALoading .*/spec/dir/subdir/a.rb\z}
389
- end
390
-
391
- it "should pick up new files added to the directory" do
392
- base_ru
393
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
394
- @ru.require('spec/app.rb')
395
- ru.call({}).must_equal({})
396
- update_app("App.call[:foo] = 2", 'spec/dir/a.rb')
397
- ru.call({}).must_equal(:foo=>2)
398
- log_match %r{\ALoading.*spec/app\.rb\z},
399
- %r{\ANew classes in .*spec/app\.rb: App\z},
400
- %r{\ALoading.*spec/dir/a\.rb\z}
401
- end
402
-
403
- it "should pick up new files added to subdirectories" do
404
- base_ru
405
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
406
- @ru.require('spec/app.rb')
407
- ru.call({}).must_equal({})
408
- update_app("App.call[:foo] = 2", 'spec/dir/subdir/a.rb')
409
- ru.call({}).must_equal(:foo=>2)
410
- log_match %r{\ALoading.*spec/app\.rb\z},
411
- %r{\ANew classes in .*spec/app\.rb: App\z},
412
- %r{\ALoading.*spec/dir/subdir/a\.rb\z}
413
- end
414
-
415
- it "should drop files deleted from the directory" do
416
- base_ru
417
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
418
- update_app("App.call[:foo] = 1", 'spec/dir/a.rb')
419
- @ru.require('spec/app.rb')
420
- ru.call({}).must_equal(:foo=>1)
421
- File.delete('spec/dir/a.rb')
422
- update_app("App.call[:foo] = 2", 'spec/dir/b.rb')
423
- ru.call({}).must_equal(:foo=>2)
424
- log_match %r{\ALoading.*spec/app\.rb\z},
425
- %r{\ALoading.*spec/dir/a\.rb\z},
426
- %r{\ANew classes in .*spec/app\.rb: App\z},
427
- %r{\ANew features in .*spec/app\.rb: .*spec/dir/a\.rb\z},
428
- %r{\AUnloading .*/spec/dir/a.rb\z},
429
- %r{\ALoading.*spec/dir/b\.rb\z}
430
- end
431
-
432
- it "should drop files deleted from subdirectories" do
433
- base_ru
434
- update_app("class App; @a = {}; def self.call(env=nil) @a end; end; RU.require 'spec/dir'")
435
- update_app("App.call[:foo] = 1", 'spec/dir/subdir/a.rb')
436
- @ru.require('spec/app.rb')
437
- ru.call({}).must_equal(:foo=>1)
438
- File.delete('spec/dir/subdir/a.rb')
439
- update_app("App.call[:foo] = 2", 'spec/dir/subdir/b.rb')
440
- ru.call({}).must_equal(:foo=>2)
441
- log_match %r{\ALoading.*spec/app\.rb\z},
442
- %r{\ALoading.*spec/dir/subdir/a\.rb\z},
443
- %r{\ANew classes in .*spec/app\.rb: App\z},
444
- %r{\ANew features in .*spec/app\.rb: .*spec/dir/subdir/a\.rb\z},
445
- %r{\AUnloading .*/spec/dir/subdir/a.rb\z},
446
- %r{\ALoading.*spec/dir/subdir/b\.rb\z}
447
- end
448
- end
449
- end