Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(1144)

Side by Side Diff: chrome/browser/extensions/api/web_request/web_request_api.cc

Issue 10694055: Add read-only access to POST data for webRequest's onBeforeRequest (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Adding an example value of formData to the docs Created 8 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "chrome/browser/extensions/api/web_request/web_request_api.h" 5 #include "chrome/browser/extensions/api/web_request/web_request_api.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 8
9 #include "base/bind.h" 9 #include "base/bind.h"
10 #include "base/json/json_writer.h" 10 #include "base/json/json_writer.h"
11 #include "base/metrics/histogram.h" 11 #include "base/metrics/histogram.h"
12 #include "base/string_number_conversions.h" 12 #include "base/string_number_conversions.h"
13 #include "base/string_util.h" 13 #include "base/string_util.h"
14 #include "base/time.h" 14 #include "base/time.h"
15 #include "base/utf_string_conversions.h" 15 #include "base/utf_string_conversions.h"
16 #include "base/values.h" 16 #include "base/values.h"
17 #include "chrome/browser/browser_process.h" 17 #include "chrome/browser/browser_process.h"
18 #include "chrome/browser/chrome_content_browser_client.h" 18 #include "chrome/browser/chrome_content_browser_client.h"
19 #include "chrome/browser/extensions/api/declarative_webrequest/webrequest_rule.h " 19 #include "chrome/browser/extensions/api/declarative_webrequest/webrequest_rule.h "
20 #include "chrome/browser/extensions/api/declarative_webrequest/webrequest_rules_ registry.h" 20 #include "chrome/browser/extensions/api/declarative_webrequest/webrequest_rules_ registry.h"
21 #include "chrome/browser/extensions/api/web_navigation/web_navigation_api_helper s.h" 21 #include "chrome/browser/extensions/api/web_navigation/web_navigation_api_helper s.h"
22 #include "chrome/browser/extensions/api/web_request/post_data_parser.h"
22 #include "chrome/browser/extensions/api/web_request/web_request_api_constants.h" 23 #include "chrome/browser/extensions/api/web_request/web_request_api_constants.h"
23 #include "chrome/browser/extensions/api/web_request/web_request_api_helpers.h" 24 #include "chrome/browser/extensions/api/web_request/web_request_api_helpers.h"
24 #include "chrome/browser/extensions/api/web_request/web_request_time_tracker.h" 25 #include "chrome/browser/extensions/api/web_request/web_request_time_tracker.h"
25 #include "chrome/browser/extensions/extension_event_router.h" 26 #include "chrome/browser/extensions/extension_event_router.h"
26 #include "chrome/browser/extensions/extension_info_map.h" 27 #include "chrome/browser/extensions/extension_info_map.h"
27 #include "chrome/browser/extensions/extension_prefs.h" 28 #include "chrome/browser/extensions/extension_prefs.h"
28 #include "chrome/browser/extensions/extension_service.h" 29 #include "chrome/browser/extensions/extension_service.h"
29 #include "chrome/browser/extensions/extension_tab_id_map.h" 30 #include "chrome/browser/extensions/extension_tab_id_map.h"
30 #include "chrome/browser/profiles/profile.h" 31 #include "chrome/browser/profiles/profile.h"
31 #include "chrome/browser/profiles/profile_manager.h" 32 #include "chrome/browser/profiles/profile_manager.h"
32 #include "chrome/browser/renderer_host/chrome_render_message_filter.h" 33 #include "chrome/browser/renderer_host/chrome_render_message_filter.h"
33 #include "chrome/browser/renderer_host/web_cache_manager.h" 34 #include "chrome/browser/renderer_host/web_cache_manager.h"
34 #include "chrome/common/extensions/extension.h" 35 #include "chrome/common/extensions/extension.h"
35 #include "chrome/common/extensions/extension_constants.h" 36 #include "chrome/common/extensions/extension_constants.h"
36 #include "chrome/common/extensions/extension_error_utils.h" 37 #include "chrome/common/extensions/extension_error_utils.h"
37 #include "chrome/common/extensions/extension_messages.h" 38 #include "chrome/common/extensions/extension_messages.h"
38 #include "chrome/common/extensions/url_pattern.h" 39 #include "chrome/common/extensions/url_pattern.h"
39 #include "chrome/common/url_constants.h" 40 #include "chrome/common/url_constants.h"
40 #include "content/public/browser/browser_message_filter.h" 41 #include "content/public/browser/browser_message_filter.h"
41 #include "content/public/browser/browser_thread.h" 42 #include "content/public/browser/browser_thread.h"
42 #include "content/public/browser/render_process_host.h" 43 #include "content/public/browser/render_process_host.h"
43 #include "content/public/browser/resource_request_info.h" 44 #include "content/public/browser/resource_request_info.h"
44 #include "googleurl/src/gurl.h" 45 #include "googleurl/src/gurl.h"
45 #include "grit/generated_resources.h" 46 #include "grit/generated_resources.h"
46 #include "net/base/auth.h" 47 #include "net/base/auth.h"
47 #include "net/base/net_errors.h" 48 #include "net/base/net_errors.h"
49 #include "net/base/upload_data.h"
48 #include "net/http/http_response_headers.h" 50 #include "net/http/http_response_headers.h"
49 #include "net/url_request/url_request.h" 51 #include "net/url_request/url_request.h"
50 #include "ui/base/l10n/l10n_util.h" 52 #include "ui/base/l10n/l10n_util.h"
51 53
52 using content::BrowserMessageFilter; 54 using content::BrowserMessageFilter;
53 using content::BrowserThread; 55 using content::BrowserThread;
54 using content::ResourceRequestInfo; 56 using content::ResourceRequestInfo;
55 using extensions::Extension; 57 using extensions::Extension;
56 58
57 using extensions::web_navigation_api_helpers::GetFrameId; 59 using extensions::web_navigation_api_helpers::GetFrameId;
(...skipping 11 matching lines...) Expand all
69 keys::kOnCompleted, 71 keys::kOnCompleted,
70 keys::kOnErrorOccurred, 72 keys::kOnErrorOccurred,
71 keys::kOnSendHeaders, 73 keys::kOnSendHeaders,
72 keys::kOnAuthRequired, 74 keys::kOnAuthRequired,
73 keys::kOnResponseStarted, 75 keys::kOnResponseStarted,
74 keys::kOnHeadersReceived, 76 keys::kOnHeadersReceived,
75 }; 77 };
76 78
77 #define ARRAYEND(array) (array + arraysize(array)) 79 #define ARRAYEND(array) (array + arraysize(array))
78 80
81 // Returns the frame ID as it will be passed to the extension:
82 // 0 if the navigation happens in the main frame, or the frame ID
83 // modulo 32 bits otherwise.
84 // Keep this in sync with the GetFrameId() function in
85 // extension_webnavigation_api.cc.
86 int GetFrameId(bool is_main_frame, int64 frame_id) {
87 return is_main_frame ? 0 : static_cast<int>(frame_id);
88 }
89
79 bool IsWebRequestEvent(const std::string& event_name) { 90 bool IsWebRequestEvent(const std::string& event_name) {
80 return std::find(kWebRequestEvents, ARRAYEND(kWebRequestEvents), 91 return std::find(kWebRequestEvents, ARRAYEND(kWebRequestEvents),
81 event_name) != ARRAYEND(kWebRequestEvents); 92 event_name) != ARRAYEND(kWebRequestEvents);
82 } 93 }
83 94
84 // Returns whether |request| has been triggered by an extension in 95 // Returns whether |request| has been triggered by an extension in
85 // |extension_info_map|. 96 // |extension_info_map|.
86 bool IsRequestFromExtension(const net::URLRequest* request, 97 bool IsRequestFromExtension(const net::URLRequest* request,
87 const ExtensionInfoMap* extension_info_map) { 98 const ExtensionInfoMap* extension_info_map) {
88 // |extension_info_map| is NULL for system-level requests. 99 // |extension_info_map| is NULL for system-level requests.
(...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after
149 base::Uint64ToString(request->identifier())); 160 base::Uint64ToString(request->identifier()));
150 out->SetString(keys::kUrlKey, request->url().spec()); 161 out->SetString(keys::kUrlKey, request->url().spec());
151 out->SetString(keys::kMethodKey, request->method()); 162 out->SetString(keys::kMethodKey, request->method());
152 out->SetInteger(keys::kFrameIdKey, frame_id_for_extension); 163 out->SetInteger(keys::kFrameIdKey, frame_id_for_extension);
153 out->SetInteger(keys::kParentFrameIdKey, parent_frame_id_for_extension); 164 out->SetInteger(keys::kParentFrameIdKey, parent_frame_id_for_extension);
154 out->SetInteger(keys::kTabIdKey, tab_id); 165 out->SetInteger(keys::kTabIdKey, tab_id);
155 out->SetString(keys::kTypeKey, helpers::ResourceTypeToString(resource_type)); 166 out->SetString(keys::kTypeKey, helpers::ResourceTypeToString(resource_type));
156 out->SetDouble(keys::kTimeStampKey, base::Time::Now().ToDoubleT() * 1000); 167 out->SetDouble(keys::kTimeStampKey, base::Time::Now().ToDoubleT() * 1000);
157 } 168 }
158 169
170 // Takes |dictionary| of <string, list of strings> pairs, and gets the list
171 // for |key|, creating it if necessary.
172 ListValue* GetOrCreateList(DictionaryValue* dictionary,
173 const std::string& key) {
174 ListValue* list = NULL;
175 if (!dictionary->GetList(key, &list)) {
176 list = new ListValue();
177 dictionary->Set(key, list);
178 }
179 return list;
180 }
181
182 // Extracts the POST data from |request| and writes the data into |out|.
183 // This can be expensive, so it's separated from ExtractRequestInfo().
184 // Contract: request->method() == "POST"
185 void ExtractRequestInfoPost(net::URLRequest* request, DictionaryValue* out) {
186 const std::vector<net::UploadData::Element>* elements =
187 request->get_upload()->elements();
188 scoped_ptr<extensions::PostDataParser> parser =
189 extensions::PostDataParser::CreatePostDataParser(request);
190 if (parser.get() == NULL) {
191 // No parser means most probably unsupported form encoding.
192 return;
193 }
194 scoped_ptr<DictionaryValue> post_data(new DictionaryValue());
Matt Perry 2012/07/23 21:19:01 The rest of this function seems like it should be
vabr (Chromium) 2012/07/30 16:05:57 Fair point, I tried to move as much as I felt is i
195 scoped_ptr<DictionaryValue> form_data(new DictionaryValue());
196 std::vector<net::UploadData::Element>::const_iterator element;
197 bool data_valid = true;
198 for (element = elements->begin();
199 data_valid && element != elements->end(); ++element) {
200 if (element->type() != net::UploadData::TYPE_BYTES) {
201 // We do not handle data including blobs or chunks.
202 if (element->type() != net::UploadData::TYPE_FILE)
203 data_valid = false;
204 continue;
205 }
206 if (!parser->SetSource(&(element->bytes()))) continue;
207 extensions::PostDataParser::Result result;
208 while (parser->GetNextPair(&result)) {
209 GetOrCreateList(form_data.get(), result.get_key())->Append(
210 new StringValue(result.get_val()));
211 }
212 }
213 if (data_valid && parser->AllDataReadOK())
214 post_data->Set(keys::kFormDataKey, form_data.release());
215 out->Set(keys::kPostDataKey, post_data.release());
216 }
217
159 // Converts a HttpHeaders dictionary to a |name|, |value| pair. Returns 218 // Converts a HttpHeaders dictionary to a |name|, |value| pair. Returns
160 // true if successful. 219 // true if successful.
161 bool FromHeaderDictionary(const DictionaryValue* header_value, 220 bool FromHeaderDictionary(const DictionaryValue* header_value,
162 std::string* name, 221 std::string* name,
163 std::string* value) { 222 std::string* value) {
164 if (!header_value->GetString(keys::kHeaderNameKey, name)) 223 if (!header_value->GetString(keys::kHeaderNameKey, name))
165 return false; 224 return false;
166 225
167 // We require either a "value" or a "binaryValue" entry. 226 // We require either a "value" or a "binaryValue" entry.
168 if (!(header_value->HasKey(keys::kHeaderValueKey) ^ 227 if (!(header_value->HasKey(keys::kHeaderValueKey) ^
(...skipping 232 matching lines...) Expand 10 before | Expand all | Expand 10 after
401 return false; 460 return false;
402 461
403 if (str == "requestHeaders") 462 if (str == "requestHeaders")
404 *extra_info_spec |= REQUEST_HEADERS; 463 *extra_info_spec |= REQUEST_HEADERS;
405 else if (str == "responseHeaders") 464 else if (str == "responseHeaders")
406 *extra_info_spec |= RESPONSE_HEADERS; 465 *extra_info_spec |= RESPONSE_HEADERS;
407 else if (str == "blocking") 466 else if (str == "blocking")
408 *extra_info_spec |= BLOCKING; 467 *extra_info_spec |= BLOCKING;
409 else if (str == "asyncBlocking") 468 else if (str == "asyncBlocking")
410 *extra_info_spec |= ASYNC_BLOCKING; 469 *extra_info_spec |= ASYNC_BLOCKING;
470 else if (str == "requestPostData")
471 *extra_info_spec |= REQUEST_POST_DATA;
411 else 472 else
412 return false; 473 return false;
413 474
414 // BLOCKING and ASYNC_BLOCKING are mutually exclusive. 475 // BLOCKING and ASYNC_BLOCKING are mutually exclusive.
415 if ((*extra_info_spec & BLOCKING) && (*extra_info_spec & ASYNC_BLOCKING)) 476 if ((*extra_info_spec & BLOCKING) && (*extra_info_spec & ASYNC_BLOCKING))
416 return false; 477 return false;
417 } 478 }
418 return true; 479 return true;
419 } 480 }
420 481
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after
486 547
487 int extra_info_spec = 0; 548 int extra_info_spec = 0;
488 std::vector<const EventListener*> listeners = 549 std::vector<const EventListener*> listeners =
489 GetMatchingListeners(profile, extension_info_map, keys::kOnBeforeRequest, 550 GetMatchingListeners(profile, extension_info_map, keys::kOnBeforeRequest,
490 request, &extra_info_spec); 551 request, &extra_info_spec);
491 if (!listeners.empty() && 552 if (!listeners.empty() &&
492 !GetAndSetSignaled(request->identifier(), kOnBeforeRequest)) { 553 !GetAndSetSignaled(request->identifier(), kOnBeforeRequest)) {
493 ListValue args; 554 ListValue args;
494 DictionaryValue* dict = new DictionaryValue(); 555 DictionaryValue* dict = new DictionaryValue();
495 ExtractRequestInfo(request, dict); 556 ExtractRequestInfo(request, dict);
557 if (extra_info_spec & ExtraInfoSpec::REQUEST_POST_DATA &&
558 request->method() == "POST")
559 ExtractRequestInfoPost(request, dict);
496 args.Append(dict); 560 args.Append(dict);
497 561
498 initialize_blocked_requests |= 562 initialize_blocked_requests |=
499 DispatchEvent(profile, request, listeners, args); 563 DispatchEvent(profile, request, listeners, args);
500 } 564 }
501 565
502 if (!initialize_blocked_requests) 566 if (!initialize_blocked_requests)
503 return net::OK; // Nobody saw a reason for modifying the request. 567 return net::OK; // Nobody saw a reason for modifying the request.
504 568
505 blocked_requests_[request->identifier()].event = kOnBeforeRequest; 569 blocked_requests_[request->identifier()].event = kOnBeforeRequest;
(...skipping 1280 matching lines...) Expand 10 before | Expand all | Expand 10 after
1786 } else if ((*it)->name().find("AdBlock") != std::string::npos) { 1850 } else if ((*it)->name().find("AdBlock") != std::string::npos) {
1787 adblock = true; 1851 adblock = true;
1788 } else { 1852 } else {
1789 other = true; 1853 other = true;
1790 } 1854 }
1791 } 1855 }
1792 } 1856 }
1793 1857
1794 host->Send(new ExtensionMsg_UsingWebRequestAPI(adblock, adblock_plus, other)); 1858 host->Send(new ExtensionMsg_UsingWebRequestAPI(adblock, adblock_plus, other));
1795 } 1859 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698