metasploit_data_models 0.17.3.pre.metasploit.pre.concern-java → 0.18.0-java

Sign up to get free protection for your applications and to get access to all the features.
Files changed (36) hide show
  1. checksums.yaml +4 -4
  2. data/CONTRIBUTING.md +164 -0
  3. data/README.md +6 -2
  4. data/app/models/mdm/host.rb +18 -0
  5. data/app/models/mdm/service.rb +12 -1
  6. data/app/models/metasploit_data_models/search/operation/port/number.rb +25 -0
  7. data/app/models/metasploit_data_models/search/operation/port/range.rb +79 -0
  8. data/app/models/metasploit_data_models/search/operation/range.rb +56 -0
  9. data/app/models/metasploit_data_models/search/operator/multitext.rb +73 -0
  10. data/app/models/metasploit_data_models/search/operator/port/list.rb +67 -0
  11. data/app/models/metasploit_data_models/search/visitor/attribute.rb +2 -1
  12. data/app/models/metasploit_data_models/search/visitor/includes.rb +3 -2
  13. data/app/models/metasploit_data_models/search/visitor/joins.rb +5 -3
  14. data/app/models/metasploit_data_models/search/visitor/method.rb +3 -2
  15. data/app/models/metasploit_data_models/search/visitor/where.rb +8 -2
  16. data/config/locales/en.yml +17 -1
  17. data/lib/metasploit_data_models.rb +1 -9
  18. data/lib/metasploit_data_models/version.rb +27 -6
  19. data/metasploit_data_models.gemspec +2 -2
  20. data/spec/app/models/metasploit_data_models/search/operation/port/number_spec.rb +41 -0
  21. data/spec/app/models/metasploit_data_models/search/operation/port/range_spec.rb +140 -0
  22. data/spec/app/models/metasploit_data_models/search/operation/range_spec.rb +235 -0
  23. data/spec/app/models/metasploit_data_models/search/operator/multitext_spec.rb +162 -0
  24. data/spec/app/models/metasploit_data_models/search/operator/port/list_spec.rb +164 -0
  25. data/spec/app/models/metasploit_data_models/search/visitor/attribute_spec.rb +48 -26
  26. data/spec/app/models/metasploit_data_models/search/visitor/includes_spec.rb +10 -7
  27. data/spec/app/models/metasploit_data_models/search/visitor/joins_spec.rb +44 -30
  28. data/spec/app/models/metasploit_data_models/search/visitor/method_spec.rb +16 -0
  29. data/spec/app/models/metasploit_data_models/search/visitor/relation_spec.rb +273 -65
  30. data/spec/app/models/metasploit_data_models/search/visitor/where_spec.rb +42 -2
  31. data/spec/factories/mdm/services.rb +1 -2
  32. data/spec/lib/metasploit_data_models/version_spec.rb +141 -0
  33. data/spec/support/shared/examples/metasploit_data_models/search/visitor/where/visit/with_metasploit_model_search_group_base.rb +1 -1
  34. metadata +28 -12
  35. data/lib/metasploit_data_models/models.rb +0 -21
  36. data/lib/metasploit_data_models/validators.rb +0 -19
@@ -12,6 +12,40 @@ describe MetasploitDataModels::Search::Visitor::Attribute do
12
12
  visitor.visit(node)
13
13
  end
14
14
 
15
+ #
16
+ # Shared examples
17
+ #
18
+
19
+ shared_examples_for 'operator.klass.arel_table[operator.attribute]' do |options = {}|
20
+ options.assert_valid_keys(:node_class)
21
+
22
+ node_class = options.fetch(:node_class)
23
+
24
+ context "with #{node_class}" do
25
+ it { should be_a Arel::Attributes::Attribute }
26
+
27
+ context '#name' do
28
+ subject(:name) do
29
+ visit.name
30
+ end
31
+
32
+ it "should be #{node_class}#attribute" do
33
+ name.should == node.attribute
34
+ end
35
+ end
36
+
37
+ context '#relation' do
38
+ subject(:relation) do
39
+ visit.relation
40
+ end
41
+
42
+ it "should be Class#arel_table for #{node_class}#klass" do
43
+ relation.should == node.klass.arel_table
44
+ end
45
+ end
46
+ end
47
+ end
48
+
15
49
  context 'with Metasploit::Model::Search::Operator::Association' do
16
50
  let(:attribute_operator) do
17
51
  double('Attribute Operator')
@@ -40,37 +74,25 @@ describe MetasploitDataModels::Search::Visitor::Attribute do
40
74
  end
41
75
  end
42
76
 
43
- context 'with Metasploit::Model::Search::Operator::Attribute' do
44
- let(:node) do
77
+ it_should_behave_like 'operator.klass.arel_table[operator.attribute]',
78
+ node_class: Metasploit::Model::Search::Operator::Attribute do
79
+ let(:node) {
45
80
  Metasploit::Model::Search::Operator::Attribute.new(
46
81
  # needs to be a real column so look up on AREL table works
47
- :attribute => :name,
82
+ attribute: :name,
48
83
  # needs to be a real class so Class#arel_table works
49
- :klass => Mdm::Host
84
+ klass: Mdm::Host
50
85
  )
51
- end
52
-
53
- it { should be_a Arel::Attributes::Attribute }
54
-
55
- context 'name' do
56
- subject(:name) do
57
- visit.name
58
- end
59
-
60
- it 'should be Metasploit::Model::Search::Operator::Attribute#attribute' do
61
- name.should == node.attribute
62
- end
63
- end
64
-
65
- context 'relation' do
66
- subject(:relation) do
67
- visit.relation
68
- end
86
+ }
87
+ end
69
88
 
70
- it 'should be Class#arel_table for Metasploit::Model::Search::Operator::Attribute#klass' do
71
- relation.should == node.klass.arel_table
72
- end
73
- end
89
+ it_should_behave_like 'operator.klass.arel_table[operator.attribute]',
90
+ node_class: MetasploitDataModels::Search::Operator::Port::List do
91
+ let(:node) {
92
+ Metasploit::Model::Search::Operator::Attribute.new(
93
+ klass: Mdm::Service
94
+ )
95
+ }
74
96
  end
75
97
  end
76
98
  end
@@ -15,7 +15,8 @@ describe MetasploitDataModels::Search::Visitor::Includes do
15
15
  children_classes = [
16
16
  Metasploit::Model::Search::Group::Intersection,
17
17
  Metasploit::Model::Search::Group::Union,
18
- Metasploit::Model::Search::Operation::Union
18
+ Metasploit::Model::Search::Operation::Group::Intersection,
19
+ Metasploit::Model::Search::Operation::Group::Union
19
20
  ]
20
21
 
21
22
  children_classes.each do |children_class|
@@ -48,12 +49,6 @@ describe MetasploitDataModels::Search::Visitor::Includes do
48
49
  end
49
50
  end
50
51
 
51
- context 'with Metasploit::Model::Search::Operation::Union' do
52
- let(:node) do
53
-
54
- end
55
- end
56
-
57
52
  context 'with Metasploit::Model::Search::Operator::Association' do
58
53
  let(:association) do
59
54
  FactoryGirl.generate :metasploit_model_search_operator_association_association
@@ -78,6 +73,14 @@ describe MetasploitDataModels::Search::Visitor::Includes do
78
73
  it { should == [] }
79
74
  end
80
75
 
76
+ context 'with MetasploitDataModels::Search::Operator::Port::List' do
77
+ let(:node) do
78
+ MetasploitDataModels::Search::Operator::Port::List.new
79
+ end
80
+
81
+ it { should == [] }
82
+ end
83
+
81
84
  context 'with Metasploit::Model::Search::Query#tree' do
82
85
  let(:node) do
83
86
  query.tree
@@ -12,48 +12,55 @@ describe MetasploitDataModels::Search::Visitor::Joins do
12
12
  visitor.visit(node)
13
13
  end
14
14
 
15
- context 'with Metasploit::Model::Search::Group::Intersection' do
16
- let(:children) do
17
- 2.times.collect { |n|
18
- double("Child #{n}")
19
- }
20
- end
15
+ intersection_classes = [
16
+ Metasploit::Model::Search::Group::Intersection,
17
+ Metasploit::Model::Search::Operation::Group::Intersection
18
+ ]
21
19
 
22
- let(:node) do
23
- Metasploit::Model::Search::Group::Intersection.new(
24
- :children => children
25
- )
26
- end
20
+ intersection_classes.each do |intersection_class|
21
+ context "with #{intersection_class}" do
22
+ let(:children) do
23
+ 2.times.collect { |n|
24
+ double("Child #{n}")
25
+ }
26
+ end
27
+
28
+ let(:node) do
29
+ intersection_class.new(
30
+ :children => children
31
+ )
32
+ end
27
33
 
28
- it 'should visit each child' do
29
- # needed for call to visit subject
30
- visitor.should_receive(:visit).with(node).and_call_original
34
+ it 'should visit each child' do
35
+ # needed for call to visit subject
36
+ visitor.should_receive(:visit).with(node).and_call_original
31
37
 
32
- children.each do |child|
33
- visitor.should_receive(:visit).with(child).and_return([])
38
+ children.each do |child|
39
+ visitor.should_receive(:visit).with(child).and_return([])
40
+ end
41
+
42
+ visit
34
43
  end
35
44
 
36
- visit
37
- end
45
+ it 'should return Array of all child visits' do
46
+ child_visits = []
38
47
 
39
- it 'should return Array of all child visits' do
40
- child_visits = []
48
+ visitor.should_receive(:visit).with(node).and_call_original
41
49
 
42
- visitor.should_receive(:visit).with(node).and_call_original
50
+ children.each_with_index do |child, i|
51
+ child_visit = ["Visited Child #{i}"]
52
+ visitor.stub(:visit).with(child).and_return(child_visit)
53
+ child_visits.concat(child_visit)
54
+ end
43
55
 
44
- children.each_with_index do |child, i|
45
- child_visit = ["Visited Child #{i}"]
46
- visitor.stub(:visit).with(child).and_return(child_visit)
47
- child_visits.concat(child_visit)
56
+ visit.should == child_visits
48
57
  end
49
-
50
- visit.should == child_visits
51
58
  end
52
59
  end
53
60
 
54
61
  union_classes = [
55
62
  Metasploit::Model::Search::Group::Union,
56
- Metasploit::Model::Search::Operation::Union
63
+ Metasploit::Model::Search::Operation::Group::Union
57
64
  ]
58
65
 
59
66
  union_classes.each do |union_class|
@@ -237,7 +244,7 @@ describe MetasploitDataModels::Search::Visitor::Joins do
237
244
  end
238
245
  end
239
246
 
240
- context "with Metasploit::Model::Search::Operator::Attribute" do
247
+ context 'with Metasploit::Model::Search::Operator::Attribute' do
241
248
  let(:node) do
242
249
  Metasploit::Model::Search::Operator::Attribute.new
243
250
  end
@@ -245,6 +252,14 @@ describe MetasploitDataModels::Search::Visitor::Joins do
245
252
  it { should == [] }
246
253
  end
247
254
 
255
+ context 'with MetasploitDataModels::Search::Operator::Port::List' do
256
+ let(:node) do
257
+ MetasploitDataModels::Search::Operator::Port::List.new
258
+ end
259
+
260
+ it { should == [] }
261
+ end
262
+
248
263
  context 'with Metasploit::Model::Search::Query#tree' do
249
264
  let(:node) do
250
265
  query.tree
@@ -263,7 +278,6 @@ describe MetasploitDataModels::Search::Visitor::Joins do
263
278
  Mdm::Host
264
279
  }
265
280
 
266
-
267
281
  context 'with name' do
268
282
  let(:name) do
269
283
  FactoryGirl.generate :mdm_host_name
@@ -24,6 +24,14 @@ describe MetasploitDataModels::Search::Visitor::Method do
24
24
  it { should == :and }
25
25
  end
26
26
 
27
+ context 'with Metasploit::Model::Search::Operation::Group::Intersection' do
28
+ let(:node_class) do
29
+ Metasploit::Model::Search::Operation::Group::Intersection
30
+ end
31
+
32
+ it { should == :and }
33
+ end
34
+
27
35
  context 'with Metasploit::Model::Search::Group::Union' do
28
36
  let(:node_class) do
29
37
  Metasploit::Model::Search::Group::Union
@@ -31,5 +39,13 @@ describe MetasploitDataModels::Search::Visitor::Method do
31
39
 
32
40
  it { should == :or }
33
41
  end
42
+
43
+ context 'with Metasploit::Model::Search::Operation::Group::Union' do
44
+ let(:node_class) do
45
+ Metasploit::Model::Search::Operation::Group::Union
46
+ end
47
+
48
+ it { should == :or }
49
+ end
34
50
  end
35
51
  end
@@ -12,10 +12,14 @@ describe MetasploitDataModels::Search::Visitor::Relation do
12
12
  "name:\"#{value}\""
13
13
  end
14
14
 
15
+ let(:klass) {
16
+ Mdm::Host
17
+ }
18
+
15
19
  let(:query) do
16
20
  Metasploit::Model::Search::Query.new(
17
21
  :formatted => formatted,
18
- :klass => Mdm::Host
22
+ :klass => klass
19
23
  )
20
24
  end
21
25
 
@@ -152,81 +156,285 @@ describe MetasploitDataModels::Search::Visitor::Relation do
152
156
  end
153
157
 
154
158
  context 'matching record' do
155
- context 'with Mdm::Host' do
156
- #
157
- # lets
158
- #
159
- # Don't use factories to prevent prefix aliasing when sequences go from 1 to 10 or 10 to 100
160
- #
161
-
162
- let(:matching_record_name) {
163
- 'mdm_host_name_a'
164
- }
165
-
166
- let(:matching_service_name) {
167
- 'mdm_service_name_a'
168
- }
169
-
170
- let(:non_matching_record_name) {
171
- 'mdm_host_name_b'
172
- }
173
-
174
- let(:non_matching_service_name) {
175
- 'mdm_service_name_b'
176
- }
177
-
178
- #
179
- # let!s
180
- #
181
-
182
- let!(:matching_record) do
183
- FactoryGirl.build(
184
- :mdm_host,
185
- name: matching_record_name
186
- )
187
- end
159
+ context 'Metasploit::Model::Search::Query#klass' do
160
+ context 'with Mdm::Service' do
161
+ let(:klass) {
162
+ Mdm::Service
163
+ }
188
164
 
189
- let!(:matching_service) do
190
- FactoryGirl.create(
191
- :mdm_service,
192
- host: matching_record,
193
- name: matching_service_name
194
- )
195
- end
165
+ let(:matching_ports) {
166
+ [
167
+ 1,
168
+ 2
169
+ ]
170
+ }
196
171
 
197
- let!(:non_matching_record) do
198
- FactoryGirl.build(
199
- :mdm_host,
200
- name: non_matching_record_name
201
- )
202
- end
172
+ let(:matching_records) {
173
+ matching_record_by_port.values
174
+ }
175
+
176
+ let(:non_matching_port) {
177
+ 3
178
+ }
179
+
180
+ #
181
+ # let!s
182
+ #
183
+
184
+ let!(:matching_record_by_port) {
185
+ matching_ports.each_with_object({}) { |matching_port, matching_record_by_port|
186
+ matching_record_by_port[matching_port] = FactoryGirl.create(
187
+ :mdm_service,
188
+ port: matching_port
189
+ )
190
+ }
191
+ }
192
+
193
+ let!(:non_matching_record) {
194
+ FactoryGirl.create(
195
+ :mdm_service,
196
+ port: non_matching_port
197
+ )
198
+ }
199
+
200
+ context 'with port' do
201
+ context 'with single port number' do
202
+ let(:formatted) {
203
+ "port:#{matching_port}"
204
+ }
205
+
206
+ let(:matching_port) {
207
+ matching_ports.sample
208
+ }
209
+
210
+ let(:matching_record) {
211
+ matching_record_by_port[matching_port]
212
+ }
213
+
214
+ it 'should find only record with that port number' do
215
+ expect(visit).to match_array([matching_record])
216
+ end
217
+ end
218
+
219
+ context 'with port range' do
220
+ let(:formatted) {
221
+ "port:#{matching_ports.min}-#{matching_ports.max}"
222
+ }
223
+
224
+ it 'should find all records with port numbers within the range' do
225
+ expect(visit).to match_array(matching_records)
226
+ end
227
+ end
228
+
229
+ context 'with comma separated port numbers' do
230
+ let(:formatted) {
231
+ "port:#{matching_ports.join(',')}"
232
+ }
233
+
234
+ it 'should find all records with the port numbers' do
235
+ expect(visit).to match_array(matching_records)
236
+ end
237
+ end
238
+
239
+ context 'with overlapping comma separated port number and range' do
240
+ let(:matching_port) {
241
+ matching_ports.sample
242
+ }
243
+
244
+ let(:formatted) {
245
+ %Q{port:#{matching_port},#{matching_ports.min}-#{matching_ports.max}}
246
+ }
203
247
 
204
- let!(:non_matching_service) do
205
- FactoryGirl.create(
206
- :mdm_service,
207
- host: non_matching_record,
208
- name: non_matching_service_name
209
- )
248
+ it 'should find all records with the matching ports once' do
249
+ expect(visit).to match_array(matching_records)
250
+ end
251
+ end
252
+ end
253
+
254
+ context 'with all operators' do
255
+ let(:formatted) {
256
+ %Q{port:#{matching_port}}
257
+ }
258
+ end
210
259
  end
211
260
 
212
- it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
213
- :attribute => :name
261
+ context 'with Mdm::Host' do
262
+ #
263
+ # lets
264
+ #
214
265
 
215
- it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
216
- association: :services,
217
- attribute: :name
266
+ let(:klass) {
267
+ Mdm::Host
268
+ }
218
269
 
219
- context 'with all operators' do
220
- let(:formatted) {
221
- %Q{name:"#{matching_record_name}" services.name:"#{matching_service_name}"}
270
+ #
271
+ # Don't use factories to prevent prefix aliasing when sequences go from 1 to 10 or 10 to 100
272
+ #
273
+
274
+ let(:matching_record_os_flavor) {
275
+ 'mdm_host_os_flavor_a'
222
276
  }
223
277
 
224
- it 'should find only matching record' do
225
- if visit.to_a != [matching_record]
226
- true
278
+ let(:matching_record_os_name) {
279
+ 'mdm_host_os_name_a'
280
+ }
281
+
282
+ let(:matching_record_os_sp) {
283
+ 'mdm_host_os_sp_a'
284
+ }
285
+
286
+ let(:matching_service_name) {
287
+ 'mdm_service_name_a'
288
+ }
289
+
290
+ let(:matching_record_name) {
291
+ 'mdm_host_name_a'
292
+ }
293
+
294
+ let(:matching_service_name) {
295
+ 'mdm_service_name_a'
296
+ }
297
+
298
+ let(:non_matching_record_os_flavor) {
299
+ 'mdm_host_os_flavor_b'
300
+ }
301
+
302
+ let(:non_matching_record_os_name) {
303
+ 'mdm_host_os_name_b'
304
+ }
305
+
306
+ let(:non_matching_record_os_sp) {
307
+ 'mdm_host_os_sp_b'
308
+ }
309
+
310
+ let(:non_matching_service_name) {
311
+ 'mdm_service_name_b'
312
+ }
313
+
314
+ let(:non_matching_record_name) {
315
+ 'mdm_host_name_b'
316
+ }
317
+
318
+ let(:non_matching_service_name) {
319
+ 'mdm_service_name_b'
320
+ }
321
+
322
+ #
323
+ # let!s
324
+ #
325
+
326
+ let!(:matching_record) do
327
+ FactoryGirl.build(
328
+ :mdm_host,
329
+ name: matching_record_name,
330
+ os_flavor: matching_record_os_flavor,
331
+ os_name: matching_record_os_name,
332
+ os_sp: matching_record_os_sp
333
+ )
334
+ end
335
+
336
+ let!(:matching_service) do
337
+ FactoryGirl.create(
338
+ :mdm_service,
339
+ host: matching_record,
340
+ name: matching_service_name
341
+ )
342
+ end
343
+
344
+ let!(:non_matching_record) do
345
+ FactoryGirl.build(
346
+ :mdm_host,
347
+ name: non_matching_record_name,
348
+ os_flavor: non_matching_record_os_flavor,
349
+ os_name: non_matching_record_os_name,
350
+ os_sp: non_matching_record_os_sp
351
+ )
352
+ end
353
+
354
+ let!(:non_matching_service) do
355
+ FactoryGirl.create(
356
+ :mdm_service,
357
+ host: non_matching_record,
358
+ name: non_matching_service_name
359
+ )
360
+ end
361
+
362
+ it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
363
+ :attribute => :name
364
+
365
+ context 'with os' do
366
+ let(:matching_record_os_flavor) {
367
+ 'XP'
368
+ }
369
+
370
+ let(:matching_record_os_name) {
371
+ 'Microsoft Windows'
372
+ }
373
+
374
+ let(:matching_record_os_sp) {
375
+ 'SP1'
376
+ }
377
+
378
+ context 'with a combination of Mdm::Host#os_name and Mdm:Host#os_sp' do
379
+ let(:formatted) {
380
+ %Q{os:"win xp"}
381
+ }
382
+
383
+ it 'finds matching record' do
384
+ expect(visit).to match_array [matching_record]
385
+ end
227
386
  end
228
387
 
229
- expect(visit).to match_array([matching_record])
388
+ context 'with a combination of Mdm::Host#os_flavor and Mdm::Host#os_sp' do
389
+ let(:formatted) {
390
+ %Q{os:"xp sp1"}
391
+ }
392
+
393
+ it 'finds matching record' do
394
+ expect(visit).to match_array [matching_record]
395
+ end
396
+ end
397
+
398
+ context 'with multiple records matching one word' do
399
+ let(:formatted) {
400
+ %Q{os:"win xp"}
401
+ }
402
+
403
+ let(:non_matching_record_os_name) {
404
+ 'Microsoft Windows'
405
+ }
406
+
407
+ it 'finds only matching record by other words refining search' do
408
+ expect(visit).to match_array [matching_record]
409
+ end
410
+ end
411
+ end
412
+
413
+ it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
414
+ :attribute => :os_flavor
415
+
416
+ it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
417
+ :attribute => :os_name
418
+
419
+ it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
420
+ :attribute => :os_sp
421
+
422
+ it_should_behave_like 'MetasploitDataModels::Search::Visitor::Relation#visit matching record',
423
+ association: :services,
424
+ attribute: :name
425
+
426
+ context 'with all operators' do
427
+ let(:formatted) {
428
+ %Q{name:"#{matching_record_name}" os:"#{matching_record_os_name} #{matching_record_os_flavor} #{matching_record_os_sp}" os_flavor:"#{matching_record_os_flavor}" os_name:"#{matching_record_os_name}" os_sp:"#{matching_record_os_sp}" services.name:"#{matching_service_name}"}
429
+ }
430
+
431
+ it 'should find only matching record' do
432
+ if visit.to_a != [matching_record]
433
+ true
434
+ end
435
+
436
+ expect(visit).to match_array([matching_record])
437
+ end
230
438
  end
231
439
  end
232
440
  end