adsl 0.0.3 → 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (91) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +2 -20
  3. data/README.md +14 -21
  4. data/bin/adsl-verify +8 -8
  5. data/lib/adsl.rb +3 -0
  6. data/lib/adsl/adsl.rb +3 -0
  7. data/lib/adsl/ds/data_store_spec.rb +339 -0
  8. data/lib/adsl/extract/instrumenter.rb +206 -0
  9. data/lib/adsl/extract/meta.rb +33 -0
  10. data/lib/adsl/extract/rails/action_block_builder.rb +233 -0
  11. data/lib/adsl/extract/rails/action_instrumenter.rb +400 -0
  12. data/lib/adsl/extract/rails/action_runner.rb +57 -0
  13. data/lib/adsl/extract/rails/active_record_metaclass_generator.rb +555 -0
  14. data/lib/adsl/extract/rails/callback_chain_simulator.rb +135 -0
  15. data/lib/adsl/extract/rails/invariant_extractor.rb +48 -0
  16. data/lib/adsl/extract/rails/invariant_instrumenter.rb +70 -0
  17. data/lib/adsl/extract/rails/other_meta.rb +57 -0
  18. data/lib/adsl/extract/rails/rails_extractor.rb +211 -0
  19. data/lib/adsl/extract/rails/rails_instrumentation_test_case.rb +34 -0
  20. data/lib/adsl/extract/rails/rails_special_gem_instrumentation.rb +120 -0
  21. data/lib/adsl/extract/rails/rails_test_helper.rb +140 -0
  22. data/lib/adsl/extract/sexp_utils.rb +54 -0
  23. data/lib/adsl/fol/first_order_logic.rb +261 -0
  24. data/lib/adsl/parser/adsl_parser.racc +159 -0
  25. data/lib/{parser → adsl/parser}/adsl_parser.rex +4 -4
  26. data/lib/{parser → adsl/parser}/adsl_parser.rex.rb +6 -6
  27. data/lib/adsl/parser/adsl_parser.tab.rb +1031 -0
  28. data/lib/adsl/parser/ast_nodes.rb +1410 -0
  29. data/lib/adsl/railtie.rb +67 -0
  30. data/lib/adsl/spass/bin.rb +230 -0
  31. data/lib/{spass → adsl/spass}/ruby_extensions.rb +0 -0
  32. data/lib/adsl/spass/spass_ds_extensions.rb +931 -0
  33. data/lib/adsl/spass/spass_translator.rb +393 -0
  34. data/lib/adsl/spass/util.rb +13 -0
  35. data/lib/adsl/util/csv_hash_formatter.rb +94 -0
  36. data/lib/adsl/util/general.rb +228 -0
  37. data/lib/adsl/util/test_helper.rb +71 -0
  38. data/lib/adsl/verification/formula_generators.rb +231 -0
  39. data/lib/adsl/verification/instrumentation_filter.rb +50 -0
  40. data/lib/adsl/verification/invariant.rb +19 -0
  41. data/lib/adsl/verification/rails_verification.rb +33 -0
  42. data/lib/adsl/verification/utils.rb +20 -0
  43. data/lib/adsl/verification/verification_case.rb +13 -0
  44. data/test/integration/rails/rails_branch_verification_test.rb +112 -0
  45. data/test/integration/rails/rails_verification_test.rb +253 -0
  46. data/test/integration/spass/basic_translation_test.rb +563 -0
  47. data/test/integration/spass/control_flow_translation_test.rb +421 -0
  48. data/test/unit/adsl/ds/data_store_spec_test.rb +54 -0
  49. data/test/unit/adsl/extract/instrumenter_test.rb +103 -0
  50. data/test/unit/adsl/extract/meta_test.rb +142 -0
  51. data/test/unit/adsl/extract/rails/action_block_builder_test.rb +178 -0
  52. data/test/unit/adsl/extract/rails/action_instrumenter_test.rb +68 -0
  53. data/test/unit/adsl/extract/rails/active_record_metaclass_generator_test.rb +336 -0
  54. data/test/unit/adsl/extract/rails/callback_chain_simulator_test.rb +76 -0
  55. data/test/unit/adsl/extract/rails/invariant_extractor_test.rb +92 -0
  56. data/test/unit/adsl/extract/rails/rails_extractor_test.rb +1380 -0
  57. data/test/unit/adsl/extract/rails/rails_test_helper_test.rb +25 -0
  58. data/test/unit/adsl/extract/sexp_utils_test.rb +100 -0
  59. data/test/unit/adsl/fol/first_order_logic_test.rb +227 -0
  60. data/test/unit/adsl/parser/action_parser_test.rb +1040 -0
  61. data/test/unit/adsl/parser/ast_nodes_test.rb +359 -0
  62. data/test/unit/adsl/parser/class_parser_test.rb +288 -0
  63. data/test/unit/adsl/parser/general_parser_test.rb +67 -0
  64. data/test/unit/adsl/parser/invariant_parser_test.rb +432 -0
  65. data/test/unit/adsl/parser/parser_util_test.rb +126 -0
  66. data/test/unit/adsl/spass/bin_test.rb +65 -0
  67. data/test/unit/adsl/spass/ruby_extensions_test.rb +39 -0
  68. data/test/unit/adsl/spass/spass_ds_extensions_test.rb +7 -0
  69. data/test/unit/adsl/spass/spass_translator_test.rb +342 -0
  70. data/test/unit/adsl/util/csv_hash_formatter_test.rb +68 -0
  71. data/test/unit/adsl/util/general_test.rb +303 -0
  72. data/test/unit/adsl/util/test_helper_test.rb +120 -0
  73. data/test/unit/adsl/verification/formula_generators_test.rb +200 -0
  74. data/test/unit/adsl/verification/instrumentation_filter_test.rb +39 -0
  75. data/test/unit/adsl/verification/utils_test.rb +39 -0
  76. data/test/unit/adsl/verification/verification_case_test.rb +8 -0
  77. metadata +229 -29
  78. data/lib/ds/data_store_spec.rb +0 -292
  79. data/lib/fol/first_order_logic.rb +0 -260
  80. data/lib/parser/adsl_ast.rb +0 -779
  81. data/lib/parser/adsl_parser.racc +0 -151
  82. data/lib/parser/adsl_parser.tab.rb +0 -976
  83. data/lib/parser/dsdl_parser.rex.rb +0 -196
  84. data/lib/parser/dsdl_parser.tab.rb +0 -976
  85. data/lib/spass/bin.rb +0 -164
  86. data/lib/spass/spass_ds_extensions.rb +0 -870
  87. data/lib/spass/spass_translator.rb +0 -388
  88. data/lib/spass/util.rb +0 -11
  89. data/lib/util/csv_hash_formatter.rb +0 -47
  90. data/lib/util/test_helper.rb +0 -33
  91. data/lib/util/util.rb +0 -114
@@ -0,0 +1,1380 @@
1
+ require 'test/unit'
2
+ require 'adsl/util/test_helper'
3
+ require 'adsl/parser/ast_nodes'
4
+ require 'adsl/extract/rails/rails_extractor'
5
+ require 'adsl/extract/rails/rails_test_helper'
6
+ require 'adsl/extract/rails/rails_instrumentation_test_case'
7
+
8
+ class ADSL::Extract::Rails::RailsExtractorTest < ADSL::Extract::Rails::RailsInstrumentationTestCase
9
+ include ::ADSL::Parser
10
+
11
+ def test_setup__routes
12
+ route_set = ADSLRailsTestApplication.routes.routes
13
+
14
+ assert route_set.map{ |route| route.ast.to_s }.include? '/asds/nothing(.:format)'
15
+ end
16
+
17
+ def test_setup__active_record
18
+ assert_false self.class.lookup_const(:Asd).nil?
19
+ assert_false self.class.lookup_const(:Kme).nil?
20
+ assert_false self.class.lookup_const('Mod::Blah').nil?
21
+ end
22
+
23
+ def test_setup__urls_visible
24
+ session = ActionDispatch::Integration::Session.new(Rails.application)
25
+ session.get('/asds/nothing')
26
+ assert_equal 200, session.response.status
27
+ assert session.response.body.strip.empty?
28
+
29
+ session = ActionDispatch::Integration::Session.new(Rails.application)
30
+ assert_raise ActionController::RoutingError do
31
+ session.get('thisdoesntexist')
32
+ end
33
+ end
34
+
35
+ def test_setup__rails_crashes_actually_crash_tests
36
+ assert_raise do
37
+ session = ActionDispatch::Integration::Session.new(Rails.application)
38
+ session.get('no_route')
39
+ end
40
+ end
41
+
42
+ def test_action_extraction__empty_action
43
+ extractor = create_rails_extractor
44
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
45
+ assert ast.block.statements.empty?
46
+ end
47
+
48
+ def test_action_extraction__create_action
49
+ AsdsController.class_exec do
50
+ def create
51
+ Asd.new
52
+ respond_to
53
+ end
54
+ end
55
+
56
+ extractor = create_rails_extractor
57
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
58
+ statements = ast.block.statements
59
+
60
+ assert_equal 1, statements.length
61
+ assert_equal ASTObjsetStmt, statements.first.class
62
+ assert_equal ASTCreateObjset, statements.first.objset.class
63
+ assert_equal 'Asd', statements.first.objset.class_name.text
64
+ end
65
+
66
+ def test_action_extraction__create_within_expression_action
67
+ AsdsController.class_exec do
68
+ def create
69
+ Asd.build
70
+ respond_to
71
+ end
72
+ end
73
+
74
+ extractor = create_rails_extractor
75
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
76
+ statements = ast.block.statements
77
+
78
+ assert_equal 1, statements.length
79
+ assert_equal ASTObjsetStmt, statements.first.class
80
+ assert_equal ASTCreateObjset, statements.first.objset.class
81
+ assert_equal 'Asd', statements.first.objset.class_name.text
82
+ end
83
+
84
+ def test_action_extraction__variable_assignment
85
+ AsdsController.class_exec do
86
+ def create
87
+ a = Asd.new
88
+ a.delete!
89
+ respond_to
90
+ end
91
+ end
92
+
93
+ extractor = create_rails_extractor
94
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
95
+ statements = ast.block.statements
96
+
97
+ assert_equal 2, statements.length
98
+ assert_equal ASTAssignment, statements.first.class
99
+ assert_equal 'a', statements.first.var_name.text
100
+ assert_equal ASTCreateObjset, statements.first.objset.class
101
+ assert_equal 'Asd', statements.first.objset.class_name.text
102
+ end
103
+
104
+ def test_action_extraction__nil_assignment
105
+ AsdsController.class_exec do
106
+ def nothing
107
+ a = nil
108
+ a = Asd.new
109
+ a.delete!
110
+ respond_to
111
+ end
112
+ end
113
+
114
+ extractor = create_rails_extractor
115
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
116
+ statements = ast.block.statements
117
+
118
+ assert_equal 3, statements.length
119
+
120
+ assert_equal ASTAssignment, statements[0].class
121
+ assert_equal 'a', statements[0].var_name.text
122
+ assert_equal ASTEmptyObjset, statements[0].objset.class
123
+
124
+ assert_equal ASTAssignment, statements[1].class
125
+ assert_equal 'a', statements[1].var_name.text
126
+ assert_equal ASTCreateObjset, statements[1].objset.class
127
+ assert_equal 'Asd', statements[1].objset.class_name.text
128
+ end
129
+
130
+ def test_action_extraction__instance_variable_assignment
131
+ AsdsController.class_exec do
132
+ def create
133
+ @a = Asd.new
134
+ @a.save!
135
+ a = nil
136
+ @a.delete! # will throw an exception if a == @a
137
+ respond_to
138
+ end
139
+ end
140
+
141
+ extractor = create_rails_extractor
142
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
143
+ statements = ast.block.statements
144
+
145
+ assert_equal 3, statements.length
146
+
147
+ # all instance variables are initialized to empty
148
+ assert_equal ASTAssignment, statements[0].class
149
+ assert_equal 'at__a', statements[0].var_name.text
150
+ assert_equal ASTEmptyObjset, statements[0].objset.class
151
+
152
+ assert_equal ASTAssignment, statements[1].class
153
+ assert_equal 'at__a', statements[1].var_name.text
154
+ assert_equal ASTCreateObjset, statements[1].objset.class
155
+ assert_equal 'Asd', statements[1].objset.class_name.text
156
+
157
+ assert_equal ASTDeleteObj, statements[2].class
158
+ assert_equal 'at__a', statements[2].objset.var_name.text
159
+ end
160
+
161
+ def test_action_extraction__class_variable_assignment
162
+ AsdsController.class_exec do
163
+ def create
164
+ @@a = Asd.new
165
+ @@a.save!
166
+ a = nil
167
+ @a = nil
168
+ @@a.delete! # will throw an exception if @@a == @a or @@ == a
169
+ respond_to
170
+ end
171
+ end
172
+
173
+ extractor = create_rails_extractor
174
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
175
+ statements = ast.block.statements
176
+
177
+ assert_false statements.empty?
178
+ assert_equal 3, statements.length
179
+
180
+ assert_equal ASTAssignment, statements[0].class
181
+ assert_equal 'atat__a', statements[0].var_name.text
182
+ assert_equal ASTEmptyObjset, statements[0].objset.class
183
+
184
+ assert_equal ASTAssignment, statements[1].class
185
+ assert_equal 'atat__a', statements[1].var_name.text
186
+ assert_equal ASTCreateObjset, statements[1].objset.class
187
+ assert_equal 'Asd', statements[1].objset.class_name.text
188
+
189
+ assert_equal ASTDeleteObj, statements[2].class
190
+ assert_equal ASTVariable, statements[2].objset.class
191
+ assert_equal 'atat__a', statements[2].objset.var_name.text
192
+ end
193
+
194
+ def test_action_extraction__assignments_dont_make_values_nil
195
+ AsdsController.class_exec do
196
+ def nothing
197
+ a = Mod::Blah.new
198
+ a.asd.delete
199
+ end
200
+ end
201
+
202
+ extractor = create_rails_extractor
203
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
204
+ statements = ast.block.statements
205
+
206
+ assert_equal 2, statements.length
207
+
208
+ assert_equal ASTAssignment, statements[0].class
209
+ assert_equal ASTCreateObjset, statements[0].objset.class
210
+ assert_equal 'Mod_Blah', statements[0].objset.class_name.text
211
+ assert_equal 'a', statements[0].var_name.text
212
+
213
+ assert_equal ASTDeleteObj, statements[1].class
214
+ assert_equal ASTDereference, statements[1].objset.class
215
+ assert_equal 'asd', statements[1].objset.rel_name.text
216
+ assert_equal ASTVariable, statements[1].objset.objset.class
217
+ assert_equal 'a', statements[1].objset.objset.var_name.text
218
+ end
219
+
220
+ def test_invariant_extraction__works
221
+ extractor = create_rails_extractor <<-invariants
222
+ invariant 'what', true
223
+ invariants
224
+
225
+ invariants = extractor.invariants
226
+ assert_equal 1, invariants.length
227
+ assert_equal 'what', invariants.first.name.text
228
+ assert_equal true, invariants.first.formula.bool_value
229
+ end
230
+
231
+ def test_action_extraction__nonreturning_branches
232
+ AsdsController.class_exec do
233
+ def nothing
234
+ if true
235
+ Asd.new
236
+ else
237
+ Asd.find.delete!
238
+ end
239
+ end
240
+ end
241
+
242
+ extractor = create_rails_extractor
243
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
244
+ statements = ast.block.statements
245
+
246
+ assert_equal 1, statements.length
247
+ assert_equal ASTEither, statements.first.class
248
+
249
+ either = statements.first
250
+
251
+ assert_equal 2, either.blocks.length
252
+ assert_equal 1, either.blocks.first.statements.length
253
+ assert_equal ASTCreateObjset, either.blocks.first.statements.first.objset.class
254
+ assert_equal 1, either.blocks.second.statements.length
255
+ assert_equal ASTDeleteObj, either.blocks.second.statements.first.class
256
+ end
257
+
258
+ def test_action_extraction__one_returning_branch
259
+ AsdsController.class_exec do
260
+ def nothing
261
+ if true
262
+ return Asd.new
263
+ else
264
+ Asd.build
265
+ end
266
+ Asd.find.delete!
267
+ end
268
+ end
269
+
270
+ extractor = create_rails_extractor
271
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
272
+ statements = ast.block.statements
273
+
274
+ assert_equal 1, statements.length
275
+ assert_equal ASTEither, statements.first.class
276
+
277
+ either = statements.first
278
+
279
+ assert_equal 2, either.blocks.length
280
+ assert_equal 1, either.blocks.first.statements.length
281
+ assert_equal ASTCreateObjset, either.blocks.first.statements.first.objset.class
282
+ assert_equal 2, either.blocks.second.statements.length
283
+ assert_equal ASTCreateObjset, either.blocks.second.statements.first.objset.class
284
+ assert_equal ASTDeleteObj, either.blocks.second.statements.second.class
285
+ end
286
+
287
+ def test_action_extraction__one_returning_branch_other_empty
288
+ AsdsController.class_exec do
289
+ def nothing
290
+ if true
291
+ return Asd.new
292
+ else
293
+ end
294
+ end
295
+ end
296
+
297
+ extractor = create_rails_extractor
298
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
299
+ statements = ast.block.statements
300
+
301
+ assert_equal 1, statements.length
302
+ assert_equal ASTObjsetStmt, statements.first.class
303
+ assert_equal ASTCreateObjset, statements.first.objset.class
304
+ end
305
+
306
+ def test_action_extraction__statements_after_return_are_ignored
307
+ AsdsController.class_exec do
308
+ def nothing
309
+ Asd.new
310
+ return
311
+ Asd.new
312
+ end
313
+ end
314
+
315
+ extractor = create_rails_extractor
316
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
317
+ statements = ast.block.statements
318
+
319
+ assert_equal 1, statements.length
320
+ assert_equal ASTObjsetStmt, statements.first.class
321
+ assert_equal ASTCreateObjset, statements.first.objset.class
322
+ end
323
+
324
+ def test_action_extraction__statements_after_return_in_branches_are_ignored
325
+ AsdsController.class_exec do
326
+ def nothing
327
+ if true
328
+ return Asd.new
329
+ else
330
+ return Kme.new
331
+ end
332
+ Asd.new
333
+ end
334
+ end
335
+
336
+ extractor = create_rails_extractor
337
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
338
+ statements = ast.block.statements
339
+
340
+ assert_equal 1, statements.length
341
+ assert_equal ASTEither, statements.first.class
342
+ assert_equal 1, statements.first.blocks[0].statements.length
343
+ assert_equal ASTCreateObjset, statements.first.blocks[0].statements.first.objset.class
344
+ assert_equal 'Asd', statements.first.blocks[0].statements.first.objset.class_name.text
345
+ assert_equal 1, statements.first.blocks[1].statements.length
346
+ assert_equal ASTCreateObjset, statements.first.blocks[1].statements.first.objset.class
347
+ assert_equal 'Kme', statements.first.blocks[1].statements.first.objset.class_name.text
348
+ end
349
+
350
+ def test_action_extraction__calls_of_method_with_multiple_paths
351
+ AsdsController.class_exec do
352
+ def something
353
+ if true
354
+ return Asd.new
355
+ else
356
+ Asd.find.delete!
357
+ end
358
+ end
359
+
360
+ def nothing
361
+ something
362
+ return Asd.new
363
+ end
364
+ end
365
+
366
+ extractor = create_rails_extractor
367
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
368
+ statements = ast.block.statements
369
+
370
+ assert_equal 2, statements.length
371
+ assert_equal ASTEither, statements.first.class
372
+ assert_equal ASTCreateObjset, statements.second.objset.class
373
+
374
+ either = statements.first
375
+
376
+ assert_equal 2, either.blocks.length
377
+ assert_equal 1, either.blocks.first.statements.length
378
+ assert_equal ASTCreateObjset, either.blocks.first.statements.first.objset.class
379
+ assert_equal 1, either.blocks.second.statements.length
380
+ assert_equal ASTDeleteObj, either.blocks.second.statements.first.class
381
+ end
382
+
383
+ def test_action_extraction__calls_of_method_with_compatible_return_values_but_sideeffects
384
+ AsdsController.class_exec do
385
+ def something
386
+ if true
387
+ Asd.new
388
+ else
389
+ Asd.find
390
+ end
391
+ end
392
+
393
+ def nothing
394
+ something
395
+ Kme.new
396
+ end
397
+ end
398
+
399
+ extractor = create_rails_extractor
400
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
401
+ statements = ast.block.statements
402
+
403
+ assert_equal 2, statements.length
404
+
405
+ assert_equal ASTEither, statements.first.class
406
+ assert_equal 1, statements.first.blocks[0].statements.length
407
+ assert_equal ASTCreateObjset, statements.first.blocks[0].statements.first.objset.class
408
+ assert_equal 0, statements.first.blocks[1].statements.length
409
+
410
+ assert_equal ASTObjsetStmt, statements.second.class
411
+ assert_equal ASTCreateObjset, statements.second.objset.class
412
+ end
413
+
414
+ def test_action_extraction__deep_call_chain
415
+ AsdsController.class_exec do
416
+ def some3
417
+ Asd.new
418
+ Asd.find
419
+ end
420
+ def some2; some3; end
421
+ def some1; some2; end
422
+ def nothing
423
+ some1.destroy!
424
+ end
425
+ end
426
+
427
+ extractor = create_rails_extractor
428
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
429
+ statements = ast.block.statements
430
+
431
+ # 4 because of the destroy dependency
432
+ assert_equal 4, statements.length
433
+
434
+ assert_equal ASTObjsetStmt, statements[0].class
435
+ assert_equal ASTCreateObjset, statements[0].objset.class
436
+ assert_equal 'Asd', statements[0].objset.class_name.text
437
+
438
+ assert_equal ASTDeleteObj, statements.last.class
439
+ assert_equal ASTOneOf, statements.last.objset.class
440
+ assert_equal ASTAllOf, statements.last.objset.objset.class
441
+ assert_equal 'Asd', statements.last.objset.objset.class_name.text
442
+ end
443
+
444
+ def test_action_extraction__multiple_return
445
+ AsdsController.class_exec do
446
+ def blah
447
+ return Asd.new, Kme.new
448
+ end
449
+
450
+ def nothing
451
+ blah
452
+ end
453
+ end
454
+
455
+ extractor = create_rails_extractor
456
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
457
+ statements = ast.block.statements
458
+
459
+ assert_equal 2, statements.length
460
+
461
+ assert_equal ASTCreateObjset, statements.first.objset.class
462
+ assert_equal 'Asd', statements.first.objset.class_name.text
463
+
464
+ assert_equal ASTCreateObjset, statements.second.objset.class
465
+ assert_equal 'Kme', statements.second.objset.class_name.text
466
+ end
467
+
468
+ def test_action_extraction__multiple_assignment
469
+ AsdsController.class_exec do
470
+ def nothing
471
+ a, b = Asd.new, Kme.new
472
+ a.delete!
473
+ b.delete!
474
+ end
475
+ end
476
+ extractor = create_rails_extractor
477
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
478
+ statements = ast.block.statements
479
+
480
+ assert_equal 4, statements.length
481
+
482
+ assert_equal ASTAssignment, statements[0].class
483
+ assert_equal 'a', statements[0].var_name.text
484
+ assert_equal ASTCreateObjset, statements[0].objset.class
485
+ assert_equal 'Asd', statements[0].objset.class_name.text
486
+
487
+ assert_equal ASTAssignment, statements[1].class
488
+ assert_equal 'b', statements[1].var_name.text
489
+ assert_equal ASTCreateObjset, statements[1].objset.class
490
+ assert_equal 'Kme', statements[1].objset.class_name.text
491
+
492
+ assert_equal ASTDeleteObj, statements[2].class
493
+ assert_equal 'a', statements[2].objset.var_name.text
494
+
495
+ assert_equal ASTDeleteObj, statements[3].class
496
+ assert_equal 'b', statements[3].objset.var_name.text
497
+ end
498
+
499
+ def test_action_extraction__optional_assignment_of_known_nil_variable
500
+ AsdsController.class_exec do
501
+ def nothing
502
+ a ||= Asd.new
503
+ a = Asd.find
504
+ a.delete!
505
+ end
506
+ end
507
+
508
+ extractor = create_rails_extractor
509
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
510
+ statements = ast.block.statements
511
+
512
+ assert_equal 4, statements.length
513
+
514
+ assert_equal ASTDeclareVar, statements[0].class
515
+ assert_equal 'a', statements[0].var_name.text
516
+ assert_equal ASTEither, statements[1].class
517
+ assert_equal 2, statements[1].blocks.length
518
+ assert statements[1].blocks[0].statements.empty?
519
+ assert_equal 1, statements[1].blocks[1].statements.length
520
+ assert_equal ASTAssignment, statements[1].blocks[1].statements[0].class
521
+ assert_equal 'a', statements[1].blocks[1].statements[0].var_name.text
522
+ assert_equal ASTCreateObjset, statements[1].blocks[1].statements[0].objset.class
523
+ assert_equal 'Asd', statements[1].blocks[1].statements[0].objset.class_name.text
524
+
525
+ assert_equal ASTAssignment, statements[2].class
526
+ assert_equal 'a', statements[2].var_name.text
527
+ assert_equal ASTOneOf, statements[2].objset.class
528
+ assert_equal ASTAllOf, statements[2].objset.objset.class
529
+ assert_equal 'Asd', statements[2].objset.objset.class_name.text
530
+ end
531
+
532
+ def test_action_extraction__optional_assignment_of_nonnil_variable
533
+ AsdsController.class_exec do
534
+ def nothing
535
+ a = Asd.new
536
+ a ||= Asd.find
537
+ a.delete!
538
+ end
539
+ end
540
+
541
+ extractor = create_rails_extractor
542
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
543
+ statements = ast.block.statements
544
+
545
+ assert_equal 4, statements.length
546
+
547
+ assert_equal ASTAssignment, statements[0].class
548
+ assert_equal 'a', statements[0].var_name.text
549
+ assert_equal ASTCreateObjset, statements[0].objset.class
550
+ assert_equal 'Asd', statements[0].objset.class_name.text
551
+
552
+ assert_equal ASTDeclareVar, statements[1].class
553
+ assert_equal 'a', statements[1].var_name.text
554
+ assert_equal ASTEither, statements[2].class
555
+ assert_equal 2, statements[2].blocks.length
556
+ assert statements[2].blocks[0].statements.empty?
557
+ assert_equal 1, statements[2].blocks[1].statements.length
558
+ assert_equal ASTAssignment, statements[2].blocks[1].statements[0].class
559
+ assert_equal 'a', statements[2].blocks[1].statements[0].var_name.text
560
+ assert_equal ASTOneOf, statements[2].blocks[1].statements[0].objset.class
561
+ assert_equal ASTAllOf, statements[2].blocks[1].statements[0].objset.objset.class
562
+ assert_equal 'Asd', statements[2].blocks[1].statements[0].objset.objset.class_name.text
563
+ end
564
+
565
+ def test_action_extraction__multiple_assignment_of_return
566
+ AsdsController.class_exec do
567
+ def blah
568
+ return Asd.new, Kme.new
569
+ end
570
+
571
+ def nothing
572
+ a, b = blah
573
+ a.delete!
574
+ b.delete!
575
+ end
576
+ end
577
+
578
+ extractor = create_rails_extractor
579
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
580
+ statements = ast.block.statements
581
+
582
+ assert_equal 4, statements.length
583
+
584
+ assert_equal ASTAssignment, statements[0].class
585
+ assert_equal 'a', statements[0].var_name.text
586
+ assert_equal ASTCreateObjset, statements[0].objset.class
587
+ assert_equal 'Asd', statements[0].objset.class_name.text
588
+
589
+ assert_equal ASTAssignment, statements[1].class
590
+ assert_equal 'b', statements[1].var_name.text
591
+ assert_equal ASTCreateObjset, statements[1].objset.class
592
+ assert_equal 'Kme', statements[1].objset.class_name.text
593
+
594
+ assert_equal ASTDeleteObj, statements[2].class
595
+ assert_equal 'a', statements[2].objset.var_name.text
596
+
597
+ assert_equal ASTDeleteObj, statements[3].class
598
+ assert_equal 'b', statements[3].objset.var_name.text
599
+ end
600
+
601
+ def test_action_extraction__variable_assignment_in_branch
602
+ AsdsController.class_exec do
603
+ def nothing
604
+ if true
605
+ a = "asd"
606
+ else
607
+ a = "blah"
608
+ end
609
+ return a
610
+ end
611
+ end
612
+
613
+ assert_nothing_raised do
614
+ extractor = create_rails_extractor
615
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
616
+ end
617
+ end
618
+
619
+ def test_callback_lookup
620
+ extractor = create_rails_extractor
621
+ assert_set_equal(
622
+ [:before, :after, :before2, :before_nothing, :after_nothing],
623
+ extractor.callbacks(AsdsController).map(&:filter)
624
+ )
625
+ end
626
+
627
+ def test_before_callbacks__instrumented
628
+ AsdsController.class_exec do
629
+ def before
630
+ Asd.new
631
+ end
632
+
633
+ def before_filter_action
634
+ Kme.new
635
+ end
636
+ end
637
+
638
+ extractor = create_rails_extractor
639
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :before_filter_action)
640
+ statements = ast.block.statements
641
+
642
+ assert_equal 2, statements.length
643
+ assert_equal 'Asd', statements[0].objset.class_name.text
644
+ assert_equal 'Kme', statements[1].objset.class_name.text
645
+ end
646
+
647
+ def test_after_callbacks__instrumented
648
+ AsdsController.class_exec do
649
+ def after_filter_action
650
+ Kme.new
651
+ end
652
+
653
+ def after
654
+ Asd.new
655
+ end
656
+ end
657
+
658
+ extractor = create_rails_extractor
659
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :after_filter_action)
660
+ statements = ast.block.statements
661
+
662
+ assert_equal 2, statements.length
663
+ assert_equal 'Kme', statements[0].objset.class_name.text
664
+ assert_equal 'Asd', statements[1].objset.class_name.text
665
+ end
666
+
667
+ def test_before_callbacks__can_have_branches_normally
668
+ AsdsController.class_exec do
669
+ def before
670
+ if true
671
+ return Kme.new
672
+ else
673
+ Asd.new
674
+ end
675
+ end
676
+
677
+ def before2
678
+ if true
679
+ Kme.new
680
+ else
681
+ end
682
+ end
683
+
684
+ def before_filter_action
685
+ Mod::Blah.new
686
+ end
687
+ end
688
+
689
+ extractor = create_rails_extractor
690
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :before_filter_action)
691
+ statements = ast.block.statements
692
+
693
+ assert_equal 3, statements.length
694
+
695
+ assert_equal ASTEither, statements[0].class
696
+ assert_equal 2, statements[0].blocks.length
697
+ blocks = statements[0].blocks
698
+ assert_equal 1, blocks[0].statements.length
699
+ assert_equal ASTObjsetStmt, blocks[0].statements[0].class
700
+ assert_equal 'Kme', blocks[0].statements[0].objset.class_name.text
701
+ assert_equal 1, blocks[1].statements.length
702
+ assert_equal ASTObjsetStmt, blocks[1].statements[0].class
703
+ assert_equal 'Asd', blocks[1].statements[0].objset.class_name.text
704
+
705
+ assert_equal ASTEither, statements[1].class
706
+ assert_equal 2, statements[1].blocks.length
707
+ blocks = statements[1].blocks
708
+ assert_equal 1, blocks[0].statements.length
709
+ assert_equal ASTObjsetStmt, blocks[0].statements[0].class
710
+ assert_equal 'Kme', blocks[0].statements[0].objset.class_name.text
711
+ assert_equal 0, blocks[1].statements.length
712
+
713
+ assert_equal ASTObjsetStmt, statements[2].class
714
+ assert_equal 'Mod_Blah', statements[2].objset.class_name.text
715
+ end
716
+
717
+ def test_after_callbacks__can_have_branches_normally
718
+ AsdsController.class_exec do
719
+ def after_filter_action
720
+ Mod::Blah.new
721
+ end
722
+
723
+ def after
724
+ if true
725
+ Kme.new
726
+ else
727
+ return Asd.new
728
+ end
729
+ end
730
+ end
731
+
732
+ extractor = create_rails_extractor
733
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :after_filter_action)
734
+ statements = ast.block.statements
735
+
736
+ assert_equal 2, statements.length
737
+
738
+ assert_equal ASTObjsetStmt, statements[0].class
739
+ assert_equal 'Mod_Blah', statements[0].objset.class_name.text
740
+
741
+ assert_equal ASTEither, statements[1].class
742
+ assert_equal 2, statements[1].blocks.length
743
+ blocks = statements[1].blocks
744
+ assert_equal 1, blocks[0].statements.length
745
+ assert_equal ASTObjsetStmt, blocks[0].statements[0].class
746
+ assert_equal 'Kme', blocks[0].statements[0].objset.class_name.text
747
+ assert_equal 1, blocks[1].statements.length
748
+ assert_equal ASTObjsetStmt, blocks[1].statements[0].class
749
+ assert_equal 'Asd', blocks[1].statements[0].objset.class_name.text
750
+ end
751
+
752
+ def test_callbacks__multiple_branched_callbacks
753
+ AsdsController.class_exec do
754
+ def before_nothing
755
+ if true
756
+ return Kme.new
757
+ else
758
+ Asd.new
759
+ end
760
+ end
761
+
762
+ def nothing
763
+ if true
764
+ Kme.new
765
+ else
766
+ return Mod::Blah.new
767
+ end
768
+ end
769
+
770
+ def after_nothing
771
+ if true
772
+ return Kme.new
773
+ else
774
+ Mod::Blah.new
775
+ end
776
+ end
777
+ end
778
+
779
+ extractor = create_rails_extractor
780
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
781
+ statements = ast.block.statements
782
+
783
+ assert_equal 3, statements.length
784
+
785
+ expected_classnames = ['Asd', 'Mod_Blah', 'Mod_Blah']
786
+ 3.times do |index|
787
+ assert_equal ASTEither, statements[index].class
788
+ blocks = statements[index].blocks
789
+ assert_equal 2, blocks.length
790
+ assert_equal 1, blocks[0].statements.length
791
+ assert_equal ASTObjsetStmt, blocks[0].statements[0].class
792
+ assert_equal 'Kme', blocks[0].statements[0].objset.class_name.text
793
+ assert_equal 1, blocks[1].statements.length
794
+ assert_equal ASTObjsetStmt, blocks[1].statements[0].class
795
+ assert_equal expected_classnames[index], blocks[1].statements[0].objset.class_name.text
796
+ end
797
+ end
798
+
799
+ def test_before_callbacks__halt_callback_chain_when_rendering_always
800
+ AsdsController.class_exec do
801
+ def before
802
+ render :text => 'blah'
803
+ end
804
+
805
+ def before2
806
+ Mod::Blah.new
807
+ end
808
+
809
+ def before_filter_action
810
+ Mod::Blah.new
811
+ end
812
+ end
813
+
814
+ extractor = create_rails_extractor
815
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :before_filter_action)
816
+ statements = ast.block.statements
817
+
818
+ assert_equal 0, statements.length
819
+ end
820
+
821
+ def test_before_callbacks__halt_callback_chain_when_rendering_sometimes
822
+ AsdsController.class_exec do
823
+ def before
824
+ if true
825
+ render :text => 'blah'
826
+ end
827
+ Asd.new
828
+ end
829
+
830
+ def before2
831
+ Kme.new
832
+ end
833
+
834
+ def before_filter_action
835
+ Mod::Blah.new
836
+ end
837
+ end
838
+
839
+ extractor = create_rails_extractor
840
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :before_filter_action)
841
+ statements = ast.block.statements
842
+
843
+ assert_equal 1, statements.length
844
+ assert_equal ASTEither, statements[0].class
845
+
846
+ blocks = statements[0].blocks
847
+ assert_equal 2, blocks.length
848
+
849
+ assert_equal 3, blocks[1].statements.length
850
+ types = ['Asd', 'Kme', 'Mod_Blah']
851
+ 3.times do |i|
852
+ assert_equal ASTObjsetStmt, blocks[1].statements[i].class
853
+ assert_equal types[i], blocks[1].statements[i].objset.class_name.text
854
+ end
855
+
856
+ assert_equal 1, blocks[0].statements.length
857
+ assert_equal 'Asd', blocks[0].statements[0].objset.class_name.text
858
+ end
859
+
860
+ def test_before_callbacks__affect_after
861
+ AsdsController.class_exec do
862
+ def before_nothing
863
+ if true
864
+ render
865
+ end
866
+ Asd.new
867
+ end
868
+
869
+ def nothing
870
+ Kme.new
871
+ end
872
+
873
+ def after_nothing
874
+ Mod::Blah.new
875
+ end
876
+ end
877
+
878
+ extractor = create_rails_extractor
879
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
880
+ statements = ast.block.statements
881
+
882
+ assert_equal 1, statements.length
883
+ assert_equal ASTEither, statements[0].class
884
+
885
+ blocks = statements[0].blocks
886
+ assert_equal 2, blocks.length
887
+
888
+ assert_equal 3, blocks[1].statements.length
889
+ types = ['Asd', 'Kme', 'Mod_Blah']
890
+ 3.times do |i|
891
+ assert_equal ASTObjsetStmt, blocks[1].statements[i].class
892
+ assert_equal types[i], blocks[1].statements[i].objset.class_name.text
893
+ end
894
+
895
+ assert_equal 1, blocks[0].statements.length
896
+ assert_equal 'Asd', blocks[0].statements[0].objset.class_name.text
897
+ end
898
+
899
+ def test_before_callbacks__render_in_action_does_not_halt_after
900
+ AsdsController.class_exec do
901
+ def before_nothing
902
+ if true
903
+ render
904
+ end
905
+ Asd.new
906
+ end
907
+
908
+ def nothing
909
+ Kme.new
910
+ instance_eval "render :text => 'blah'"
911
+ end
912
+
913
+ def after_nothing
914
+ Mod::Blah.new
915
+ end
916
+ end
917
+
918
+ extractor = create_rails_extractor
919
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
920
+ statements = ast.block.statements
921
+
922
+ assert_equal 1, statements.length
923
+ assert_equal ASTEither, statements[0].class
924
+
925
+ blocks = statements[0].blocks
926
+ assert_equal 2, blocks.length
927
+
928
+ assert_equal 3, blocks[1].statements.length
929
+ types = ['Asd', 'Kme', 'Mod_Blah']
930
+ 3.times do |i|
931
+ assert_equal ASTObjsetStmt, blocks[1].statements[i].class
932
+ assert_equal types[i], blocks[1].statements[i].objset.class_name.text
933
+ end
934
+
935
+ assert_equal 1, blocks[0].statements.length
936
+ assert_equal 'Asd', blocks[0].statements[0].objset.class_name.text
937
+ end
938
+
939
+ def test_extract_action__instrumentation_filters_work
940
+ AsdsController.class_exec do
941
+ def before_nothing
942
+ Asd.new
943
+ end
944
+
945
+ def nothing
946
+ Asd.new
947
+ end
948
+ end
949
+
950
+ extractor = create_rails_extractor <<-filters
951
+ blacklist :before_nothing
952
+ filters
953
+
954
+ assert_equal 1, extractor.instrumentation_filters.length
955
+
956
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
957
+ statements = ast.block.statements
958
+ assert_equal 1, statements.length
959
+ end
960
+
961
+ def test_extract_action__raise_ignores_the_root_path
962
+ AsdsController.class_exec do
963
+ def nothing
964
+ Kme.new
965
+ raise
966
+ end
967
+ end
968
+
969
+ extractor = create_rails_extractor
970
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
971
+ statements = ast.block.statements
972
+
973
+ assert_equal 0, statements.length
974
+ end
975
+
976
+ def test_extract_action__raise_ignores_the_root_path_in_branch
977
+ AsdsController.class_exec do
978
+ def nothing
979
+ if true
980
+ Asd.new
981
+ else
982
+ Kme.new
983
+ raise
984
+ end
985
+ end
986
+ end
987
+
988
+ extractor = create_rails_extractor
989
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
990
+ statements = ast.block.statements
991
+
992
+ assert_equal 1, statements.length
993
+ assert_equal ASTObjsetStmt, statements[0].class
994
+ assert_equal ASTCreateObjset, statements[0].objset.class
995
+ assert_equal 'Asd', statements[0].objset.class_name.text
996
+ end
997
+
998
+ def test_extract_action__exceptions_in_callbacks_stop_the_chain
999
+ AsdsController.class_exec do
1000
+ def before_nothing
1001
+ raise
1002
+ end
1003
+
1004
+ def nothing
1005
+ Asd.new
1006
+ end
1007
+ end
1008
+
1009
+ extractor = create_rails_extractor
1010
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1011
+ statements = ast.block.statements
1012
+
1013
+ assert_equal 0, statements.length
1014
+ end
1015
+
1016
+ def test_extract_action__foreach_basic
1017
+ AsdsController.class_exec do
1018
+ def nothing
1019
+ Kme.all.each do |asd|
1020
+ a = asd
1021
+ a.delete!
1022
+ end
1023
+ end
1024
+ end
1025
+
1026
+ extractor = create_rails_extractor
1027
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1028
+ statements = ast.block.statements
1029
+
1030
+ assert_equal 1, statements.length
1031
+
1032
+ foreach = statements.first
1033
+ assert_equal ASTForEach, foreach.class
1034
+ assert_equal 'asd', foreach.var_name.text
1035
+ assert_equal ASTAllOf, foreach.objset.class
1036
+ assert_equal 'Kme', foreach.objset.class_name.text
1037
+ assert_equal ASTBlock, foreach.block.class
1038
+
1039
+ block_stmts = foreach.block.statements
1040
+ assert_equal 2, block_stmts.length
1041
+ assert_equal ASTAssignment, block_stmts[0].class
1042
+ assert_equal ASTVariable, block_stmts[0].objset.class
1043
+ assert_equal 'asd', block_stmts[0].objset.var_name.text
1044
+ assert_equal 'a', block_stmts[0].var_name.text
1045
+ assert_equal ASTDeleteObj, block_stmts[1].class
1046
+ assert_equal 'a', block_stmts[1].objset.var_name.text
1047
+ end
1048
+
1049
+ def test_extract_action__association_setter_direct
1050
+ AsdsController.class_exec do
1051
+ def nothing
1052
+ Kme.new.blah = Mod::Blah.new
1053
+ end
1054
+ end
1055
+
1056
+ extractor = create_rails_extractor
1057
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1058
+ statements = ast.block.statements
1059
+
1060
+ assert_equal 1, statements.length
1061
+
1062
+ assert_equal ASTSetTup, statements[0].class
1063
+ assert_equal ASTCreateObjset, statements[0].objset1.class
1064
+ assert_equal 'Kme', statements[0].objset1.class_name.text
1065
+ assert_equal 'blah', statements[0].rel_name.text
1066
+ assert_equal ASTSetTup, statements[0].class
1067
+ assert_equal ASTCreateObjset, statements[0].objset2.class
1068
+ assert_equal 'Mod_Blah', statements[0].objset2.class_name.text
1069
+ end
1070
+
1071
+ def test_extract_action__association_setter_through
1072
+ AsdsController.class_exec do
1073
+ def nothing
1074
+ Asd.find.kmes = Kme.new
1075
+ end
1076
+ end
1077
+
1078
+ extractor = create_rails_extractor
1079
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1080
+ statements = ast.block.statements
1081
+
1082
+ assert_equal 4, statements.length
1083
+
1084
+ assert_equal ASTAssignment, statements[0].class
1085
+ origin_name = statements[0].var_name.text
1086
+ assert_equal ASTOneOf, statements[0].objset.class
1087
+ assert_equal ASTAllOf, statements[0].objset.objset.class
1088
+ assert_equal 'Asd', statements[0].objset.objset.class_name.text
1089
+
1090
+ assert_equal ASTAssignment, statements[1].class
1091
+ target_name = statements[1].var_name.text
1092
+ assert_equal ASTCreateObjset, statements[1].objset.class
1093
+ assert_equal 'Kme', statements[1].objset.class_name.text
1094
+
1095
+ assert_equal ASTDeleteObj, statements[2].class
1096
+ assert_equal ASTDereference, statements[2].objset.class
1097
+ assert_equal ASTVariable, statements[2].objset.objset.class
1098
+ assert_equal origin_name, statements[2].objset.objset.var_name.text
1099
+ assert_equal 'blahs', statements[2].objset.rel_name.text
1100
+
1101
+ assert_equal ASTForEach, statements[3].class
1102
+ iter_name = statements[3].var_name.text
1103
+ assert_equal ASTVariable, statements[3].objset.class
1104
+ assert_equal target_name, statements[3].objset.var_name.text
1105
+ block = statements[3].block
1106
+
1107
+ assert_equal 3, block.statements.length
1108
+
1109
+ assert_equal ASTAssignment, block.statements[0].class
1110
+ temp_name = block.statements[0].var_name.text
1111
+ assert_equal ASTCreateObjset, block.statements[0].objset.class
1112
+ assert_equal 'Mod_Blah', block.statements[0].objset.class_name.text
1113
+
1114
+ assert_equal ASTCreateTup, block.statements[1].class
1115
+ assert_equal ASTVariable, block.statements[1].objset1.class
1116
+ assert_equal origin_name, block.statements[1].objset1.var_name.text
1117
+ assert_equal 'blahs', block.statements[1].rel_name.text
1118
+ assert_equal ASTVariable, block.statements[1].objset2.class
1119
+ assert_equal temp_name, block.statements[1].objset2.var_name.text
1120
+
1121
+ assert_equal ASTCreateTup, block.statements[2].class
1122
+ assert_equal ASTVariable, block.statements[2].objset1.class
1123
+ assert_equal temp_name, block.statements[2].objset1.var_name.text
1124
+ assert_equal 'kme12', block.statements[2].rel_name.text
1125
+ assert_equal ASTVariable, block.statements[2].objset2.class
1126
+ assert_equal iter_name, block.statements[2].objset2.var_name.text
1127
+
1128
+ assert_equal 4, [origin_name, target_name, temp_name, iter_name].uniq.length
1129
+ assert origin_name.is_a? String
1130
+ assert target_name.is_a? String
1131
+ assert temp_name.is_a? String
1132
+ assert iter_name.is_a? String
1133
+ end
1134
+
1135
+ def test_extract_action__nested_foreachs
1136
+ AsdsController.class_exec do
1137
+ def nothing
1138
+ Asd.all.each do |asd|
1139
+ asd.blahs.each do |blah|
1140
+ blah.delete
1141
+ end
1142
+ end
1143
+ end
1144
+ end
1145
+
1146
+ extractor = create_rails_extractor
1147
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1148
+ statements = ast.block.statements
1149
+
1150
+ assert_equal 1, statements.length
1151
+
1152
+ assert_equal ASTForEach, statements.first.class
1153
+ assert_equal ASTAllOf, statements.first.objset.class
1154
+ assert_equal 'Asd', statements.first.objset.class_name.text
1155
+ assert_equal 'asd', statements.first.var_name.text
1156
+
1157
+ block_stmts = statements.first.block.statements
1158
+
1159
+ assert_equal 1, block_stmts.length
1160
+ assert_equal ASTForEach, block_stmts.first.class
1161
+ assert_equal ASTDereference, block_stmts.first.objset.class
1162
+ assert_equal ASTVariable, block_stmts.first.objset.objset.class
1163
+ assert_equal 'asd', block_stmts.first.objset.objset.var_name.text
1164
+ assert_equal 'blahs', block_stmts.first.objset.rel_name.text
1165
+ assert_equal 'blah', block_stmts.first.var_name.text
1166
+
1167
+ final_block_stmts = block_stmts.first.block.statements
1168
+
1169
+ assert_equal 1, final_block_stmts.length
1170
+ assert_equal ASTDeleteObj, final_block_stmts.first.class
1171
+ assert_equal ASTVariable, final_block_stmts.first.objset.class
1172
+ assert_equal 'blah', final_block_stmts.first.objset.var_name.text
1173
+ end
1174
+
1175
+ def test_extract_action__assignment_in_branch_condition
1176
+ AsdsController.class_exec do
1177
+ def nothing
1178
+ if asd = Asd.new
1179
+ asd.delete
1180
+ end
1181
+ asd.delete
1182
+ end
1183
+ end
1184
+
1185
+ extractor = create_rails_extractor
1186
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1187
+ statements = ast.block.statements
1188
+
1189
+ assert_equal 3, statements.length
1190
+
1191
+ assert_equal ASTAssignment, statements[0].class
1192
+ assert_equal 'asd', statements[0].var_name.text
1193
+ assert_equal ASTCreateObjset, statements[0].objset.class
1194
+ assert_equal 'Asd', statements[0].objset.class_name.text
1195
+
1196
+ assert_equal ASTEither, statements[1].class
1197
+ assert_equal 2, statements[1].blocks.length
1198
+ assert_equal 1, statements[1].blocks[0].statements.length
1199
+ assert_equal ASTDeleteObj, statements[1].blocks[0].statements[0].class
1200
+ assert_equal ASTVariable, statements[1].blocks[0].statements[0].objset.class
1201
+ assert_equal 'asd', statements[1].blocks[0].statements[0].objset.var_name.text
1202
+ assert_equal 0, statements[1].blocks[1].statements.length
1203
+
1204
+ assert_equal ASTDeleteObj, statements[2].class
1205
+ assert_equal ASTVariable, statements[2].objset.class
1206
+ assert_equal 'asd', statements[2].objset.var_name.text
1207
+ end
1208
+
1209
+ def test_extract_action__assignment_of_branch
1210
+ AsdsController.class_exec do
1211
+ def nothing
1212
+ a = if true; Asd.all; else; nil; end
1213
+ a.delete
1214
+ end
1215
+ end
1216
+
1217
+ extractor = create_rails_extractor
1218
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1219
+ statements = ast.block.statements
1220
+
1221
+ assert_equal 2, statements.length
1222
+
1223
+ assert_equal ASTAssignment, statements[0].class
1224
+ assert_equal 'a', statements[0].var_name.text
1225
+ assert_equal ASTOneOfObjset, statements[0].objset.class
1226
+ assert_equal ASTAllOf, statements[0].objset.objsets[0].class
1227
+ assert_equal ASTEmptyObjset, statements[0].objset.objsets[1].class
1228
+
1229
+ assert_equal ASTDeleteObj, statements[1].class
1230
+ assert_equal ASTVariable, statements[1].objset.class
1231
+ assert_equal 'a', statements[1].objset.var_name.text
1232
+ end
1233
+
1234
+ def test_extract_action__assignment_of_trinary
1235
+ AsdsController.class_exec do
1236
+ def nothing
1237
+ a = true ? Asd.all : nil
1238
+ a.delete
1239
+ end
1240
+ end
1241
+
1242
+ extractor = create_rails_extractor
1243
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1244
+ statements = ast.block.statements
1245
+
1246
+ assert_equal 2, statements.length
1247
+
1248
+ assert_equal ASTAssignment, statements[0].class
1249
+ assert_equal 'a', statements[0].var_name.text
1250
+ assert_equal ASTOneOfObjset, statements[0].objset.class
1251
+ assert_equal ASTAllOf, statements[0].objset.objsets[0].class
1252
+ assert_equal ASTEmptyObjset, statements[0].objset.objsets[1].class
1253
+
1254
+ assert_equal ASTDeleteObj, statements[1].class
1255
+ assert_equal ASTVariable, statements[1].objset.class
1256
+ assert_equal 'a', statements[1].objset.var_name.text
1257
+ end
1258
+
1259
+ def test_extract_action__rescue_stmt_modifier
1260
+ AsdsController.class_exec do
1261
+ def nothing
1262
+ a = Asd.all rescue nil
1263
+ a.delete
1264
+ end
1265
+ end
1266
+
1267
+ extractor = create_rails_extractor
1268
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1269
+ statements = ast.block.statements
1270
+
1271
+ assert_equal 2, statements.length
1272
+
1273
+ assert_equal ASTAssignment, statements[0].class
1274
+ assert_equal 'a', statements[0].var_name.text
1275
+ assert_equal ASTOneOfObjset, statements[0].objset.class
1276
+ assert_equal ASTEmptyObjset, statements[0].objset.objsets[0].class
1277
+ assert_equal ASTAllOf, statements[0].objset.objsets[1].class
1278
+
1279
+ assert_equal ASTDeleteObj, statements[1].class
1280
+ assert_equal ASTVariable, statements[1].objset.class
1281
+ assert_equal 'a', statements[1].objset.var_name.text
1282
+ end
1283
+
1284
+ def test_extract_action__action_may_call_action
1285
+ AsdsController.class_exec do
1286
+ def nothing
1287
+ Asd.new
1288
+ end
1289
+
1290
+ def create
1291
+ Kme.new
1292
+ nothing
1293
+ Mod::Blah.new
1294
+ end
1295
+ end
1296
+
1297
+ extractor = create_rails_extractor
1298
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1299
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :create)
1300
+ statements = ast.block.statements
1301
+
1302
+ assert_equal 3, statements.length
1303
+
1304
+ assert_equal ASTObjsetStmt, statements[0].class
1305
+ assert_equal ASTCreateObjset, statements[0].objset.class
1306
+ assert_equal 'Kme', statements[0].objset.class_name.text
1307
+ assert_equal ASTObjsetStmt, statements[1].class
1308
+ assert_equal ASTCreateObjset, statements[1].objset.class
1309
+ assert_equal 'Asd', statements[1].objset.class_name.text
1310
+ assert_equal ASTObjsetStmt, statements[2].class
1311
+ assert_equal ASTCreateObjset, statements[2].objset.class
1312
+ assert_equal 'Mod_Blah', statements[2].objset.class_name.text
1313
+ end
1314
+
1315
+ def test_extract_action__foreign_key_reads_and_writes_propagate_kinda
1316
+ AsdsController.class_exec do
1317
+ def nothing
1318
+ blah = Mod::Blah.find
1319
+ asd = Asd.find
1320
+
1321
+ blah.asd_id = asd.id
1322
+ end
1323
+ end
1324
+
1325
+ extractor = create_rails_extractor
1326
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1327
+ statements = ast.block.statements
1328
+
1329
+ assert_equal 3, statements.length
1330
+
1331
+ assert_equal ASTAssignment, statements[0].class
1332
+ assert_equal 'blah', statements[0].var_name.text
1333
+ assert_equal ASTOneOf, statements[0].objset.class
1334
+ assert_equal ASTAllOf, statements[0].objset.objset.class
1335
+ assert_equal 'Mod_Blah', statements[0].objset.objset.class_name.text
1336
+
1337
+ assert_equal ASTAssignment, statements[1].class
1338
+ assert_equal 'asd', statements[1].var_name.text
1339
+ assert_equal ASTOneOf, statements[1].objset.class
1340
+ assert_equal ASTAllOf, statements[1].objset.objset.class
1341
+ assert_equal 'Asd', statements[1].objset.objset.class_name.text
1342
+
1343
+ assert_equal ASTSetTup, statements[2].class
1344
+ assert_equal ASTVariable, statements[2].objset1.class
1345
+ assert_equal 'blah', statements[2].objset1.var_name.text
1346
+ assert_equal 'asd', statements[2].rel_name.text
1347
+ assert_equal ASTVariable, statements[2].objset2.class
1348
+ assert_equal 'asd', statements[2].objset2.var_name.text
1349
+ end
1350
+
1351
+ def test_extract_action__has_many_delete_removes_one
1352
+ AsdsController.class_exec do
1353
+ def nothing
1354
+ a = Asd.new
1355
+ a.blahs.delete(1)
1356
+ end
1357
+ end
1358
+
1359
+ extractor = create_rails_extractor
1360
+ ast = extractor.action_to_adsl_ast(extractor.route_for AsdsController, :nothing)
1361
+ statements = ast.block.statements
1362
+
1363
+ assert_equal 2, statements.length
1364
+
1365
+ assert_equal ASTAssignment, statements[0].class
1366
+ assert_equal 'a', statements[0].var_name.text
1367
+ assert_equal ASTCreateObjset, statements[0].objset.class
1368
+ assert_equal 'Asd', statements[0].objset.class_name.text
1369
+
1370
+ assert_equal ASTDeleteTup, statements[1].class
1371
+ assert_equal ASTVariable, statements[1].objset1.class
1372
+ assert_equal 'a', statements[1].objset1.var_name.text
1373
+ assert_equal 'blahs', statements[1].rel_name.text
1374
+ assert_equal ASTOneOf, statements[1].objset2.class
1375
+ assert_equal ASTDereference, statements[1].objset2.objset.class
1376
+ assert_equal ASTVariable, statements[1].objset2.objset.objset.class
1377
+ assert_equal 'a', statements[1].objset2.objset.objset.var_name.text
1378
+ assert_equal 'blahs', statements[1].objset2.objset.rel_name.text
1379
+ end
1380
+ end