OLD | NEW |
---|---|
1 // Copyright 2017 The Chromium Authors. All rights reserved. | 1 // Copyright 2017 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 #include "components/safe_browsing/password_protection/password_protection_reque st.h" | 4 #include "components/safe_browsing/password_protection/password_protection_reque st.h" |
5 | 5 |
6 #include "base/memory/ptr_util.h" | 6 #include "base/memory/ptr_util.h" |
7 #include "base/memory/weak_ptr.h" | 7 #include "base/memory/weak_ptr.h" |
8 #include "base/metrics/histogram_macros.h" | 8 #include "base/metrics/histogram_macros.h" |
9 #include "components/data_use_measurement/core/data_use_user_data.h" | 9 #include "components/data_use_measurement/core/data_use_user_data.h" |
10 #include "content/public/browser/browser_thread.h" | 10 #include "components/safe_browsing_db/database_manager.h" |
11 #include "net/base/escape.h" | 11 #include "net/base/escape.h" |
12 #include "net/base/load_flags.h" | 12 #include "net/base/load_flags.h" |
13 #include "net/base/url_util.h" | 13 #include "net/base/url_util.h" |
14 #include "net/http/http_status_code.h" | 14 #include "net/http/http_status_code.h" |
15 | 15 |
16 using content::BrowserThread; | 16 using content::BrowserThread; |
17 | 17 |
18 namespace safe_browsing { | 18 namespace safe_browsing { |
Nathan Parker
2017/04/18 23:07:26
Maybe it'd be good to have a state diagram on what
Jialiu Lin
2017/04/19 00:21:14
Added a flow diagram in the .h file.
| |
19 | 19 |
20 PasswordProtectionRequest::PasswordProtectionRequest( | 20 PasswordProtectionRequest::PasswordProtectionRequest( |
21 const GURL& main_frame_url, | 21 const GURL& main_frame_url, |
22 LoginReputationClientRequest::TriggerType type, | 22 LoginReputationClientRequest::TriggerType type, |
23 bool is_extended_reporting, | 23 std::unique_ptr<PasswordProtectionFrameList> pending_password_frames, |
24 bool is_incognito, | |
25 base::WeakPtr<PasswordProtectionService> pps, | 24 base::WeakPtr<PasswordProtectionService> pps, |
26 int request_timeout_in_ms) | 25 int request_timeout_in_ms) |
27 : main_frame_url_(main_frame_url), | 26 : main_frame_url_(main_frame_url), |
28 request_type_(type), | 27 request_type_(type), |
29 is_extended_reporting_(is_extended_reporting), | 28 pending_password_frames_(std::move(pending_password_frames)), |
30 is_incognito_(is_incognito), | |
31 password_protection_service_(pps), | 29 password_protection_service_(pps), |
30 database_manager_(password_protection_service_->database_manager()), | |
32 request_timeout_in_ms_(request_timeout_in_ms), | 31 request_timeout_in_ms_(request_timeout_in_ms), |
33 weakptr_factory_(this) { | 32 weakptr_factory_(this) { |
34 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 33 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
35 } | 34 } |
36 | 35 |
37 PasswordProtectionRequest::~PasswordProtectionRequest() { | 36 PasswordProtectionRequest::~PasswordProtectionRequest() { |
38 weakptr_factory_.InvalidateWeakPtrs(); | 37 weakptr_factory_.InvalidateWeakPtrs(); |
39 } | 38 } |
40 | 39 |
41 void PasswordProtectionRequest::Start() { | 40 void PasswordProtectionRequest::Start() { |
42 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 41 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
43 // Initially we only send ping for Safe Browsing Extended Reporting users when | 42 // Initially we only send ping for Safe Browsing Extended Reporting users when |
44 // they are not in incognito mode. We may loose these conditions later. | 43 // they are not in incognito mode. We may loose these conditions later. |
45 if (is_incognito_) { | 44 if (password_protection_service_->IsIncognito()) { |
46 Finish(RequestOutcome::INCOGNITO, nullptr); | 45 Finish(RequestOutcome::INCOGNITO, nullptr); |
47 return; | 46 return; |
48 } | 47 } |
49 if (!is_extended_reporting_) { | 48 if (!password_protection_service_->IsExtendedReporting()) { |
50 Finish(RequestOutcome::NO_EXTENDED_REPORTING, nullptr); | 49 Finish(RequestOutcome::NO_EXTENDED_REPORTING, nullptr); |
51 return; | 50 return; |
52 } | 51 } |
53 | 52 |
54 CheckWhitelistsOnUIThread(); | 53 CheckWhitelistOnUIThread(); |
55 } | 54 } |
56 | 55 |
57 void PasswordProtectionRequest::CheckWhitelistsOnUIThread() { | 56 void PasswordProtectionRequest::CheckWhitelistOnUIThread() { |
58 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 57 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
59 DCHECK(password_protection_service_); | 58 bool* match_whitelist = new bool(false); |
60 | 59 tracker_.PostTaskAndReply( |
61 BrowserThread::PostTask( | 60 BrowserThread::GetTaskRunnerForThread(BrowserThread::IO).get(), FROM_HERE, |
62 BrowserThread::IO, FROM_HERE, | |
63 base::Bind(&PasswordProtectionService::CheckCsdWhitelistOnIOThread, | 61 base::Bind(&PasswordProtectionService::CheckCsdWhitelistOnIOThread, |
64 password_protection_service_, main_frame_url_, | 62 base::Unretained(password_protection_service_.get()), |
65 base::Bind(&PasswordProtectionRequest::OnWhitelistCheckDone, | 63 main_frame_url_, match_whitelist), |
66 GetWeakPtr()))); | 64 base::Bind(&PasswordProtectionRequest::OnWhitelistCheckDone, this, |
65 base::Owned(match_whitelist))); | |
67 } | 66 } |
68 | 67 |
69 void PasswordProtectionRequest::OnWhitelistCheckDone(bool match_whitelist) { | 68 void PasswordProtectionRequest::OnWhitelistCheckDone( |
69 const bool* match_whitelist) { | |
70 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 70 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
71 if (match_whitelist) | 71 if (*match_whitelist) |
72 Finish(RequestOutcome::MATCHED_WHITELIST, nullptr); | 72 Finish(RequestOutcome::MATCHED_WHITELIST, nullptr); |
73 else | 73 else |
74 CheckCachedVerdicts(); | 74 CheckCachedVerdicts(); |
75 } | 75 } |
76 | 76 |
77 void PasswordProtectionRequest::CheckCachedVerdicts() { | 77 void PasswordProtectionRequest::CheckCachedVerdicts() { |
78 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 78 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
79 if (!password_protection_service_) { | 79 if (!password_protection_service_) { |
80 Finish(RequestOutcome::SERVICE_DESTROYED, nullptr); | 80 Finish(RequestOutcome::SERVICE_DESTROYED, nullptr); |
81 return; | 81 return; |
(...skipping 11 matching lines...) Expand all Loading... | |
93 | 93 |
94 void PasswordProtectionRequest::FillRequestProto() { | 94 void PasswordProtectionRequest::FillRequestProto() { |
95 request_proto_ = base::MakeUnique<LoginReputationClientRequest>(); | 95 request_proto_ = base::MakeUnique<LoginReputationClientRequest>(); |
96 request_proto_->set_page_url(main_frame_url_.spec()); | 96 request_proto_->set_page_url(main_frame_url_.spec()); |
97 request_proto_->set_trigger_type(request_type_); | 97 request_proto_->set_trigger_type(request_type_); |
98 request_proto_->set_stored_verdict_cnt( | 98 request_proto_->set_stored_verdict_cnt( |
99 password_protection_service_->GetStoredVerdictCount()); | 99 password_protection_service_->GetStoredVerdictCount()); |
100 LoginReputationClientRequest::Frame* main_frame = | 100 LoginReputationClientRequest::Frame* main_frame = |
101 request_proto_->add_frames(); | 101 request_proto_->add_frames(); |
102 main_frame->set_url(main_frame_url_.spec()); | 102 main_frame->set_url(main_frame_url_.spec()); |
103 main_frame->set_frame_index(0 /* main frame */); | |
104 main_frame->set_has_password_field(true); | |
103 password_protection_service_->FillReferrerChain( | 105 password_protection_service_->FillReferrerChain( |
104 main_frame_url_, -1 /* tab id not available */, main_frame); | 106 main_frame_url_, -1 /* tab id not available */, main_frame); |
105 // TODO(jialiul): Add sub-frame information and password form information. | 107 |
108 // TODO(jialiul): Fill more password form related info based on | |
109 // |password_frame_map_| when Safe Browsing backend is ready to handle these | |
110 // pieces of information. | |
106 } | 111 } |
107 | 112 |
108 void PasswordProtectionRequest::SendRequest() { | 113 void PasswordProtectionRequest::SendRequest() { |
109 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 114 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
110 FillRequestProto(); | 115 FillRequestProto(); |
111 | 116 |
112 std::string serialized_request; | 117 std::string serialized_request; |
113 if (!request_proto_->SerializeToString(&serialized_request)) { | 118 if (!request_proto_->SerializeToString(&serialized_request)) { |
114 Finish(RequestOutcome::REQUEST_MALFORMED, nullptr); | 119 Finish(RequestOutcome::REQUEST_MALFORMED, nullptr); |
115 return; | 120 return; |
(...skipping 16 matching lines...) Expand all Loading... | |
132 fetcher_->Start(); | 137 fetcher_->Start(); |
133 } | 138 } |
134 | 139 |
135 void PasswordProtectionRequest::StartTimeout() { | 140 void PasswordProtectionRequest::StartTimeout() { |
136 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 141 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
137 | 142 |
138 // If request is not done withing 10 seconds, we cancel this request. | 143 // If request is not done withing 10 seconds, we cancel this request. |
139 // The weak pointer used for the timeout will be invalidated (and | 144 // The weak pointer used for the timeout will be invalidated (and |
140 // hence would prevent the timeout) if the check completes on time and | 145 // hence would prevent the timeout) if the check completes on time and |
141 // execution reaches Finish(). | 146 // execution reaches Finish(). |
142 BrowserThread::PostDelayedTask( | 147 BrowserThread::PostDelayedTask( |
Nathan Parker
2017/04/18 23:07:26
Should this use the tracker_ too, so it'll get can
Jialiu Lin
2017/04/19 00:21:14
Since this is posted to the same thread, WeakPtr w
| |
143 BrowserThread::UI, FROM_HERE, | 148 BrowserThread::UI, FROM_HERE, |
144 base::Bind(&PasswordProtectionRequest::Cancel, GetWeakPtr(), true), | 149 base::Bind(&PasswordProtectionRequest::Cancel, GetWeakPtr(), true), |
145 base::TimeDelta::FromMilliseconds(request_timeout_in_ms_)); | 150 base::TimeDelta::FromMilliseconds(request_timeout_in_ms_)); |
146 } | 151 } |
147 | 152 |
148 void PasswordProtectionRequest::OnURLFetchComplete( | 153 void PasswordProtectionRequest::OnURLFetchComplete( |
149 const net::URLFetcher* source) { | 154 const net::URLFetcher* source) { |
150 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 155 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
151 net::URLRequestStatus status = source->GetStatus(); | 156 net::URLRequestStatus status = source->GetStatus(); |
152 const bool is_success = status.is_success(); | 157 const bool is_success = status.is_success(); |
153 const int response_code = source->GetResponseCode(); | 158 const int response_code = source->GetResponseCode(); |
154 | 159 |
155 UMA_HISTOGRAM_SPARSE_SLOWLY( | 160 UMA_HISTOGRAM_SPARSE_SLOWLY( |
156 "PasswordProtection.PasswordProtectionResponseOrErrorCode", | 161 "PasswordProtection.PasswordProtectionResponseOrErrorCode", |
157 is_success ? response_code : status.error()); | 162 is_success ? response_code : status.error()); |
158 | 163 |
159 if (!is_success || net::HTTP_OK != response_code) { | 164 if (!is_success || net::HTTP_OK != response_code) { |
160 Finish(RequestOutcome::FETCH_FAILED, nullptr); | 165 Finish(RequestOutcome::FETCH_FAILED, nullptr); |
161 return; | 166 return; |
162 } | 167 } |
163 | 168 |
164 std::unique_ptr<LoginReputationClientResponse> response = | 169 std::unique_ptr<LoginReputationClientResponse> response = |
165 base::MakeUnique<LoginReputationClientResponse>(); | 170 base::MakeUnique<LoginReputationClientResponse>(); |
166 std::string response_body; | 171 std::string response_body; |
167 bool received_data = source->GetResponseAsString(&response_body); | 172 bool received_data = source->GetResponseAsString(&response_body); |
168 DCHECK(received_data); | 173 DCHECK(received_data); |
169 fetcher_.reset(); // We don't need it anymore. | 174 fetcher_.reset(); // We don't need it anymore. |
170 UMA_HISTOGRAM_TIMES("PasswordProtection.RequestNetworkDuration", | 175 UMA_HISTOGRAM_TIMES("PasswordProtection.RequestNetworkDuration", |
171 base::TimeTicks::Now() - request_start_time_); | 176 base::TimeTicks::Now() - request_start_time_); |
172 if (response->ParseFromString(response_body)) { | 177 if (response->ParseFromString(response_body)) |
173 Finish(RequestOutcome::SUCCEEDED, std::move(response)); | 178 Finish(RequestOutcome::SUCCEEDED, std::move(response)); |
174 } else { | 179 else |
175 Finish(RequestOutcome::RESPONSE_MALFORMED, nullptr); | 180 Finish(RequestOutcome::RESPONSE_MALFORMED, nullptr); |
176 } | |
177 } | 181 } |
178 | 182 |
179 void PasswordProtectionRequest::Finish( | 183 void PasswordProtectionRequest::Finish( |
180 RequestOutcome outcome, | 184 RequestOutcome outcome, |
181 std::unique_ptr<LoginReputationClientResponse> response) { | 185 std::unique_ptr<LoginReputationClientResponse> response) { |
182 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 186 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
187 tracker_.TryCancelAll(); | |
Nathan Parker
2017/04/18 23:07:26
Will this automatically get called in the destruct
Jialiu Lin
2017/04/19 00:21:14
Yes.
The destruction of PasswordProtectionRequest
| |
183 | 188 |
184 UMA_HISTOGRAM_ENUMERATION("PasswordProtection.RequestOutcome", outcome, | 189 UMA_HISTOGRAM_ENUMERATION("PasswordProtection.RequestOutcome", outcome, |
185 RequestOutcome::MAX_OUTCOME); | 190 RequestOutcome::MAX_OUTCOME); |
186 | 191 |
187 if (response) { | 192 if (response) { |
188 switch (request_type_) { | 193 switch (request_type_) { |
189 case LoginReputationClientRequest::UNFAMILIAR_LOGIN_PAGE: | 194 case LoginReputationClientRequest::UNFAMILIAR_LOGIN_PAGE: |
190 UMA_HISTOGRAM_ENUMERATION( | 195 UMA_HISTOGRAM_ENUMERATION( |
191 "PasswordProtection.UnfamiliarLoginPageVerdict", | 196 "PasswordProtection.UnfamiliarLoginPageVerdict", |
192 response->verdict_type(), | 197 response->verdict_type(), |
(...skipping 15 matching lines...) Expand all Loading... | |
208 } | 213 } |
209 | 214 |
210 void PasswordProtectionRequest::Cancel(bool timed_out) { | 215 void PasswordProtectionRequest::Cancel(bool timed_out) { |
211 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 216 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
212 fetcher_.reset(); | 217 fetcher_.reset(); |
213 | 218 |
214 Finish(timed_out ? TIMEDOUT : CANCELED, nullptr); | 219 Finish(timed_out ? TIMEDOUT : CANCELED, nullptr); |
215 } | 220 } |
216 | 221 |
217 } // namespace safe_browsing | 222 } // namespace safe_browsing |
OLD | NEW |