metasploit-runner 0.1.9 → 0.2.1

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 250b963d7aab6e8e6ef915674a0de8edca5c50bf
4
- data.tar.gz: e54e5098ef8f5f70fff4d7e540ca99e50c087809
3
+ metadata.gz: 73317964938841513e2416cfcc75a4ca3298d314
4
+ data.tar.gz: 735c44a012cf169362a164f20174eec6f89aa9c4
5
5
  SHA512:
6
- metadata.gz: eb5fca636b93affc501761b1aaf9c33bad357dc8fce3a32533eaf71af7c67d01345372948c00634ba663b8e4a82fceaa2077ce43f7fc4a2b32be4657c5257f5e
7
- data.tar.gz: 58cbe28bc29feda56e45b39de9e82008fbe1f23e7f05e0e5a5c0a45a8f4f844816687daa2d87249cbb0665e10042c16111d84ef6b63a47a31dbc86802e13326b
6
+ metadata.gz: 271fe1d83224bca7e1ed3a4e49e12c0940eaf402309c968d90c16789ea35f457f22f00e390bc3237703073a837193293c0788852ce2365b8f64920b248b70d91
7
+ data.tar.gz: d84c7f0fb8defdab950e6e550c89013ed84319f5919e0ba09489367cc4ec3ddcc77b8b0983a9f9af4dd0f662772424ec8a9ae4bcec0d793dec2e5df539ee5eae
data/README.md CHANGED
@@ -29,15 +29,15 @@ This gem allows you to specify the Metasploit Connection URL, Metasploit Connect
29
29
  The nexpose_console_name is optional, if you specify a nexpose console name it will use the workspace_name, and nexpose console name to pull scan data from a nexpose console.
30
30
  IMPORTANT: Your "Site Name" in Nexpose, must match your "Workspace" name in Metasploit and you must add your Nexpose Console to Metasploit for this to work properly.
31
31
 
32
- $ exploit "connection_url" "port" "uri" "use_ssl" "token" "workspace_name" "nexpose_console_name" "device_ip_to_scan" "os_filter" "module_filter"
32
+ $ exploit "connection_url" "port" "uri" "use_ssl" "token" "workspace_name" "nexpose_console_name" "device_ip_to_scan" "os_filter" "module_filter" "report_type"
33
33
 
34
34
  Example WITH Nexpose Console Integration:
35
35
 
36
- $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "<true/false>" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "<true/false>" "exploit/windows/smb/psexec"
36
+ $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "<true/false>" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "<true/false>" "exploit/windows/smb/psexec" "fisma"
37
37
 
38
38
  Example WITHOUT Nexpose Console Integration:
39
39
 
40
- $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "true" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "" "10.0.0.1" "false" "exploit/windows/smb/psexec"
40
+ $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "true" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "" "10.0.0.1" "false" "exploit/windows/smb/psexec" "fisma"
41
41
 
42
42
  Additionally, an os filter may be passed in to determine which modules will be ran during an exploit. The os filter parameter will default to false (all modules will run) if you do not pass a value.
43
43
 
@@ -45,7 +45,7 @@ Additionally, an os filter may be passed in to determine which modules will be r
45
45
 
46
46
  Example WITH OS Filter:
47
47
 
48
- $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "true" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "true"
48
+ $ exploit "sploit.mydomain.com" "3790" "/api/1.0" "true" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "true" "" "fisma"
49
49
 
50
50
  The if you do not pass the following options they will default to the respective values:
51
51
 
@@ -56,7 +56,7 @@ The if you do not pass the following options they will default to the respective
56
56
 
57
57
  Example using the defaults:
58
58
 
59
- $ exploit "sploit.mydomain.com" "" "" "" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "" ""
59
+ $ exploit "sploit.mydomain.com" "" "" "" "asdlkjhsdfuw1228340asdasf8" "mycoolsoftware-build-28" "nexpose-console-1" "10.0.0.1" "" "" ""
60
60
 
61
61
  ## Contributing
62
62
 
data/bin/exploit CHANGED
@@ -3,4 +3,16 @@
3
3
  require 'metasploit/exploit'
4
4
 
5
5
  $stdout.sync = true
6
- Metasploit::Exploit.start ARGV[0], ARGV[1], ARGV[2], ARGV[3], ARGV[4], ARGV[5], ARGV[6], ARGV[7], ARGV[8], ARGV[9]
6
+ Metasploit::Exploit.start({
7
+ 'connection_url' => ARGV[0],
8
+ 'port' => ARGV[1],
9
+ 'uri' => ARGV[2],
10
+ 'use_ssl' => ARGV[3],
11
+ 'token' => ARGV[4],
12
+ 'workspace_name' => ARGV[5],
13
+ 'nexpose_console_name' => ARGV[6],
14
+ 'device_ip_to_scan' => ARGV[7],
15
+ 'use_os_filter' => ARGV[8],
16
+ 'module_filter' => ARGV[9],
17
+ 'report_type' => ARGV[10]
18
+ })
@@ -1,3 +1,3 @@
1
1
  module MetasploitPenTestScript
2
- VERSION = "0.1.9"
2
+ VERSION = "0.2.1"
3
3
  end
@@ -16,10 +16,12 @@ module CONSTANTS
16
16
  SCANNING_MESSAGE = '[*] Scanning all your things with WebScan...'
17
17
  AUDIT_MESSAGE = '[*] Performing web audit...'
18
18
  EXPLOIT_MESSAGE = '[*] Exploiting all your things...'
19
+ REPORT_MESSAGE = '[*} Generating report...'
19
20
  REQUIRED_WORKSPACE_MESSAGE = 'PWNED! Workspace Name is required'
20
21
  SKIPPING_IMPORT_MESSAGE = '[*] Nexpose Console option was not passed, skipping Nexpose Import'
21
22
  USING_OS_FILTER_MESSAGE = '[*] The OS Filter is set to TRUE so we are limiting the modules to just the ones applicable to this Operating System'
22
23
  NO_OS_FILTER = '[*] We did not receive an option for the OS Filter or you set it to FALSE, either way we are backing the truck up and using all modules'
23
24
  USING_MODULE_FILTER = '[*] Filtering exploits based on your desired modules'
24
25
  NO_MODULE_FILTER = '[*] Not filtering any modules'
26
+ NO_REPORT_TYPE_MESSAGE = 'No report type specified - skipping report generation'
25
27
  end
@@ -4,17 +4,9 @@ require 'metasploit/exploit_run_description'
4
4
 
5
5
  module Metasploit
6
6
  module Exploit
7
- def Exploit.start(connection_url,
8
- port,
9
- uri,
10
- use_ssl,
11
- token,
12
- workspace_name,
13
- nexpose_console_name,
14
- device_ip_to_scan,
15
- use_os_filter,
16
- module_filter)
17
- run_details = ExploitRunDescription.new connection_url, port, uri, use_ssl, token, workspace_name, nexpose_console_name, device_ip_to_scan, use_os_filter, module_filter
7
+ def Exploit.start(options)
8
+
9
+ run_details = ExploitRunDescription.new(options)
18
10
  run_details.verify
19
11
 
20
12
  rpc_client = get_new_metasploit_rpc_connection(run_details)
@@ -28,6 +20,8 @@ module Metasploit
28
20
  do_metasploit_audit(rpc_client, run_details)
29
21
 
30
22
  do_metasploit_exploit(rpc_client, run_details)
23
+
24
+ do_metasploit_report(rpc_client, run_details)
31
25
  end
32
26
 
33
27
  private
@@ -83,6 +77,18 @@ module Metasploit
83
77
  wait_for_task_to_stop_running(rpc_client, CONSTANTS::EXPLOIT_MESSAGE, sploit['task_id'])
84
78
  end
85
79
 
80
+ def self.do_metasploit_report(rpc_client, run_details)
81
+ if run_details.report_type.length > 0
82
+ puts "Generating a #{run_details.report_type} Report"
83
+
84
+ report = rpc_client.call('pro.start_report', run_details.get_report_options)
85
+
86
+ self.write_report_after_generation(rpc_client, run_details, report['report_id'])
87
+ else
88
+ puts CONSTANTS::NO_REPORT_TYPE_MESSAGE
89
+ end
90
+ end
91
+
86
92
  def self.wait_for_task_to_stop_running(rpc_client, status_message, task_id)
87
93
  loop do
88
94
  sleep(3)
@@ -97,5 +103,23 @@ module Metasploit
97
103
  break if status != CONSTANTS::RUNNING_IMPORT_STATUS
98
104
  end
99
105
  end
106
+
107
+ def self.write_report_after_generation(rpc_client, run_details, report_id)
108
+ (1..100).each do
109
+ download = rpc_client.call('pro.report_download', report_id)
110
+ if download && download['report_artifacts'] && download['report_artifacts'].length > 0
111
+ download['report_artifacts'].each_with_index do |artifact, index|
112
+ File.open("#{run_details.workspace_name}_#{index}#{File.extname(artifact['file_path'])}", "wb") do |fd|
113
+ fd.write(artifact['data'])
114
+ end
115
+ puts "Report File #{index} Written"
116
+ end
117
+ break
118
+ else
119
+ puts "Waiting for report to generate"
120
+ sleep(3)
121
+ end
122
+ end
123
+ end
100
124
  end
101
125
  end
@@ -8,7 +8,8 @@ class ExploitRunDescription
8
8
  :nexpose_console_name,
9
9
  :device_ip_to_scan,
10
10
  :use_os_filter,
11
- :module_filter
11
+ :module_filter,
12
+ :report_type
12
13
 
13
14
  @@port_value = ''
14
15
  @@uri_value = ''
@@ -16,26 +17,18 @@ class ExploitRunDescription
16
17
  @@device_ip_to_scan_value = ''
17
18
  @@use_os_filter_value = ''
18
19
 
19
- def initialize(connection_url,
20
- port,
21
- uri,
22
- use_ssl,
23
- token,
24
- workspace_name,
25
- nexpose_console_name,
26
- device_ip_to_scan,
27
- use_os_filter,
28
- module_filter)
29
- self.connection_url = connection_url
30
- @@port_value = port
31
- @@uri_value = uri
32
- @@use_ssl_value = use_ssl
33
- self.token = token
34
- self.workspace_name = workspace_name
35
- self.nexpose_console_name = nexpose_console_name
36
- @@device_ip_to_scan_value = device_ip_to_scan
37
- self.use_os_filter = use_os_filter
38
- self.module_filter = module_filter
20
+ def initialize(options)
21
+ self.connection_url = options['connection_url']
22
+ @@port_value = options['port']
23
+ @@uri_value = options['uri']
24
+ @@use_ssl_value = options['use_ssl']
25
+ self.token = options['token']
26
+ self.workspace_name = options['workspace_name']
27
+ self.nexpose_console_name = options['nexpose_console_name']
28
+ @@device_ip_to_scan_value = options['device_ip_to_scan']
29
+ self.use_os_filter = options['use_os_filter']
30
+ self.module_filter = options['module_filter']
31
+ self.report_type = options['report_type']
39
32
  end
40
33
 
41
34
  def verify
@@ -81,6 +74,17 @@ class ExploitRunDescription
81
74
  "DS_ModuleFilter" => self.module_filter}
82
75
  end
83
76
 
77
+ def get_report_options
78
+ {
79
+ 'workspace' => self.workspace_name,
80
+ 'name' => self.workspace_name,
81
+ 'report_type' => self.report_type,
82
+ 'created_by' => self.workspace_name,
83
+ 'file_formats' => [:pdf],
84
+ 'DS_WHITELIST_HOSTS' => self.device_ip_to_scan
85
+ }
86
+ end
87
+
84
88
  def device_ip_to_scan
85
89
  "http://#{@@device_ip_to_scan_value}"
86
90
  end
@@ -10,6 +10,7 @@ describe 'exploit_run_description' do
10
10
  @expected_ssl = false
11
11
  @expected_os_filter = false
12
12
  @expected_module_filter = 'exploit/windows/smb/psexec'
13
+ @expected_report_type = :fisma
13
14
  @expected_workspacename = 'workspacename'
14
15
  @expected_nexpose_console_name = 'nexpose_console_name'
15
16
  @expected_webscan_task_id = '12'
@@ -18,18 +19,21 @@ describe 'exploit_run_description' do
18
19
  @mock_rpc_client = get_mock_rpc_client
19
20
  @mock_device_ip_to_scan = '127.0.0.1'
20
21
  @mock_device_url_to_scan = "http://#{@mock_device_ip_to_scan}"
22
+ @options = {
23
+ 'connection_url' => @expected_connection,
24
+ 'port' => @expected_port,
25
+ 'uri' => @expected_uri,
26
+ 'use_ssl' => @expected_ssl,
27
+ 'token' => @expected_token,
28
+ 'workspace_name' => @expected_workspace_name,
29
+ 'nexpose_console_name' => @expected_nexpose_console_name,
30
+ 'device_ip_to_scan' => @mock_device_ip_to_scan,
31
+ 'use_os_filter' => @expected_use_os_filter,
32
+ 'module_filter' => @expected_module_filter,
33
+ 'report_type' => @expected_report_type
34
+ }
21
35
 
22
- @exploit_run_description = ExploitRunDescription.new @expected_connection,
23
- @expected_port,
24
- @expected_uri,
25
- @expected_ssl,
26
- @expected_token,
27
- @expected_workspace_name,
28
- @expected_nexpose_console_name,
29
- @mock_device_ip_to_scan,
30
- @expected_os_filter,
31
- @expected_module_filter
32
-
36
+ @exploit_run_description = ExploitRunDescription.new(@options)
33
37
  end
34
38
 
35
39
  it 'should accept all of the needed parameters and persist them' do
@@ -43,6 +47,7 @@ describe 'exploit_run_description' do
43
47
  expect(@exploit_run_description.device_ip_to_scan).to eq(@mock_device_url_to_scan)
44
48
  expect(@exploit_run_description.use_os_filter).to eq(@expected_os_filter)
45
49
  expect(@exploit_run_description.module_filter).to eq(@expected_module_filter)
50
+ expect(@exploit_run_description.report_type).to eq(@expected_report_type)
46
51
  end
47
52
 
48
53
  it 'should use 3790 as default if port is empty string' do
data/spec/exploit_spec.rb CHANGED
@@ -20,6 +20,7 @@ describe 'exploit' do
20
20
  @expected_import_task_id = '1'
21
21
  @expected_exploit_task_id = '13'
22
22
  @expected_audit_task_id = '14'
23
+ @expected_report_id = '15'
23
24
  @expected_audit_max_requests = 1000
24
25
  @expected_audit_max_minutes = 3
25
26
  @expected_audit_max_threads = 5
@@ -31,10 +32,25 @@ describe 'exploit' do
31
32
  @expected_match_vulns = true
32
33
  @expected_match_ports = true
33
34
  @expected_ssl_version ='TLS1'
35
+ @expected_report_type = :fisma
34
36
  @expected_module_filter = 'exploit/windows/smb/psexec'
35
37
  @mock_rpc_client = get_mock_rpc_client
36
38
  @mock_device_ip_to_scan = '127.0.0.1'
37
39
  @mock_device_url_to_scan = "http://#{@mock_device_ip_to_scan}"
40
+
41
+ @options = {
42
+ 'connection_url' => @expected_connection,
43
+ 'port' => @expected_port,
44
+ 'uri' => @expected_uri,
45
+ 'use_ssl' => @expected_ssl,
46
+ 'token' => @expected_token,
47
+ 'workspace_name' => @expected_workspace_name,
48
+ 'nexpose_console_name' => @expected_nexpose_console_name,
49
+ 'device_ip_to_scan' => @mock_device_ip_to_scan,
50
+ 'use_os_filter' => @expected_use_os_filter,
51
+ 'module_filter' => @expected_module_filter,
52
+ 'report_type' => @expected_report_type
53
+ }
38
54
  end
39
55
 
40
56
  describe 'get connection' do
@@ -45,22 +61,31 @@ describe 'exploit' do
45
61
  .with(expected_options)
46
62
  .and_return(@mock_rpc_client)
47
63
 
48
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
64
+ Metasploit::Exploit.start(@options)
49
65
  end
50
66
 
51
67
  it 'should throw an error if no token is passed' do
52
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, '', @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Token is required')
53
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, nil, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Token is required')
68
+ options = @options.clone
69
+ options['token'] = nil;
70
+ expect {
71
+ Metasploit::Exploit.start(options)
72
+ }.to raise_error(StandardError, 'PWNED! Token is required')
54
73
  end
55
74
 
56
75
  it 'should throw an error if no connection url is passed' do
57
- expect { Metasploit::Exploit.start('', @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Connection URL is required')
58
- expect { Metasploit::Exploit.start(nil, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Connection URL is required')
76
+ options = @options.clone
77
+ options['connection_url'] = nil
78
+ expect {
79
+ Metasploit::Exploit.start(options)
80
+ }.to raise_error(StandardError, 'PWNED! Connection URL is required')
59
81
  end
60
82
 
61
83
  it 'should throw an error if no ip address is passed' do
62
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, '', @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Device IP to scan is required')
63
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, nil, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Device IP to scan is required')
84
+ options = @options.clone
85
+ options['device_ip_to_scan'] = nil;
86
+ expect {
87
+ Metasploit::Exploit.start(options)
88
+ }.to raise_error(StandardError, 'PWNED! Device IP to scan is required')
64
89
  end
65
90
 
66
91
  it 'should use 3790 as default if port is empty string' do
@@ -70,30 +95,41 @@ describe 'exploit' do
70
95
  .with(expected_options)
71
96
  .and_return(@mock_rpc_client)
72
97
 
73
- Metasploit::Exploit.start(@expected_connection, '', @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
98
+ run_options = @options.clone
99
+ run_options['port'] = nil
100
+ Metasploit::Exploit.start(run_options)
74
101
  end
75
102
  end
76
103
 
77
104
  describe 'create workspace' do
78
105
  it 'should create a workspace based on workspace name' do
79
106
  expect(@mock_rpc_client).to receive(:call)
80
- .with('pro.workspace_add', {'name' => @expected_workspace_name})
107
+ .with('pro.workspace_add', {
108
+ 'name' => @expected_workspace_name
109
+ })
81
110
 
82
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
111
+ Metasploit::Exploit.start(@options)
83
112
  end
84
113
 
85
114
  it 'should throw an error if workspace name is invalid' do
86
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, '', @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Workspace Name is required')
87
- expect { Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, nil, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter) }.to raise_error(StandardError, 'PWNED! Workspace Name is required')
115
+ options = @options.clone
116
+ options['workspace_name'] = nil
117
+ expect {
118
+ Metasploit::Exploit.start(options)
119
+ }.to raise_error(StandardError, 'PWNED! Workspace Name is required')
88
120
  end
89
121
  end
90
122
 
91
123
  describe 'should skip nexpose import' do
92
124
  it 'should skip the import if nexpose_console variable is empty or nil' do
93
- expect {Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, '', @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)}.to output(/\[\*\] Nexpose Console option was not passed, skipping Nexpose Import/).to_stdout
94
- expect {Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, nil, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)}.to output(/\[\*\] Nexpose Console option was not passed, skipping Nexpose Import/).to_stdout
95
- expect {Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, '', @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)}.to_not output(/\[\*\] Importing.../).to_stdout
96
- expect {Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, nil, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)}.to_not output(/\[\*\] Importing...'/).to_stdout
125
+ options = @options.clone
126
+ options['nexpose_console_name'] = nil
127
+ expect {
128
+ Metasploit::Exploit.start(options)
129
+ }.to output(/\[\*\] Nexpose Console option was not passed, skipping Nexpose Import/).to_stdout
130
+ expect {
131
+ Metasploit::Exploit.start(options)
132
+ }.to_not output(/\[\*\] Importing.../).to_stdout
97
133
  end
98
134
  end
99
135
 
@@ -101,61 +137,88 @@ describe 'exploit' do
101
137
 
102
138
  it 'should start a import' do
103
139
  expect(@mock_rpc_client).to receive(:call)
104
- .with('pro.start_import', {'workspace' => @expected_workspace_name,
105
- 'DS_NEXPOSE_CONSOLE' => @expected_nexpose_console_name,
106
- 'DS_NEXPOSE_SITE' => @expected_workspace_name})
107
-
108
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
140
+ .with('pro.start_import', {
141
+ 'workspace' => @expected_workspace_name,
142
+ 'DS_NEXPOSE_CONSOLE' => @expected_nexpose_console_name,
143
+ 'DS_NEXPOSE_SITE' => @expected_workspace_name
144
+ })
145
+
146
+ Metasploit::Exploit.start(@options)
109
147
  end
110
148
 
111
149
  describe 'wait to be over' do
112
150
  before(:each) do
113
151
  expect(@mock_rpc_client).to receive(:call)
114
- .with('pro.start_import', {'workspace' => @expected_workspace_name,
115
- 'DS_NEXPOSE_CONSOLE' => @expected_nexpose_console_name,
116
- 'DS_NEXPOSE_SITE' => @expected_workspace_name})
152
+ .with('pro.start_import', {
153
+ 'workspace' => @expected_workspace_name,
154
+ 'DS_NEXPOSE_CONSOLE' => @expected_nexpose_console_name,
155
+ 'DS_NEXPOSE_SITE' => @expected_workspace_name
156
+ })
117
157
  .and_return({'task_id' => @expected_import_task_id})
118
158
  end
119
159
 
120
160
  it 'should call to check the status of an import' do
121
161
  expect(@mock_rpc_client).to receive(:call).with('pro.task_status', @expected_import_task_id)
122
-
123
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
162
+
163
+ Metasploit::Exploit.start(@options)
124
164
  end
125
165
 
126
166
  it 'should call to check the status until it is not running' do
127
167
  expect(@mock_rpc_client).to receive(:call)
128
168
  .with('pro.task_status', @expected_import_task_id)
129
- .and_return({'1'=>{'status' => 'running', 'progress' => 25, 'info' => 'Generating the export data file'}})
169
+ .and_return({
170
+ '1' => {
171
+ 'status' => 'running',
172
+ 'progress' => 25,
173
+ 'info' => 'Generating the export data file'
174
+ }
175
+ })
130
176
  .exactly(3).times
131
177
  .ordered
132
178
 
133
179
  expect(@mock_rpc_client).to receive(:call)
134
180
  .with('pro.task_status', @expected_import_task_id)
135
- .and_return({'1'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
181
+ .and_return({
182
+ '1' => {
183
+ 'status' => 'not running',
184
+ 'progress' => 100,
185
+ 'info' => 'Complete'
186
+ }
187
+ })
136
188
  .once
137
189
  .ordered
138
190
 
139
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
191
+ Metasploit::Exploit.start(@options)
140
192
  end
141
193
 
142
194
  it 'should sleep for 3 seconds if the status is still running' do
143
195
  expect(@mock_rpc_client).to receive(:call)
144
196
  .with('pro.task_status', @expected_import_task_id)
145
- .and_return({'1'=>{'status' => 'running', 'progress' => 25, 'info' => 'Generating the export data file'}})
197
+ .and_return({
198
+ '1' => {
199
+ 'status' => 'running',
200
+ 'progress' => 25,
201
+ 'info' => 'Generating the export data file'
202
+ }
203
+ })
146
204
  .exactly(3).times
147
205
  .ordered
148
206
 
149
207
  expect(@mock_rpc_client).to receive(:call)
150
208
  .with('pro.task_status', @expected_import_task_id)
151
- .and_return({'1'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
209
+ .and_return({
210
+ '1' => {
211
+ 'status' => 'not running',
212
+ 'progress' => 100,
213
+ 'info' => 'Complete'
214
+ }
215
+ })
152
216
  .once
153
217
  .ordered
154
-
155
218
  #Expecting 7 because we are mocking 6 above and the global :call mock in get_mock_rpc_client
156
- expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(7).times
157
-
158
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
219
+ expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(107).times
220
+
221
+ Metasploit::Exploit.start(@options)
159
222
  end
160
223
  end
161
224
  end
@@ -163,77 +226,123 @@ describe 'exploit' do
163
226
  describe 'start metasploit scan' do
164
227
  it 'should kick off a scan' do
165
228
  expect(@mock_rpc_client).to receive(:call)
166
- .with('pro.start_webscan', {'workspace' => @expected_workspace_name,
167
- 'DS_URLS' => @mock_device_url_to_scan})
229
+ .with('pro.start_webscan', {
230
+ 'workspace' => @expected_workspace_name,
231
+ 'DS_URLS' => @mock_device_url_to_scan
232
+ })
168
233
 
169
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
234
+ Metasploit::Exploit.start(@options)
170
235
  end
171
236
 
172
237
  describe 'wait for scan to be over' do
173
238
  before(:each) do
174
239
  expect(@mock_rpc_client).to receive(:call)
175
- .with('pro.start_webscan', {'workspace' => @expected_workspace_name,
176
- 'DS_URLS' => @mock_device_url_to_scan})
177
- .and_return({'task_id' => @expected_webscan_task_id})
240
+ .with('pro.start_webscan', {
241
+ 'workspace' => @expected_workspace_name,
242
+ 'DS_URLS' => @mock_device_url_to_scan
243
+ })
244
+ .and_return({
245
+ 'task_id' => @expected_webscan_task_id
246
+ })
178
247
  end
179
248
 
180
249
  it 'should call to check the status of the scan' do
181
250
  expect(@mock_rpc_client).to receive(:call).with('pro.task_status', @expected_webscan_task_id)
182
251
 
183
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
252
+ Metasploit::Exploit.start(@options)
184
253
  end
185
254
 
186
255
  it 'should call to check the status until it is not running' do
187
256
  expect(@mock_rpc_client).to receive(:call)
188
257
  .with('pro.task_status', @expected_webscan_task_id)
189
- .and_return({'12'=>{'status' => 'running', 'progress' => 50, 'info' => 'Validating Target URLs'}})
258
+ .and_return({
259
+ '12' => {
260
+ 'status' => 'running',
261
+ 'progress' => 50,
262
+ 'info' => 'Validating Target URLs'
263
+ }
264
+ })
190
265
  .exactly(3).times
191
266
  .ordered
192
267
 
193
268
  expect(@mock_rpc_client).to receive(:call)
194
269
  .with('pro.task_status', @expected_webscan_task_id)
195
- .and_return({'12'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
270
+ .and_return({
271
+ '12' => {
272
+ 'status' => 'not running',
273
+ 'progress' => 100,
274
+ 'info' => 'Complete'
275
+ }
276
+ })
196
277
  .once
197
278
  .ordered
198
279
 
199
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
280
+ Metasploit::Exploit.start(@options)
200
281
  end
201
282
 
202
283
  it 'should sleep for 3 seconds if the status is still running' do
203
284
  expect(@mock_rpc_client).to receive(:call)
204
285
  .with('pro.task_status', @expected_webscan_task_id)
205
- .and_return({'12'=>{'status' => 'running', 'progress' => 50, 'info' => 'Validating Target URLs'}})
286
+ .and_return({
287
+ '12' => {
288
+ 'status' => 'running',
289
+ 'progress' => 50,
290
+ 'info' => 'Validating Target URLs'
291
+ }
292
+ })
206
293
  .exactly(3).times
207
294
  .ordered
208
295
 
209
296
  expect(@mock_rpc_client).to receive(:call)
210
297
  .with('pro.task_status', @expected_webscan_task_id)
211
- .and_return({'12'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
298
+ .and_return({
299
+ '12' => {
300
+ 'status' => 'not running',
301
+ 'progress' => 100,
302
+ 'info' => 'Complete'
303
+ }
304
+ })
212
305
  .once
213
306
  .ordered
214
307
 
215
308
  #Expecting 7 because we are mocking 6 above and the global :call mock in get_mock_rpc_client
216
- expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(7).times
309
+ expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(107).times
217
310
 
218
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
311
+ Metasploit::Exploit.start(@options)
219
312
  end
220
313
  end
221
314
  end
222
315
 
316
+ describe 'start generating report' do
317
+ it 'should start a report' do
318
+ expect(@mock_rpc_client).to receive(:call)
319
+ .with('pro.start_report', {
320
+ 'workspace' => @expected_workspace_name,
321
+ 'name' => @expected_workspace_name,
322
+ 'report_type' => @expected_report_type,
323
+ 'created_by' => @expected_workspace_name,
324
+ 'file_formats' => [:pdf],
325
+ 'DS_WHITELIST_HOSTS' => @mock_device_url_to_scan,
326
+ })
327
+
328
+ Metasploit::Exploit.start(@options)
329
+ end
330
+ end
331
+
223
332
  describe 'start an audit' do
224
333
 
225
334
  it 'should kick off an audit' do
226
335
  expect(@mock_rpc_client).to receive(:call)
227
336
  .with('pro.start_webaudit', {
228
- 'workspace' => @expected_workspace_name,
229
- 'DS_URLS' => @mock_device_url_to_scan,
230
- 'DS_MAX_REQUESTS' => @expected_audit_max_requests,
231
- 'DS_MAX_MINUTES' => @expected_audit_max_minutes,
232
- 'DS_MAX_THREADS' => @expected_audit_max_threads,
233
- 'DS_MAX_INSTANCES' => @expected_audit_max_instances
234
- })
235
-
236
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
337
+ 'workspace' => @expected_workspace_name,
338
+ 'DS_URLS' => @mock_device_url_to_scan,
339
+ 'DS_MAX_REQUESTS' => @expected_audit_max_requests,
340
+ 'DS_MAX_MINUTES' => @expected_audit_max_minutes,
341
+ 'DS_MAX_THREADS' => @expected_audit_max_threads,
342
+ 'DS_MAX_INSTANCES' => @expected_audit_max_instances
343
+ })
344
+
345
+ Metasploit::Exploit.start(@options)
237
346
  end
238
347
 
239
348
  describe 'wait for audit to be over' do
@@ -241,55 +350,82 @@ describe 'exploit' do
241
350
 
242
351
  expect(@mock_rpc_client).to receive(:call)
243
352
  .with('pro.start_webaudit', {
244
- "workspace" => @expected_workspace_name,
245
- "DS_URLS" => @mock_device_url_to_scan,
246
- "DS_MAX_REQUESTS" => @expected_audit_max_requests,
247
- "DS_MAX_MINUTES" => @expected_audit_max_minutes,
248
- "DS_MAX_THREADS" => @expected_audit_max_threads,
249
- "DS_MAX_INSTANCES" => @expected_audit_max_instances
250
- })
353
+ "workspace" => @expected_workspace_name,
354
+ "DS_URLS" => @mock_device_url_to_scan,
355
+ "DS_MAX_REQUESTS" => @expected_audit_max_requests,
356
+ "DS_MAX_MINUTES" => @expected_audit_max_minutes,
357
+ "DS_MAX_THREADS" => @expected_audit_max_threads,
358
+ "DS_MAX_INSTANCES" => @expected_audit_max_instances
359
+ })
251
360
  .and_return({'task_id' => @expected_audit_task_id})
252
361
  end
253
362
 
254
363
  it 'should call to check the status of the audit' do
255
- expect(@mock_rpc_client).to receive(:call).with('pro.task_status', @expected_audit_task_id)
364
+ expect(@mock_rpc_client).to receive(:call)
365
+ .with('pro.task_status', @expected_audit_task_id)
256
366
 
257
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
367
+ Metasploit::Exploit.start(@options)
258
368
  end
259
369
 
260
370
  it 'should call to check the status until it is not running' do
261
371
  expect(@mock_rpc_client).to receive(:call)
262
372
  .with('pro.task_status', @expected_audit_task_id)
263
- .and_return({'14'=>{'status' => 'running', 'progress' => 3, 'info' => 'Auditing your website'}})
373
+ .and_return({
374
+ '14' => {
375
+ 'status' => 'running',
376
+ 'progress' => 3,
377
+ 'info' => 'Auditing your website'
378
+ }
379
+ })
264
380
  .exactly(3).times
265
381
  .ordered
266
382
 
267
383
  expect(@mock_rpc_client).to receive(:call)
268
384
  .with('pro.task_status', @expected_audit_task_id)
269
- .and_return({'14'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
385
+ .and_return({
386
+ '14' => {
387
+ 'status' => 'not running',
388
+ 'progress' => 100,
389
+ 'info' => 'Complete'
390
+ }
391
+ })
270
392
  .once
271
393
  .ordered
272
394
 
273
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
395
+ Metasploit::Exploit.start(@options)
274
396
  end
275
397
 
276
398
  it 'should sleep for 3 seconds if the status is still running' do
277
399
  expect(@mock_rpc_client).to receive(:call)
278
400
  .with('pro.task_status', @expected_audit_task_id)
279
- .and_return({'14'=>{'status' => 'running', 'progress' => 3, 'info' => 'Auditing your website'}})
401
+ .and_return({
402
+ '14' => {
403
+ 'status' => 'running',
404
+ 'progress' => 3,
405
+ 'info' => 'Auditing your website'
406
+ }
407
+ })
280
408
  .exactly(3).times
281
409
  .ordered
282
410
 
283
411
  expect(@mock_rpc_client).to receive(:call)
284
412
  .with('pro.task_status', @expected_audit_task_id)
285
- .and_return({'14'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
413
+ .and_return({
414
+ '14' => {
415
+ 'status' => 'not running',
416
+ 'progress' => 100,
417
+ 'info' => 'Complete'
418
+ }
419
+ })
286
420
  .once
287
421
  .ordered
422
+
423
+ expect(Metasploit::Exploit).to receive(:sleep)
424
+ .with(3)
425
+ .exactly(107)
426
+ .times
288
427
 
289
- #Expecting 7 because we are mocking 6 above and the global :call mock in get_mock_rpc_client
290
- expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(7).times
291
-
292
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
428
+ Metasploit::Exploit.start(@options)
293
429
  end
294
430
  end
295
431
  end
@@ -299,163 +435,210 @@ describe 'exploit' do
299
435
  it 'should kick off an exploit' do
300
436
  expect(@mock_rpc_client).to receive(:call)
301
437
  .with('pro.start_exploit', {
302
- "workspace" => @expected_workspace_name,
303
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
304
- "DS_MinimumRank" => @expected_minimum_rank,
305
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
306
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
307
- "DS_LimitSessions" => @expected_session_limit,
308
- "DS_MATCH_VULNS" => @expected_match_vulns,
309
- "DS_MATCH_PORTS" => @expected_match_ports,
310
- "DS_FilterByOS" => @expected_use_os_filter,
311
- "DS_ModuleFilter" => @expected_module_filter
312
- })
313
-
314
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
438
+ "workspace" => @expected_workspace_name,
439
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
440
+ "DS_MinimumRank" => @expected_minimum_rank,
441
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
442
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
443
+ "DS_LimitSessions" => @expected_session_limit,
444
+ "DS_MATCH_VULNS" => @expected_match_vulns,
445
+ "DS_MATCH_PORTS" => @expected_match_ports,
446
+ "DS_FilterByOS" => @expected_use_os_filter,
447
+ "DS_ModuleFilter" => @expected_module_filter
448
+ })
449
+
450
+ Metasploit::Exploit.start(@options)
315
451
  end
316
452
 
317
453
  it 'should use a operating system filter if its set to true' do
318
454
  expect(@mock_rpc_client).to receive(:call)
319
455
  .with('pro.start_exploit', {
320
- "workspace" => @expected_workspace_name,
321
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
322
- "DS_MinimumRank" => @expected_minimum_rank,
323
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
324
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
325
- "DS_LimitSessions" => @expected_session_limit,
326
- "DS_MATCH_VULNS" => @expected_match_vulns,
327
- "DS_MATCH_PORTS" => @expected_match_ports,
328
- "DS_FilterByOS" => @expected_use_os_filter,
329
- "DS_ModuleFilter" => @expected_module_filter
330
- })
331
-
332
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, true, @expected_module_filter)
456
+ "workspace" => @expected_workspace_name,
457
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
458
+ "DS_MinimumRank" => @expected_minimum_rank,
459
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
460
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
461
+ "DS_LimitSessions" => @expected_session_limit,
462
+ "DS_MATCH_VULNS" => @expected_match_vulns,
463
+ "DS_MATCH_PORTS" => @expected_match_ports,
464
+ "DS_FilterByOS" => @expected_use_os_filter,
465
+ "DS_ModuleFilter" => @expected_module_filter
466
+ })
467
+
468
+ Metasploit::Exploit.start(@options)
333
469
  end
334
470
 
335
471
  it 'should not use a operating system filter if its set to false' do
336
472
  expect(@mock_rpc_client).to receive(:call)
337
- .with('pro.start_exploit', {"workspace" => @expected_workspace_name,
338
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
339
- "DS_MinimumRank" => @expected_minimum_rank,
340
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
341
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
342
- "DS_LimitSessions" => @expected_session_limit,
343
- "DS_MATCH_VULNS" => @expected_match_vulns,
344
- "DS_MATCH_PORTS" => @expected_match_ports,
345
- "DS_FilterByOS" => false,
346
- "DS_ModuleFilter" => @expected_module_filter
347
- })
348
-
349
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, false, @expected_module_filter)
473
+ .with('pro.start_exploit', {
474
+ "workspace" => @expected_workspace_name,
475
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
476
+ "DS_MinimumRank" => @expected_minimum_rank,
477
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
478
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
479
+ "DS_LimitSessions" => @expected_session_limit,
480
+ "DS_MATCH_VULNS" => @expected_match_vulns,
481
+ "DS_MATCH_PORTS" => @expected_match_ports,
482
+ "DS_FilterByOS" => false,
483
+ "DS_ModuleFilter" => @expected_module_filter
484
+ })
485
+
486
+ options = @options.clone
487
+ options['use_os_filter'] = false
488
+ Metasploit::Exploit.start(options)
350
489
  end
351
490
 
352
491
  it 'should not use a module filter if no modules are passed' do
353
492
  expect(@mock_rpc_client).to receive(:call)
354
- .with('pro.start_exploit', {"workspace" => @expected_workspace_name,
355
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
356
- "DS_MinimumRank" => @expected_minimum_rank,
357
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
358
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
359
- "DS_LimitSessions" => @expected_session_limit,
360
- "DS_MATCH_VULNS" => @expected_match_vulns,
361
- "DS_MATCH_PORTS" => @expected_match_ports,
362
- "DS_FilterByOS" => false,
363
- "DS_ModuleFilter" => ''
364
- })
365
-
366
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, false, '')
493
+ .with('pro.start_exploit', {
494
+ "workspace" => @expected_workspace_name,
495
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
496
+ "DS_MinimumRank" => @expected_minimum_rank,
497
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
498
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
499
+ "DS_LimitSessions" => @expected_session_limit,
500
+ "DS_MATCH_VULNS" => @expected_match_vulns,
501
+ "DS_MATCH_PORTS" => @expected_match_ports,
502
+ "DS_FilterByOS" => false,
503
+ "DS_ModuleFilter" => nil
504
+ })
505
+
506
+ options = @options.clone
507
+ options['module_filter'] = nil
508
+ options['use_os_filter'] = false
509
+ Metasploit::Exploit.start(options)
367
510
  end
368
511
 
369
512
  it 'should use a module filter if a module is passed' do
370
513
  expect(@mock_rpc_client).to receive(:call)
371
- .with('pro.start_exploit', {"workspace" => @expected_workspace_name,
372
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
373
- "DS_MinimumRank" => @expected_minimum_rank,
374
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
375
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
376
- "DS_LimitSessions" => @expected_session_limit,
377
- "DS_MATCH_VULNS" => @expected_match_vulns,
378
- "DS_MATCH_PORTS" => @expected_match_ports,
379
- "DS_FilterByOS" => false,
380
- "DS_ModuleFilter" => @expected_module_filter
381
- })
382
-
383
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, false, @expected_module_filter)
514
+ .with('pro.start_exploit', {
515
+ "workspace" => @expected_workspace_name,
516
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
517
+ "DS_MinimumRank" => @expected_minimum_rank,
518
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
519
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
520
+ "DS_LimitSessions" => @expected_session_limit,
521
+ "DS_MATCH_VULNS" => @expected_match_vulns,
522
+ "DS_MATCH_PORTS" => @expected_match_ports,
523
+ "DS_FilterByOS" => false,
524
+ "DS_ModuleFilter" => @expected_module_filter
525
+ })
526
+ options = @options.clone
527
+ options['use_os_filter'] = false
528
+ Metasploit::Exploit.start(options)
384
529
  end
385
530
 
386
531
  describe 'wait for exploit to be over' do
387
532
  before(:each) do
388
533
 
389
534
  expect(@mock_rpc_client).to receive(:call)
390
- .with('pro.start_exploit', {"workspace" => @expected_workspace_name,
391
- "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
392
- "DS_MinimumRank" => @expected_minimum_rank,
393
- "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
394
- "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
395
- "DS_LimitSessions" => @expected_session_limit,
396
- "DS_MATCH_VULNS" => @expected_match_vulns,
397
- "DS_MATCH_PORTS" => @expected_match_ports,
398
- "DS_FilterByOS" => @expected_use_os_filter,
399
- "DS_ModuleFilter" => @expected_module_filter
400
- })
401
- .and_return({'task_id' => @expected_exploit_task_id})
535
+ .with('pro.start_exploit', {
536
+ "workspace" => @expected_workspace_name,
537
+ "DS_WHITELIST_HOSTS" => @mock_device_ip_to_scan,
538
+ "DS_MinimumRank" => @expected_minimum_rank,
539
+ "DS_EXPLOIT_SPEED" => @expected_exploit_speed,
540
+ "DS_EXPLOIT_TIMEOUT" => @expected_exploit_timeout,
541
+ "DS_LimitSessions" => @expected_session_limit,
542
+ "DS_MATCH_VULNS" => @expected_match_vulns,
543
+ "DS_MATCH_PORTS" => @expected_match_ports,
544
+ "DS_FilterByOS" => @expected_use_os_filter,
545
+ "DS_ModuleFilter" => @expected_module_filter
546
+ })
547
+ .and_return({
548
+ 'task_id' => @expected_exploit_task_id
549
+ })
402
550
  end
403
551
 
404
552
  it 'should call to check the status of the exploit' do
405
- expect(@mock_rpc_client).to receive(:call).with('pro.task_status', @expected_exploit_task_id)
553
+ expect(@mock_rpc_client).to receive(:call)
554
+ .with('pro.task_status', @expected_exploit_task_id)
406
555
 
407
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
556
+ Metasploit::Exploit.start(@options)
408
557
  end
409
558
 
410
559
  it 'should call to check the status until it is not running' do
411
560
  expect(@mock_rpc_client).to receive(:call)
412
561
  .with('pro.task_status', @expected_exploit_task_id)
413
- .and_return({'13'=>{'status' => 'running', 'progress' => 3, 'info' => 'WordPress Asset-Manager PHP File Upload Vulnerability'}})
562
+ .and_return({
563
+ '13' => {
564
+ 'status' => 'running',
565
+ 'progress' => 3,
566
+ 'info' => 'WordPress Asset-Manager PHP File Upload Vulnerability'
567
+ }
568
+ })
414
569
  .exactly(3).times
415
570
  .ordered
416
571
 
417
572
  expect(@mock_rpc_client).to receive(:call)
418
573
  .with('pro.task_status', @expected_exploit_task_id)
419
- .and_return({'13'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
574
+ .and_return({
575
+ '13' => {
576
+ 'status' => 'not running',
577
+ 'progress' => 100,
578
+ 'info' => 'Complete'
579
+ }
580
+ })
420
581
  .once
421
582
  .ordered
422
583
 
423
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
584
+ Metasploit::Exploit.start(@options)
424
585
  end
425
586
 
426
587
  it 'should sleep for 3 seconds if the status is still running' do
427
588
  expect(@mock_rpc_client).to receive(:call)
428
589
  .with('pro.task_status', @expected_exploit_task_id)
429
- .and_return({'13'=>{'status' => 'running', 'progress' => 3, 'info' => 'WordPress Asset-Manager PHP File Upload Vulnerability'}})
590
+ .and_return({
591
+ '13' => {
592
+ 'status' => 'running',
593
+ 'progress' => 3,
594
+ 'info' => 'WordPress Asset-Manager PHP File Upload Vulnerability'
595
+ }
596
+ })
430
597
  .exactly(3).times
431
598
  .ordered
432
599
 
433
600
  expect(@mock_rpc_client).to receive(:call)
434
601
  .with('pro.task_status', @expected_exploit_task_id)
435
- .and_return({'13'=>{'status' => 'not running', 'progress' => 100, 'info' => 'Complete'}})
602
+ .and_return({
603
+ '13' => {
604
+ 'status' => 'not running',
605
+ 'progress' => 100,
606
+ 'info' => 'Complete'
607
+ }
608
+ })
436
609
  .once
437
610
  .ordered
438
611
 
439
- #Expecting 7 because we are mocking 6 above and the global :call mock in get_mock_rpc_client
440
- expect(Metasploit::Exploit).to receive(:sleep).with(3).exactly(7).times
612
+ expect(Metasploit::Exploit).to receive(:sleep)
613
+ .with(3)
614
+ .exactly(107)
615
+ .times
441
616
 
442
- Metasploit::Exploit.start(@expected_connection, @expected_port, @expected_uri, @expected_ssl, @expected_token, @expected_workspace_name, @expected_nexpose_console_name, @mock_device_ip_to_scan, @expected_use_os_filter, @expected_module_filter)
617
+ Metasploit::Exploit.start(@options)
443
618
  end
444
619
  end
445
620
  end
446
621
 
447
-
448
622
  end
449
623
  end
450
624
 
451
625
  def get_default_options_and_override(override)
452
- {:host => @expected_connection, :port => @expected_port, :token => @expected_token, :uri => @expected_uri, :ssl => @expected_ssl, :ssl_version => @expected_ssl_version}.merge(override)
626
+ {
627
+ :host => @expected_connection,
628
+ :port => @expected_port,
629
+ :token => @expected_token,
630
+ :uri => @expected_uri,
631
+ :ssl => @expected_ssl,
632
+ :ssl_version => @expected_ssl_version
633
+ }.merge(override)
453
634
  end
454
635
 
455
636
  def get_mock_rpc_client
456
637
  mock_rpc_client = double(Msf::RPC::Client)
457
638
 
458
- allow(mock_rpc_client).to receive(:call).with(any_args).and_return({})
639
+ allow(mock_rpc_client).to receive(:call)
640
+ .with(any_args)
641
+ .and_return({})
459
642
 
460
643
  allow(Msf::RPC::Client).to receive(:new)
461
644
  .and_return(mock_rpc_client)
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: metasploit-runner
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.9
4
+ version: 0.2.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Nathan Gibson
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-02-11 00:00:00.000000000 Z
11
+ date: 2015-03-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: msfrpc-client