pwn 0.5.401 → 0.5.403

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: d84bc3035034f9064b99d250eaebdae6868b2a6c67df2cd4ce9463060f32115f
4
- data.tar.gz: 4be12fe5b7df1abdf32a8ce0944eafa6e627138823b0010bc05ad9be2181a35c
3
+ metadata.gz: 3e5390f3bf6209a6f425edc5c920dbd6869add40979a7f25e8962356d5c9a6bd
4
+ data.tar.gz: 5cf631f4bc2838ed8f016bc0da2d34c4543b4610300783ce39ace423d501be57
5
5
  SHA512:
6
- metadata.gz: fbd47dd6ccf640ea9cfaebefb5ee4543ceb878f403700ddcc211872764ceb0ec5a494657fe3b5cd25f1f80039130bdea3c738b66d8cce31fec00a697667b48e0
7
- data.tar.gz: eff9efbad951fe531b743fea854f23f38afd1e55101d2c88a6b2134ab7a2689710957c1eedb90bba97bf1bac46d15b88972cdae0aa8ce83bbc67aa5d83af3351
6
+ metadata.gz: 36181bae24a6d150c6badf0f42a5c1e7a76fc0f385ffe775eaf0b1d2403fbbcb577aaf5dd746b0f5f6cacbcd34fdd3b40be5bf31006f1a701499906236f38b21
7
+ data.tar.gz: cabc729dc772df80d270bc43192db6127cf1f6c418f580031d909a1c66488d8e75c24212e137758b01fe94eb45ae955fdee2d803a1ca6da553c38a3966e7ed27
data/README.md CHANGED
@@ -37,7 +37,7 @@ $ cd /opt/pwn
37
37
  $ ./install.sh
38
38
  $ ./install.sh ruby-gem
39
39
  $ pwn
40
- pwn[v0.5.401]:001 >>> PWN.help
40
+ pwn[v0.5.403]:001 >>> PWN.help
41
41
  ```
42
42
 
43
43
  [![Installing the pwn Security Automation Framework](https://raw.githubusercontent.com/0dayInc/pwn/master/documentation/pwn_install.png)](https://youtu.be/G7iLUY4FzsI)
@@ -52,7 +52,7 @@ $ rvm use ruby-3.4.4@pwn
52
52
  $ gem uninstall --all --executables pwn
53
53
  $ gem install --verbose pwn
54
54
  $ pwn
55
- pwn[v0.5.401]:001 >>> PWN.help
55
+ pwn[v0.5.403]:001 >>> PWN.help
56
56
  ```
57
57
 
58
58
  If you're using a multi-user install of RVM do:
@@ -62,7 +62,7 @@ $ rvm use ruby-3.4.4@pwn
62
62
  $ rvmsudo gem uninstall --all --executables pwn
63
63
  $ rvmsudo gem install --verbose pwn
64
64
  $ pwn
65
- pwn[v0.5.401]:001 >>> PWN.help
65
+ pwn[v0.5.403]:001 >>> PWN.help
66
66
  ```
67
67
 
68
68
  PWN periodically upgrades to the latest version of Ruby which is reflected in `/opt/pwn/.ruby-version`. The easiest way to upgrade to the latest version of Ruby from a previous PWN installation is to run the following script:
@@ -31,6 +31,10 @@ OptionParser.new do |options|
31
31
  opts[:headless] = h
32
32
  end
33
33
 
34
+ options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to firefox)>') do |b|
35
+ opts[:browser_type] = b
36
+ end
37
+
34
38
  options.on('-D', '--[no-]debug', '<Optional - Enable Debug Output and Do Not Delete Temporary OpenAPI Spec>') do |d|
35
39
  opts[:debug] = d
36
40
  end
@@ -55,7 +59,7 @@ OptionParser.new do |options|
55
59
  opts[:exclude_paths] = e
56
60
  end
57
61
 
58
- options.on('-iURL', '--in_scope=URL', '<Optional - URL to add include in scope (Defaults to value of --target_url)>') do |s|
62
+ options.on('-iURL', '--in_scope=URL', '<Optional - URL to include in scope (Defaults to value of --target_url)>') do |s|
59
63
  opts[:in_scope] = s
60
64
  end
61
65
  end.parse!
@@ -80,6 +84,8 @@ begin
80
84
 
81
85
  burp_jar_path = opts[:burp_jar_path]
82
86
  headless = opts[:headless] || false
87
+ browser_type = opts[:browser_type] ||= :firefox
88
+ browser_type = browser_type.to_s.downcase.to_sym unless browser_type.is_a?(Symbol)
83
89
  debug = opts[:debug] || false
84
90
 
85
91
  swagger_defs_arr = swagger_definitions.split(',').map(&:strip)
@@ -120,7 +126,7 @@ begin
120
126
  else
121
127
  burp_obj = PWN::Plugins::BurpSuite.start(
122
128
  burp_jar_path: burp_jar_path,
123
- browser_type: :chrome
129
+ browser_type: browser_type
124
130
  )
125
131
  end
126
132
 
@@ -165,10 +171,8 @@ begin
165
171
  output_dir: output_dir
166
172
  )
167
173
  end
168
-
169
- burp_obj = PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj)
170
174
  rescue StandardError => e
171
175
  raise e
172
176
  ensure
173
- burp_obj = PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj) unless burp_obj.nil?
177
+ PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj) unless burp_obj.nil?
174
178
  end
@@ -30,7 +30,7 @@ OptionParser.new do |options|
30
30
  opts[:headless] = h
31
31
  end
32
32
 
33
- options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to chrome)>') do |b|
33
+ options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to firefox)>') do |b|
34
34
  opts[:browser_type] = b
35
35
  end
36
36
 
@@ -42,7 +42,7 @@ OptionParser.new do |options|
42
42
  opts[:navigation_instruct] = i
43
43
  end
44
44
 
45
- options.on('-iURL', '--in_scope=URL', '<Optional - URL to add include in scope (Defaults to value of --target_url)>') do |s|
45
+ options.on('-iURL', '--in_scope=URL', '<Optional - URL to include in scope (Defaults to value of --target_url)>') do |s|
46
46
  opts[:in_scope] = s
47
47
  end
48
48
  end.parse!
@@ -65,7 +65,8 @@ begin
65
65
  exlude_paths = exlude_paths.split(',').map(&:strip) if exlude_paths.is_a?(String)
66
66
  burp_jar_path = opts[:burp_jar_path]
67
67
  headless = opts[:headless] || false
68
- browser_type = opts[:browser_type] ||= :chrome
68
+ browser_type = opts[:browser_type] ||= :firefox
69
+ browser_type = browser_type.to_s.downcase.to_sym unless browser_type.is_a?(Symbol)
69
70
  spider = opts[:spider] || false
70
71
  navigation_instruct = opts[:navigation_instruct]
71
72
  in_scope = opts[:in_scope] ||= target_url
@@ -100,7 +101,7 @@ begin
100
101
  # support JavaScript, DOM-based XSS vuln attempts are
101
102
  # possible as well since we have a DOM to interact w/
102
103
  # (Burp's DOM-XSS checks are based on static code analysis)
103
- browser_obj = burp_obj[:burp_browser]
104
+ browser_obj = burp_obj[:mitm_browser]
104
105
  browser = browser_obj[:browser]
105
106
  browser.goto(target_url)
106
107
 
@@ -135,10 +136,8 @@ begin
135
136
  output_dir: output_dir
136
137
  )
137
138
  end
138
-
139
- burp_obj = PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj)
140
139
  rescue StandardError => e
141
140
  raise e
142
141
  ensure
143
- burp_obj = PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj) unless burp_obj.nil?
142
+ PWN::Plugins::BurpSuite.stop(burp_obj: burp_obj) unless burp_obj.nil?
144
143
  end
@@ -36,6 +36,10 @@ OptionParser.new do |options|
36
36
  opts[:headless] = h
37
37
  end
38
38
 
39
+ options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to firefox)>') do |b|
40
+ opts[:browser_type] = b
41
+ end
42
+
39
43
  options.on('-D', '--[no-]debug', '<Optional - Enable Debug Output and Do Not Delete Temporary OpenAPI Spec>') do |d|
40
44
  opts[:debug] = d
41
45
  end
@@ -52,7 +56,7 @@ OptionParser.new do |options|
52
56
  opts[:exclude_paths] = e
53
57
  end
54
58
 
55
- options.on('-iURL', '--in_scope=URL', '<Optional - URL to add include in scope (Defaults to value of --target_url)>') do |s|
59
+ options.on('-iURL', '--in_scope=URL', '<Optional - URL regex to include in scope (Defaults to "<target_url>.*")>') do |s|
56
60
  opts[:in_scope] = s
57
61
  end
58
62
  end.parse!
@@ -80,6 +84,8 @@ begin
80
84
 
81
85
  zap_bin_path = opts[:zap_bin_path]
82
86
  headless = opts[:headless] || false
87
+ browser_type = opts[:browser_type] ||= :firefox
88
+ browser_type = browser_type.to_s.downcase.to_sym unless browser_type.is_a?(Symbol)
83
89
  debug = opts[:debug] || false
84
90
 
85
91
  swagger_defs_arr = swagger_definitions.split(',').map(&:strip)
@@ -100,12 +106,10 @@ begin
100
106
  )
101
107
 
102
108
  additional_http_headers = opts[:additional_http_headers]
103
- additional_http_headers = JSON.parse(additional_http_headers, symbolize_names: true) if additional_http_headers.is_a?(String)
104
-
105
109
  exlude_paths = opts[:exclude_paths]
106
110
  exlude_paths = exlude_paths.split(',').map(&:strip) if exlude_paths.is_a?(String)
107
111
 
108
- in_scope = opts[:in_scope] ||= target_url
112
+ in_scope = opts[:in_scope] ||= "#{target_url}.*"
109
113
 
110
114
  # ------
111
115
  # Open ZAP
@@ -117,7 +121,7 @@ begin
117
121
  else
118
122
  zap_obj = PWN::Plugins::Zaproxy.start(
119
123
  zap_bin_path: zap_bin_path,
120
- browser_type: :chrome
124
+ browser_type: browser_type
121
125
  )
122
126
  end
123
127
 
@@ -127,12 +131,25 @@ begin
127
131
  zap_obj: zap_obj,
128
132
  openapi_spec: openapi_spec
129
133
  )
130
-
131
134
  raise "ERROR: Failed to import OpenAPI/Swagger spec #{openapi_spec} into ZAP's Sitemap." if json_sitemap.nil? || json_sitemap.empty?
132
135
 
136
+ if additional_http_headers.is_a?(String)
137
+ additional_http_headers = JSON.parse(additional_http_headers, symbolize_names: true)
138
+ PWN::Plugins::Zaproxy.inject_additional_http_headers(
139
+ zap_obj: zap_obj,
140
+ target_regex: in_scope,
141
+ additional_http_headers: additional_http_headers
142
+ )
143
+ end
144
+
145
+ PWN::Plugins::Zaproxy.add_to_scope(
146
+ zap_obj: zap_obj,
147
+ target_regex: in_scope
148
+ )
149
+
133
150
  PWN::Plugins::Zaproxy.active_scan(
134
151
  zap_obj: zap_obj,
135
- target_url: target_url,
152
+ target_url: in_scope,
136
153
  exclude_paths: exlude_paths
137
154
  )
138
155
 
@@ -150,10 +167,8 @@ begin
150
167
  output_dir: output_dir
151
168
  )
152
169
  end
153
-
154
- zap_obj = PWN::Plugins::Zaproxy.stop(zap_obj: zap_obj)
155
170
  rescue StandardError => e
156
171
  raise e
157
172
  ensure
158
- zap_obj = PWN::Plugins::Zaproxy.stop(zap_obj: zap_obj) unless zap_obj.nil?
173
+ PWN::Plugins::Zaproxy.stop(zap_obj: zap_obj) unless zap_obj.nil?
159
174
  end
@@ -34,7 +34,7 @@ OptionParser.new do |options|
34
34
  opts[:headless] = h
35
35
  end
36
36
 
37
- options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to chrome)>') do |b|
37
+ options.on('-bTYPE', '--browser_type=TYPE', '<Optional - Browser Type <firefox|chrome|headless|rest> (Defaults to firefox)>') do |b|
38
38
  opts[:browser_type] = b
39
39
  end
40
40
 
@@ -46,7 +46,7 @@ OptionParser.new do |options|
46
46
  opts[:navigation_instruct] = i
47
47
  end
48
48
 
49
- options.on('-iURL', '--in_scope=URL', '<Optional - URL to add include in scope (Defaults to value of --target_url)>') do |s|
49
+ options.on('-iURL', '--in_scope=URL', '<Optional - URL regex to include in scope (Defaults to "<target_url>.*")>') do |s|
50
50
  opts[:in_scope] = s
51
51
  end
52
52
  end.parse!
@@ -62,12 +62,6 @@ begin
62
62
  api_key = opts[:api_key]
63
63
  raise 'ERROR: --api_key is required.' if api_key.nil?
64
64
 
65
- if opts[:browser_type].nil?
66
- browser_type = :chrome
67
- else
68
- browser_type = opts[:browser_type].to_s.strip.chomp.scrub.to_sym
69
- end
70
-
71
65
  target_url = opts[:target_url]
72
66
  raise 'ERROR: --target_url is required.' if target_url.nil?
73
67
 
@@ -78,10 +72,11 @@ begin
78
72
  exlude_paths = exlude_paths.split(',').map(&:strip) if exlude_paths.is_a?(String)
79
73
  zap_bin_path = opts[:zap_bin_path].to_s.strip.chomp.scrub if File.exist?(opts[:zap_bin_path].to_s.strip.chomp.scrub)
80
74
  headless = opts[:headless] || false
81
- browser_type = opts[:browser_type] ||= :chrome
75
+ browser_type = opts[:browser_type] ||= :firefox
76
+ browser_type = browser_type.to_s.downcase.to_sym unless browser_type.is_a?(Symbol)
82
77
  spider = opts[:spider] || false
83
78
  navigation_instruct = opts[:navigation_instruct]
84
- in_scope = opts[:in_scope] ||= target_url
79
+ in_scope = opts[:in_scope] ||= "#{target_url}.*"
85
80
 
86
81
  # ------
87
82
  # Dynamically build arguments hash based on flags passed and Open Zap
@@ -102,7 +97,7 @@ begin
102
97
 
103
98
  logger.info(zap_obj)
104
99
 
105
- browser_obj = zap_obj[:zap_browser]
100
+ browser_obj = zap_obj[:mitm_browser]
106
101
  browser = browser_obj[:browser]
107
102
  browser.goto(target_url)
108
103
 
@@ -117,9 +112,16 @@ begin
117
112
  end
118
113
 
119
114
  PWN::Plugins::Zaproxy.spider(zap_obj: zap_obj, target_url: target_url) if spider
115
+
116
+ PWN::Plugins::Zaproxy.add_to_scope(
117
+ zap_obj: zap_obj,
118
+ target_regex: in_scope
119
+ )
120
+
120
121
  PWN::Plugins::Zaproxy.active_scan(
121
122
  zap_obj: zap_obj,
122
- target_url: target_url
123
+ target_url: in_scope,
124
+ exclude_paths: exlude_paths
123
125
  )
124
126
 
125
127
  # Generate all Report Types
@@ -133,11 +135,8 @@ begin
133
135
 
134
136
  logger.info("Report can be found here: #{report_path}")
135
137
  end
136
-
137
- PWN::Plugins::Zaproxy.stop(zap_obj: zap_obj)
138
138
  rescue StandardError => e
139
139
  raise e
140
140
  ensure
141
141
  PWN::Plugins::Zaproxy.stop(zap_obj: zap_obj) unless zap_obj.nil?
142
- browser_obj = PWN::Plugins::TransparentBrowser.close(browser_obj: browser_obj) unless browser_obj.nil?
143
142
  end
@@ -82,7 +82,7 @@ module PWN
82
82
  rest_browser = browser_obj1[:browser]
83
83
 
84
84
  burp_obj[:mitm_proxy] = "#{burp_ip}:#{burp_port}"
85
- burp_obj[:pwn_burp_api] = "#{pwn_burp_ip}:#{pwn_burp_port}"
85
+ burp_obj[:mitm_rest_api] = "#{pwn_burp_ip}:#{pwn_burp_port}"
86
86
  burp_obj[:rest_browser] = rest_browser
87
87
 
88
88
  # Proxy always listens on localhost...use SSH tunneling if remote access is required
@@ -92,7 +92,7 @@ module PWN
92
92
  devtools: true
93
93
  )
94
94
 
95
- burp_obj[:burp_browser] = browser_obj2
95
+ burp_obj[:mitm_browser] = browser_obj2
96
96
 
97
97
  # Wait for pwn_burp_port to open prior to returning burp_obj
98
98
  loop do
@@ -133,11 +133,11 @@ module PWN
133
133
  raise 'ERROR: uri parameter is required' if uri.nil?
134
134
 
135
135
  rest_browser = burp_obj[:rest_browser]
136
- pwn_burp_api = burp_obj[:pwn_burp_api]
136
+ mitm_rest_api = burp_obj[:mitm_rest_api]
137
137
  base64_encoded_uri = Base64.strict_encode64(uri.to_s.scrub.strip.chomp)
138
138
 
139
139
  in_scope_resp = rest_browser.get(
140
- "http://#{pwn_burp_api}/scope/#{base64_encoded_uri}",
140
+ "http://#{mitm_rest_api}/scope/#{base64_encoded_uri}",
141
141
  content_type: 'application/json; charset=UTF8'
142
142
  )
143
143
  json_in_scope = JSON.parse(in_scope_resp, symbolize_names: true)
@@ -156,11 +156,11 @@ module PWN
156
156
  burp_obj = opts[:burp_obj]
157
157
  target_url = opts[:target_url]
158
158
  rest_browser = burp_obj[:rest_browser]
159
- pwn_burp_api = burp_obj[:pwn_burp_api]
159
+ mitm_rest_api = burp_obj[:mitm_rest_api]
160
160
 
161
161
  post_body = { url: target_url }.to_json
162
162
 
163
- in_scope = rest_browser.post("http://#{pwn_burp_api}/scope", post_body, content_type: 'application/json; charset=UTF8')
163
+ in_scope = rest_browser.post("http://#{mitm_rest_api}/scope", post_body, content_type: 'application/json; charset=UTF8')
164
164
  JSON.parse(in_scope, symbolize_names: true)
165
165
  rescue StandardError => e
166
166
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -177,12 +177,12 @@ module PWN
177
177
  burp_obj = opts[:burp_obj]
178
178
  target_url = opts[:target_url]
179
179
  rest_browser = burp_obj[:rest_browser]
180
- pwn_burp_api = burp_obj[:pwn_burp_api]
180
+ mitm_rest_api = burp_obj[:mitm_rest_api]
181
181
 
182
182
  post_body = { url: target_url }.to_json
183
183
 
184
184
  in_scope = rest_browser.post(
185
- "http://#{pwn_burp_api}/spider",
185
+ "http://#{mitm_rest_api}/spider",
186
186
  post_body,
187
187
  content_type: 'application/json; charset=UTF8'
188
188
  )
@@ -192,7 +192,7 @@ module PWN
192
192
  spider_status_json = {}
193
193
  loop do
194
194
  print '.'
195
- spider_status_resp = rest_browser.get("http://#{pwn_burp_api}/spider/#{spider_id}")
195
+ spider_status_resp = rest_browser.get("http://#{mitm_rest_api}/spider/#{spider_id}")
196
196
  spider_status_json = JSON.parse(spider_status_resp, symbolize_names: true)
197
197
  spider_status = spider_status_json[:status]
198
198
  case spider_status
@@ -221,9 +221,9 @@ module PWN
221
221
  public_class_method def self.enable_proxy(opts = {})
222
222
  burp_obj = opts[:burp_obj]
223
223
  rest_browser = burp_obj[:rest_browser]
224
- pwn_burp_api = burp_obj[:pwn_burp_api]
224
+ mitm_rest_api = burp_obj[:mitm_rest_api]
225
225
 
226
- enable_resp = rest_browser.post("http://#{pwn_burp_api}/proxy/intercept/enable", nil)
226
+ enable_resp = rest_browser.post("http://#{mitm_rest_api}/proxy/intercept/enable", nil)
227
227
  JSON.parse(enable_resp, symbolize_names: true)
228
228
  rescue StandardError => e
229
229
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -238,9 +238,9 @@ module PWN
238
238
  public_class_method def self.disable_proxy(opts = {})
239
239
  burp_obj = opts[:burp_obj]
240
240
  rest_browser = burp_obj[:rest_browser]
241
- pwn_burp_api = burp_obj[:pwn_burp_api]
241
+ mitm_rest_api = burp_obj[:mitm_rest_api]
242
242
 
243
- disable_resp = rest_browser.post("http://#{pwn_burp_api}/proxy/intercept/disable", nil)
243
+ disable_resp = rest_browser.post("http://#{mitm_rest_api}/proxy/intercept/disable", nil)
244
244
  JSON.parse(disable_resp, symbolize_names: true)
245
245
  rescue StandardError => e
246
246
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -255,9 +255,9 @@ module PWN
255
255
  public_class_method def self.get_proxy_listeners(opts = {})
256
256
  burp_obj = opts[:burp_obj]
257
257
  rest_browser = burp_obj[:rest_browser]
258
- pwn_burp_api = burp_obj[:pwn_burp_api]
258
+ mitm_rest_api = burp_obj[:mitm_rest_api]
259
259
 
260
- listeners = rest_browser.get("http://#{pwn_burp_api}/proxy/listeners", content_type: 'application/json; charset=UTF8')
260
+ listeners = rest_browser.get("http://#{mitm_rest_api}/proxy/listeners", content_type: 'application/json; charset=UTF8')
261
261
  JSON.parse(listeners, symbolize_names: true)
262
262
  rescue StandardError => e
263
263
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -275,7 +275,7 @@ module PWN
275
275
  public_class_method def self.add_proxy_listener(opts = {})
276
276
  burp_obj = opts[:burp_obj]
277
277
  rest_browser = burp_obj[:rest_browser]
278
- pwn_burp_api = burp_obj[:pwn_burp_api]
278
+ mitm_rest_api = burp_obj[:mitm_rest_api]
279
279
  bind_address = opts[:bind_address]
280
280
  raise 'ERROR: bind_address parameter is required' if bind_address.nil?
281
281
 
@@ -295,7 +295,7 @@ module PWN
295
295
  enabled: enabled
296
296
  }.to_json
297
297
 
298
- listener = rest_browser.post("http://#{pwn_burp_api}/proxy/listeners", post_body, content_type: 'application/json; charset=UTF8')
298
+ listener = rest_browser.post("http://#{mitm_rest_api}/proxy/listeners", post_body, content_type: 'application/json; charset=UTF8')
299
299
  JSON.parse(listener, symbolize_names: true)
300
300
  rescue StandardError => e
301
301
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -314,7 +314,7 @@ module PWN
314
314
  public_class_method def self.update_proxy_listener(opts = {})
315
315
  burp_obj = opts[:burp_obj]
316
316
  rest_browser = burp_obj[:rest_browser]
317
- pwn_burp_api = burp_obj[:pwn_burp_api]
317
+ mitm_rest_api = burp_obj[:mitm_rest_api]
318
318
  id = opts[:id] ||= '0'
319
319
  bind_address = opts[:bind_address] ||= '127.0.0.1'
320
320
  port = opts[:port] ||= 8080
@@ -327,7 +327,7 @@ module PWN
327
327
  enabled: enabled
328
328
  }.to_json
329
329
 
330
- listener = rest_browser.put("http://#{pwn_burp_api}/proxy/listeners/#{id}", post_body, content_type: 'application/json; charset=UTF8')
330
+ listener = rest_browser.put("http://#{mitm_rest_api}/proxy/listeners/#{id}", post_body, content_type: 'application/json; charset=UTF8')
331
331
  JSON.parse(listener, symbolize_names: true)
332
332
  rescue StandardError => e
333
333
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -343,11 +343,11 @@ module PWN
343
343
  public_class_method def self.delete_proxy_listener(opts = {})
344
344
  burp_obj = opts[:burp_obj]
345
345
  rest_browser = burp_obj[:rest_browser]
346
- pwn_burp_api = burp_obj[:pwn_burp_api]
346
+ mitm_rest_api = burp_obj[:mitm_rest_api]
347
347
  id = opts[:id] ||= '0'
348
348
  raise 'ERROR: id parameter is required' if id.nil?
349
349
 
350
- rest_browser.delete("http://#{pwn_burp_api}/proxy/listeners/#{id}")
350
+ rest_browser.delete("http://#{mitm_rest_api}/proxy/listeners/#{id}")
351
351
  true # Return true to indicate successful deletion (or error if API fails)
352
352
  rescue StandardError => e
353
353
  stop(burp_obj: burp_obj) unless burp_obj.nil?
@@ -363,12 +363,12 @@ module PWN
363
363
  public_class_method def self.get_sitemap(opts = {})
364
364
  burp_obj = opts[:burp_obj]
365
365
  rest_browser = burp_obj[:rest_browser]
366
- pwn_burp_api = burp_obj[:pwn_burp_api]
366
+ mitm_rest_api = burp_obj[:mitm_rest_api]
367
367
  target_url = opts[:target_url]
368
368
 
369
369
  base64_encoded_target_url = Base64.strict_encode64(target_url.to_s.scrub.strip.chomp) if target_url
370
370
 
371
- rest_call = "http://#{pwn_burp_api}/sitemap"
371
+ rest_call = "http://#{mitm_rest_api}/sitemap"
372
372
  rest_call = "#{rest_call}/#{base64_encoded_target_url}" if target_url
373
373
 
374
374
  sitemap = rest_browser.get(
@@ -407,14 +407,14 @@ module PWN
407
407
  public_class_method def self.add_to_sitemap(opts = {})
408
408
  burp_obj = opts[:burp_obj]
409
409
  rest_browser = burp_obj[:rest_browser]
410
- pwn_burp_api = burp_obj[:pwn_burp_api]
410
+ mitm_rest_api = burp_obj[:mitm_rest_api]
411
411
  sitemap = opts[:sitemap] ||= {}
412
412
  debug = opts[:debug] || false
413
413
 
414
414
  rest_client = rest_browser::Request
415
415
  response = rest_client.execute(
416
416
  method: :post,
417
- url: "http://#{pwn_burp_api}/sitemap",
417
+ url: "http://#{mitm_rest_api}/sitemap",
418
418
  payload: sitemap.to_json,
419
419
  headers: { content_type: 'application/json; charset=UTF-8' },
420
420
  timeout: 10
@@ -881,14 +881,14 @@ module PWN
881
881
  # Supported Method Parameters::
882
882
  # active_scan_url_arr = PWN::Plugins::BurpSuite.active_scan(
883
883
  # burp_obj: 'required - burp_obj returned by #start method',
884
- # target_url: 'required - target url to scan in sitemap (should be loaded & authenticated w/ burp_obj[:burp_browser])',
884
+ # target_url: 'required - target url to scan in sitemap (should be loaded & authenticated w/ burp_obj[:mitm_browser])',
885
885
  # exclude_paths: 'optional - array of paths to exclude from active scan (default: [])'
886
886
  # )
887
887
 
888
888
  public_class_method def self.active_scan(opts = {})
889
889
  burp_obj = opts[:burp_obj]
890
890
  rest_browser = burp_obj[:rest_browser]
891
- pwn_burp_api = burp_obj[:pwn_burp_api]
891
+ mitm_rest_api = burp_obj[:mitm_rest_api]
892
892
  target_url = opts[:target_url].to_s.scrub.strip.chomp
893
893
  raise 'ERROR: target_url parameter is required' if target_url.empty?
894
894
 
@@ -947,7 +947,7 @@ module PWN
947
947
  }.to_json
948
948
  # Kick off an active scan for each given page in the json_sitemap results
949
949
  resp = rest_browser.post(
950
- "http://#{pwn_burp_api}/scan/active",
950
+ "http://#{mitm_rest_api}/scan/active",
951
951
  post_body,
952
952
  content_type: 'application/json'
953
953
  )
@@ -959,7 +959,7 @@ module PWN
959
959
 
960
960
  # Wait for scan completion
961
961
  loop do
962
- scan_queue = rest_browser.get("http://#{pwn_burp_api}/scan/active")
962
+ scan_queue = rest_browser.get("http://#{mitm_rest_api}/scan/active")
963
963
  json_scan_queue = JSON.parse(scan_queue, symbolize_names: true)
964
964
  break if json_scan_queue.all? { |scan| scan[:status] == 'finished' }
965
965
 
@@ -975,7 +975,7 @@ module PWN
975
975
  # json_scan_queue.each do |scan_item|
976
976
  # this_scan_item_id = scan_item[:id]
977
977
  # until scan_item[:status] == 'finished'
978
- # scan_item_resp = rest_browser.get("http://#{pwn_burp_api}/scan/active/#{this_scan_item_id}")
978
+ # scan_item_resp = rest_browser.get("http://#{mitm_rest_api}/scan/active/#{this_scan_item_id}")
979
979
  # scan_item = JSON.parse(scan_item_resp, symbolize_names: true)
980
980
  # scan_status = scan_item[:status]
981
981
  # puts "Target ID ##{this_scan_item_id} of ##{scan_queue_total}| #{scan_status}"
@@ -999,12 +999,12 @@ module PWN
999
999
  public_class_method def self.get_scan_issues(opts = {})
1000
1000
  burp_obj = opts[:burp_obj]
1001
1001
  rest_browser = burp_obj[:rest_browser]
1002
- pwn_burp_api = burp_obj[:pwn_burp_api]
1002
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1003
1003
 
1004
1004
  rest_client = rest_browser::Request
1005
1005
  scan_issues = rest_client.execute(
1006
1006
  method: :get,
1007
- url: "http://#{pwn_burp_api}/scanissues",
1007
+ url: "http://#{mitm_rest_api}/scanissues",
1008
1008
  timeout: 540
1009
1009
  )
1010
1010
  JSON.parse(scan_issues, symbolize_names: true)
@@ -1031,7 +1031,7 @@ module PWN
1031
1031
  raise 'ERROR: request parameter is required' if request.nil?
1032
1032
 
1033
1033
  rest_browser = burp_obj[:rest_browser]
1034
- pwn_burp_api = burp_obj[:pwn_burp_api]
1034
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1035
1035
 
1036
1036
  post_body = {
1037
1037
  name: name[0..29],
@@ -1039,7 +1039,7 @@ module PWN
1039
1039
  }.to_json
1040
1040
 
1041
1041
  repeater_resp = rest_browser.post(
1042
- "http://#{pwn_burp_api}/repeater",
1042
+ "http://#{mitm_rest_api}/repeater",
1043
1043
  post_body,
1044
1044
  content_type: 'application/json; charset=UTF8'
1045
1045
  )
@@ -1060,10 +1060,10 @@ module PWN
1060
1060
  raise 'ERROR: burp_obj parameter is required' unless burp_obj.is_a?(Hash)
1061
1061
 
1062
1062
  rest_browser = burp_obj[:rest_browser]
1063
- pwn_burp_api = burp_obj[:pwn_burp_api]
1063
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1064
1064
 
1065
1065
  repeater_resp = rest_browser.get(
1066
- "http://#{pwn_burp_api}/repeater",
1066
+ "http://#{mitm_rest_api}/repeater",
1067
1067
  content_type: 'application/json; charset=UTF8'
1068
1068
  )
1069
1069
 
@@ -1086,10 +1086,10 @@ module PWN
1086
1086
  raise 'ERROR: id parameter is required' if id.nil?
1087
1087
 
1088
1088
  rest_browser = burp_obj[:rest_browser]
1089
- pwn_burp_api = burp_obj[:pwn_burp_api]
1089
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1090
1090
 
1091
1091
  repeater_resp = rest_browser.get(
1092
- "http://#{pwn_burp_api}/repeater/#{id}",
1092
+ "http://#{mitm_rest_api}/repeater/#{id}",
1093
1093
  content_type: 'application/json; charset=UTF8'
1094
1094
  )
1095
1095
 
@@ -1112,10 +1112,10 @@ module PWN
1112
1112
  raise 'ERROR: id parameter is required' if id.nil?
1113
1113
 
1114
1114
  rest_browser = burp_obj[:rest_browser]
1115
- pwn_burp_api = burp_obj[:pwn_burp_api]
1115
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1116
1116
 
1117
1117
  repeater_resp = rest_browser.post(
1118
- "http://#{pwn_burp_api}/repeater/#{id}/send",
1118
+ "http://#{mitm_rest_api}/repeater/#{id}/send",
1119
1119
  content_type: 'application/json; charset=UTF8'
1120
1120
  )
1121
1121
 
@@ -1146,7 +1146,7 @@ module PWN
1146
1146
  raise 'ERROR: request parameter is required' if request.nil?
1147
1147
 
1148
1148
  rest_browser = burp_obj[:rest_browser]
1149
- pwn_burp_api = burp_obj[:pwn_burp_api]
1149
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1150
1150
 
1151
1151
  put_body = {
1152
1152
  name: name[0..29],
@@ -1154,7 +1154,7 @@ module PWN
1154
1154
  }.to_json
1155
1155
 
1156
1156
  repeater_resp = rest_browser.put(
1157
- "http://#{pwn_burp_api}/repeater/#{id}",
1157
+ "http://#{mitm_rest_api}/repeater/#{id}",
1158
1158
  put_body,
1159
1159
  content_type: 'application/json; charset=UTF8'
1160
1160
  )
@@ -1178,10 +1178,10 @@ module PWN
1178
1178
  raise 'ERROR: id parameter is required' if id.nil?
1179
1179
 
1180
1180
  rest_browser = burp_obj[:rest_browser]
1181
- pwn_burp_api = burp_obj[:pwn_burp_api]
1181
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1182
1182
 
1183
1183
  rest_browser.delete(
1184
- "http://#{pwn_burp_api}/repeater/#{id}",
1184
+ "http://#{mitm_rest_api}/repeater/#{id}",
1185
1185
  content_type: 'application/json; charset=UTF8'
1186
1186
  )
1187
1187
 
@@ -1202,7 +1202,7 @@ module PWN
1202
1202
  burp_obj = opts[:burp_obj]
1203
1203
  target_url = opts[:target_url]
1204
1204
  rest_browser = burp_obj[:rest_browser]
1205
- pwn_burp_api = burp_obj[:pwn_burp_api]
1205
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1206
1206
  output_dir = opts[:output_dir]
1207
1207
  raise "ERROR: #{output_dir} does not exist." unless Dir.exist?(output_dir)
1208
1208
 
@@ -1236,7 +1236,7 @@ module PWN
1236
1236
  report_url = Base64.strict_encode64(target_domain)
1237
1237
  # Ready scanreport API call in pwn_burp to support HTML & XML report generation
1238
1238
  report_resp = rest_browser.get(
1239
- "http://#{pwn_burp_api}/scanreport/#{report_type.to_s.upcase}/#{report_url}"
1239
+ "http://#{mitm_rest_api}/scanreport/#{report_type.to_s.upcase}/#{report_url}"
1240
1240
  )
1241
1241
 
1242
1242
  File.open(report_path, 'w') do |f|
@@ -1264,13 +1264,13 @@ module PWN
1264
1264
 
1265
1265
  public_class_method def self.stop(opts = {})
1266
1266
  burp_obj = opts[:burp_obj]
1267
- browser_obj = burp_obj[:burp_browser]
1267
+ browser_obj = burp_obj[:mitm_browser]
1268
1268
  rest_browser = burp_obj[:rest_browser]
1269
- pwn_burp_api = burp_obj[:pwn_burp_api]
1269
+ mitm_rest_api = burp_obj[:mitm_rest_api]
1270
1270
  # burp_pid = burp_obj[:pid]
1271
1271
 
1272
- browser_obj = PWN::Plugins::TransparentBrowser.close(browser_obj: browser_obj)
1273
- rest_browser.post("http://#{pwn_burp_api}/shutdown", '')
1272
+ PWN::Plugins::TransparentBrowser.close(browser_obj: browser_obj)
1273
+ rest_browser.post("http://#{mitm_rest_api}/shutdown", '')
1274
1274
  # Process.kill('TERM', burp_pid)
1275
1275
 
1276
1276
  burp_obj = nil
@@ -1381,7 +1381,7 @@ module PWN
1381
1381
 
1382
1382
  active_scan_url_arr = #{self}.active_scan(
1383
1383
  burp_obj: 'required - burp_obj returned by #start method',
1384
- target_url: 'required - target url to scan in sitemap (should be loaded & authenticated w/ burp_obj[:burp_browser])',
1384
+ target_url: 'required - target url to scan in sitemap (should be loaded & authenticated w/ burp_obj[:mitm_browser])',
1385
1385
  exclude_paths: 'optional - array of paths to exclude from active scan (default: [])'
1386
1386
  )
1387
1387
 
@@ -1225,7 +1225,8 @@ module PWN
1225
1225
  PWN::Plugins::Tor.stop(tor_obj: browser_obj[:tor_obj]) if tor_obj
1226
1226
 
1227
1227
  # Close the browser unless browser.nil? (thus the &)
1228
- browser&.close unless browser.to_s == 'RestClient'
1228
+ # browser&.close unless browser.to_s == 'RestClient'
1229
+ browser&.close unless browser.is_a?(RestClient)
1229
1230
 
1230
1231
  nil
1231
1232
  rescue StandardError => e
@@ -24,17 +24,15 @@ module PWN
24
24
  private_class_method def self.zap_rest_call(opts = {})
25
25
  zap_obj = opts[:zap_obj]
26
26
  rest_call = opts[:rest_call].to_s.scrub
27
- http_method = if opts[:http_method].nil?
28
- :get
29
- else
30
- opts[:http_method].to_s.scrub.to_sym
31
- end
27
+ http_method = opts[:http_method] ||= :get
28
+ http_method = http_method.to_s.downcase.to_sym unless http_method.is_a?(Symbol)
32
29
  params = opts[:params]
33
30
  http_body = opts[:http_body].to_s.scrub
34
- zap_rest_api = zap_obj[:zap_rest_api]
35
- base_zap_api_uri = "http://#{zap_rest_api}"
36
31
 
37
32
  rest_client = zap_obj[:rest_browser]::Request
33
+ mitm_rest_api = zap_obj[:mitm_rest_api]
34
+
35
+ base_zap_api_uri = "http://#{mitm_rest_api}"
38
36
 
39
37
  case http_method
40
38
  when :get
@@ -66,7 +64,7 @@ module PWN
66
64
 
67
65
  response
68
66
  rescue StandardError, SystemExit, Interrupt => e
69
- stop(zap_obj) unless zap_obj.nil?
67
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
70
68
  raise e
71
69
  end
72
70
 
@@ -100,20 +98,11 @@ module PWN
100
98
  zap_rest_ip = zap_ip
101
99
  zap_rest_port = zap_port
102
100
 
103
- if headless
104
- zaproxy_cmd = "cd #{zap_root} && ./#{zap_bin} -daemon"
105
- else
106
- zaproxy_cmd = "cd #{zap_root} && ./#{zap_bin}"
107
- end
108
-
109
- zaproxy_cmd = "#{zaproxy_cmd} -host #{zap_ip} -port #{zap_port}"
110
-
111
- zap_obj[:pid] = Process.spawn(zaproxy_cmd)
112
101
  browser_obj1 = PWN::Plugins::TransparentBrowser.open(browser_type: :rest)
113
102
  rest_browser = browser_obj1[:browser]
114
103
 
115
104
  zap_obj[:mitm_proxy] = "#{zap_ip}:#{zap_port}"
116
- zap_obj[:zap_rest_api] = zap_obj[:mitm_proxy]
105
+ zap_obj[:mitm_rest_api] = zap_obj[:mitm_proxy]
117
106
  zap_obj[:rest_browser] = rest_browser
118
107
 
119
108
  browser_obj2 = PWN::Plugins::TransparentBrowser.open(
@@ -122,8 +111,17 @@ module PWN
122
111
  devtools: true
123
112
  )
124
113
 
125
- zap_obj[:zap_browser] = browser_obj2
114
+ zap_obj[:mitm_browser] = browser_obj2
126
115
 
116
+ if headless
117
+ zaproxy_cmd = "cd #{zap_root} && ./#{zap_bin} -daemon"
118
+ else
119
+ zaproxy_cmd = "cd #{zap_root} && ./#{zap_bin}"
120
+ end
121
+
122
+ zaproxy_cmd = "#{zaproxy_cmd} -host #{zap_ip} -port #{zap_port}"
123
+
124
+ zap_obj[:pid] = Process.spawn(zaproxy_cmd)
127
125
  # Wait for pwn_burp_port to open prior to returning burp_obj
128
126
  loop do
129
127
  s = TCPSocket.new(zap_rest_ip, zap_rest_port)
@@ -136,8 +134,8 @@ module PWN
136
134
  end
137
135
 
138
136
  zap_obj
139
- rescue StandardError, SystemExit, Interrupt => e
140
- stop(zap_obj) unless zap_obj.nil?
137
+ rescue Selenium::WebDriver::Error::SessionNotCreatedError, StandardError, SystemExit, Interrupt => e
138
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
141
139
  raise e
142
140
  end
143
141
 
@@ -169,7 +167,40 @@ module PWN
169
167
 
170
168
  JSON.parse(response.body, symbolize_names: true)
171
169
  rescue StandardError, SystemExit, Interrupt => e
172
- stop(zap_obj) unless zap_obj.nil?
170
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
171
+ raise e
172
+ end
173
+
174
+ # Supported Method Parameters::
175
+ # PWN::Plugins::Zaproxy.add_to_scope(
176
+ # zap_obj: 'required - zap_obj returned from #open method',
177
+ # target_regex: 'required - url regex to add to scope (e.g. https://test.domain.local.*)',
178
+ # context_name: 'optional - context name to add target_regex to (defaults to Default Context)'
179
+ # )
180
+
181
+ public_class_method def self.add_to_scope(opts = {})
182
+ zap_obj = opts[:zap_obj]
183
+ api_key = zap_obj[:api_key].to_s.scrub
184
+ target_regex = opts[:target_regex]
185
+ raise 'ERROR: target_url must be provided' if target_regex.nil?
186
+
187
+ context_name = opts[:context_name] ||= 'Default Context'
188
+
189
+ params = {
190
+ apikey: api_key,
191
+ contextName: context_name,
192
+ regex: target_regex
193
+ }
194
+
195
+ response = zap_rest_call(
196
+ zap_obj: zap_obj,
197
+ rest_call: 'JSON/context/action/includeInContext/',
198
+ params: params
199
+ )
200
+
201
+ JSON.parse(response.body, symbolize_names: true)
202
+ rescue StandardError, SystemExit, Interrupt => e
203
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
173
204
  raise e
174
205
  end
175
206
 
@@ -222,7 +253,53 @@ module PWN
222
253
  break if status == 100
223
254
  end
224
255
  rescue StandardError, SystemExit, Interrupt => e
225
- stop(zap_obj) unless zap_obj.nil?
256
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
257
+ raise e
258
+ end
259
+
260
+ # Supported Method Parameters::
261
+ # PWN::Plugins::Zaproxy.inject_additional_http_headers(
262
+ # zap_obj: 'required - zap_obj returned from #open method',
263
+ # target_regex: 'required - url regex to inject headers into (e.g. https://test.domain.local.*)',
264
+ # headers: 'required - hash of additional headers to inject into each request',
265
+ # )
266
+
267
+ public_class_method def self.inject_additional_http_headers(opts = {})
268
+ zap_obj = opts[:zap_obj]
269
+ api_key = zap_obj[:api_key].to_s.scrub
270
+ target_regex = opts[:target_regex]
271
+ raise 'ERROR: target_regex must be provided' if target_regex.nil?
272
+
273
+ headers = opts[:headers] ||= {}
274
+ raise 'ERROR: headers must be provided' if headers.empty? || !headers.is_a?(Hash)
275
+
276
+ replacer_resp_arr = []
277
+ headers.each_key do |header_key|
278
+ params = {
279
+ apikey: api_key,
280
+ description: header_key,
281
+ enabled: true,
282
+ matchType: 'REQ_HEADER',
283
+ matchRegex: false,
284
+ matchString: header_key,
285
+ replacement: "#{header_key}: #{headers[header_key]}",
286
+ initiators: '',
287
+ url: target_regex
288
+ }
289
+
290
+ response = zap_rest_call(
291
+ zap_obj: zap_obj,
292
+ rest_call: 'JSON/replacer/action/addRule/',
293
+ params: params
294
+ )
295
+
296
+ json_resp = JSON.parse(response.body, symbolize_names: true)
297
+ replacer_resp_arr.push(json_resp)
298
+ end
299
+
300
+ replacer_resp_arr
301
+ rescue StandardError, SystemExit, Interrupt => e
302
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
226
303
  raise e
227
304
  end
228
305
 
@@ -230,6 +307,7 @@ module PWN
230
307
  # PWN::Plugins::Zaproxy.active_scan(
231
308
  # zap_obj: 'required - zap_obj returned from #open method',
232
309
  # target_url: 'required - url to scan',
310
+ # exclude_paths: 'optional - array of paths to exclude from scan (default: [])',
233
311
  # scan_policy: 'optional - scan policy to use (defaults to Default Policy)'
234
312
  # )
235
313
 
@@ -237,10 +315,23 @@ module PWN
237
315
  zap_obj = opts[:zap_obj]
238
316
  api_key = zap_obj[:api_key].to_s.scrub
239
317
  target_url = opts[:target_url]
240
- if opts[:scan_policy].nil?
241
- scan_policy = 'Default Policy'
242
- else
243
- scan_policy = opts[:scan_policy].to_s.scrub.strip.chomp
318
+ raise 'ERROR: target_url must be provided' if target_url.nil?
319
+
320
+ exclude_paths = opts[:exclude_paths] ||= []
321
+ scan_policy = opts[:scan_policy] ||= 'Default Policy'
322
+
323
+ exclude_paths.each do |exclude_path|
324
+ exclude_path_regex = "#{target_url}#{exclude_path}.*"
325
+ params = {
326
+ apikey: api_key,
327
+ regex: exclude_path_regex
328
+ }
329
+ zap_rest_call(
330
+ zap_obj: zap_obj,
331
+ rest_call: 'JSON/ascan/action/excludeFromScan/',
332
+ params: params
333
+ )
334
+ puts "Excluding #{exclude_path_regex} from Active Scan"
244
335
  end
245
336
 
246
337
  # TODO: Implement adding target_url to scope so that inScopeOnly can be changed to true
@@ -279,17 +370,17 @@ module PWN
279
370
  break if status == 100
280
371
  end
281
372
  rescue StandardError, SystemExit, Interrupt => e
282
- stop(zap_obj) unless zap_obj.nil?
373
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
283
374
  raise e
284
375
  end
285
376
 
286
377
  # Supported Method Parameters::
287
- # PWN::Plugins::Zaproxy.alerts(
378
+ # PWN::Plugins::Zaproxy.get_alerts(
288
379
  # zap_obj: 'required - zap_obj returned from #open method',
289
380
  # target_url: 'required - base url to return alerts'
290
381
  # )
291
382
 
292
- public_class_method def self.alerts(opts = {})
383
+ public_class_method def self.get_alerts(opts = {})
293
384
  zap_obj = opts[:zap_obj]
294
385
  api_key = zap_obj[:api_key].to_s.scrub
295
386
  target_url = opts[:target_url]
@@ -307,7 +398,7 @@ module PWN
307
398
 
308
399
  JSON.parse(response.body, symbolize_names: true)
309
400
  rescue StandardError, SystemExit, Interrupt => e
310
- stop(zap_obj) unless zap_obj.nil?
401
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
311
402
  raise e
312
403
  end
313
404
 
@@ -357,7 +448,7 @@ module PWN
357
448
 
358
449
  report_path
359
450
  rescue StandardError, SystemExit, Interrupt => e
360
- stop(zap_obj) unless zap_obj.nil?
451
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
361
452
  raise e
362
453
  end
363
454
 
@@ -391,7 +482,7 @@ module PWN
391
482
  http_method: :get
392
483
  )
393
484
  rescue StandardError, SystemExit, Interrupt => e
394
- stop(zap_obj) unless zap_obj.nil?
485
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
395
486
  raise e
396
487
  end
397
488
 
@@ -423,47 +514,7 @@ module PWN
423
514
  http_method: :get
424
515
  )
425
516
  rescue StandardError, SystemExit, Interrupt => e
426
- stop(zap_obj) unless zap_obj.nil?
427
- raise e
428
- end
429
-
430
- # Supported Method Parameters::
431
- # watir_resp = PWN::Plugins::Zaproxy.request(
432
- # zap_obj: 'required - zap_obj returned from #open method',
433
- # browser_obj: 'required - browser_obj w/ browser_type: :firefox||:headless returned from #open method',
434
- # instruction: 'required - watir instruction to make (e.g. button(text: "Google Search").click)'
435
- # )
436
-
437
- public_class_method def self.request(opts = {})
438
- zap_obj = opts[:zap_obj]
439
- api_key = zap_obj[:api_key].to_s.scrub
440
- this_browser_obj = opts[:browser_obj]
441
- instruction = opts[:instruction].to_s.strip.chomp.scrub
442
-
443
- raise "\nbrowser_obj.class == #{this_browser_obj.class} browser_obj == #{this_browser_obj}\n#{self}.nonblocking_goto only supports browser_obj.class == Watir::Browser" unless this_browser_obj.is_a?(Watir::Browser)
444
- raise "\nthis_browser_obj.driver.browser == #{this_browser_obj.driver.browser}\n#{self}.nonblocking_goto only supports this_browser_obj.driver.browser == :firefox" unless this_browser_obj.driver.browser == :firefox
445
-
446
- timeout = 0
447
- # this_browser_obj.driver.manage.timeouts.implicit_wait = timeout
448
- this_browser_obj.driver.manage.timeouts.page_load = timeout
449
- # this_browser_obj.driver.manage.timeouts.script_timeout = timeout
450
-
451
- watir_resp = this_browser_obj.instance_eval(instruction)
452
- rescue Timeout::Error
453
- sleep 0.9
454
- request_content = zap_rest_call(
455
- zap_obj: zap_obj,
456
- rest_call: "JSON/break/view/httpMessage/?zapapiformat=JSON&apikey=#{api_key}",
457
- http_method: :get
458
- ).body
459
-
460
- # Now set all the timeouts back to default:
461
- # this_browser_obj.driver.manage.timeouts.implicit_wait = b.driver.capabilities[:implicit_timeout]
462
- this_browser_obj.driver.manage.timeouts.page_load = this_browser_obj.driver.capabilities[:page_load_timeout]
463
- # this_browser_obj.driver.manage.timeouts.script_timeout = b.driver.capabilities[:script_timeout]
464
-
465
- request_content
466
- rescue StandardError => e
517
+ stop(zap_obj: zap_obj) unless zap_obj.nil?
467
518
  raise e
468
519
  end
469
520
 
@@ -475,10 +526,9 @@ module PWN
475
526
  public_class_method def self.stop(opts = {})
476
527
  zap_obj = opts[:zap_obj]
477
528
  api_key = zap_obj[:api_key]
478
- browser_obj = zap_obj[:zap_browser]
479
- rest_browser = zap_obj[:rest_browser]
529
+ browser_obj = zap_obj[:mitm_browser]
480
530
 
481
- browser_obj = PWN::Plugins::TransparentBrowser.close(browser_obj: browser_obj)
531
+ PWN::Plugins::TransparentBrowser.close(browser_obj: browser_obj)
482
532
 
483
533
  params = { apikey: api_key }
484
534
  zap_rest_call(
@@ -489,7 +539,6 @@ module PWN
489
539
 
490
540
  zap_obj = nil
491
541
  rescue StandardError, SystemExit, Interrupt => e
492
- stop(zap_obj) unless zap_obj.nil?
493
542
  raise e
494
543
  end
495
544
 
@@ -522,13 +571,26 @@ module PWN
522
571
  openapi_spec: 'required - path to OpenAPI JSON or YAML spec file'
523
572
  )
524
573
 
574
+ #{self}.add_to_scope(
575
+ zap_obj: 'required - zap_obj returned from #open method',
576
+ target_regex: 'required - url regex to add to scope (e.g. https://test.domain.local.*)',
577
+ context_name: 'optional - context name to add target_regex to (defaults to Default Context)'
578
+ )
579
+
580
+ #{self}.inject_additional_http_headers(
581
+ zap_obj: 'required - zap_obj returned from #open method',
582
+ target_regex: 'required - url regex to inject headers into (e.g. https://test.domain.local.*)',
583
+ headers: 'required - hash of additional headers to inject into each request'
584
+ )
585
+
525
586
  #{self}.active_scan(
526
587
  zap_obj: 'required - zap_obj returned from #open method'
527
588
  target_url: 'required - url to scan',
589
+ exclude_paths: 'optional - array of paths to exclude from scan (default: [])',
528
590
  scan_policy: 'optional - scan policy to use (defaults to Default Policy)'
529
591
  )
530
592
 
531
- json_alerts = #{self}.alerts(
593
+ json_alerts = #{self}.get_alerts(
532
594
  zap_obj: 'required - zap_obj returned from #open method'
533
595
  target_url: 'required - base url to return alerts'
534
596
  )
@@ -546,10 +608,10 @@ module PWN
546
608
  enabled: 'optional - boolean (defaults to true)'
547
609
  )
548
610
 
549
- watir_resp = #{self}.request(
611
+ #{self}.tamper(
550
612
  zap_obj: 'required - zap_obj returned from #open method',
551
- browser_obj: 'required - browser_obj w/ browser_type: :firefox||:headless returned from #open method',
552
- instruction: 'required - watir instruction to make (e.g. button(text: \"Google Search\").click)'
613
+ domain: 'required - FQDN to tamper (e.g. test.domain.local)',
614
+ enabled: 'optional - boolean (defaults to true)'
553
615
  )
554
616
 
555
617
  #{self}.stop(
data/lib/pwn/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module PWN
4
- VERSION = '0.5.401'
4
+ VERSION = '0.5.403'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: pwn
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.401
4
+ version: 0.5.403
5
5
  platform: ruby
6
6
  authors:
7
7
  - 0day Inc.