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

Side by Side Diff: chrome/browser/predictors/autocomplete_action_predictor.cc

Issue 9610006: Refactoring, moving and renaming the NetworkActionPredictor. (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: Created 8 years, 9 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/autocomplete/network_action_predictor.h" 5 #include "chrome/browser/predictors/autocomplete_action_predictor.h"
6 6
7 #include <math.h> 7 #include <math.h>
8 8
9 #include <vector> 9 #include <vector>
10 10
11 #include "base/bind.h" 11 #include "base/bind.h"
12 #include "base/i18n/case_conversion.h" 12 #include "base/i18n/case_conversion.h"
13 #include "base/metrics/histogram.h" 13 #include "base/metrics/histogram.h"
14 #include "base/string_util.h" 14 #include "base/string_util.h"
15 #include "base/stringprintf.h" 15 #include "base/stringprintf.h"
16 #include "base/utf_string_conversions.h" 16 #include "base/utf_string_conversions.h"
17 #include "chrome/browser/autocomplete/autocomplete.h" 17 #include "chrome/browser/autocomplete/autocomplete.h"
18 #include "chrome/browser/autocomplete/autocomplete_match.h" 18 #include "chrome/browser/autocomplete/autocomplete_match.h"
19 #include "chrome/browser/autocomplete/network_action_predictor_database.h"
20 #include "chrome/browser/history/history.h" 19 #include "chrome/browser/history/history.h"
21 #include "chrome/browser/history/history_notifications.h" 20 #include "chrome/browser/history/history_notifications.h"
22 #include "chrome/browser/history/in_memory_database.h" 21 #include "chrome/browser/history/in_memory_database.h"
22 #include "chrome/browser/predictors/predictor_database.h"
23 #include "chrome/browser/predictors/predictor_database_factory.h"
23 #include "chrome/browser/prerender/prerender_field_trial.h" 24 #include "chrome/browser/prerender/prerender_field_trial.h"
24 #include "chrome/browser/prerender/prerender_manager.h" 25 #include "chrome/browser/prerender/prerender_manager.h"
25 #include "chrome/browser/prerender/prerender_manager_factory.h" 26 #include "chrome/browser/prerender/prerender_manager_factory.h"
26 #include "chrome/browser/profiles/profile.h" 27 #include "chrome/browser/profiles/profile.h"
27 #include "chrome/common/chrome_notification_types.h" 28 #include "chrome/common/chrome_notification_types.h"
28 #include "chrome/common/guid.h" 29 #include "chrome/common/guid.h"
29 #include "content/public/browser/browser_thread.h" 30 #include "content/public/browser/browser_thread.h"
30 #include "content/public/browser/notification_details.h" 31 #include "content/public/browser/notification_details.h"
31 #include "content/public/browser/notification_service.h" 32 #include "content/public/browser/notification_service.h"
32 #include "content/public/browser/notification_source.h" 33 #include "content/public/browser/notification_source.h"
33 34
34 namespace { 35 namespace {
35 36
36 const float kConfidenceCutoff[] = { 37 const float kConfidenceCutoff[] = {
37 0.8f, 38 0.8f,
38 0.5f 39 0.5f
39 }; 40 };
40 41
41 const size_t kMinimumUserTextLength = 1; 42 const size_t kMinimumUserTextLength = 1;
42 const int kMinimumNumberOfHits = 3; 43 const int kMinimumNumberOfHits = 3;
43 44
44 COMPILE_ASSERT(arraysize(kConfidenceCutoff) == 45 COMPILE_ASSERT(arraysize(kConfidenceCutoff) ==
45 NetworkActionPredictor::LAST_PREDICT_ACTION, 46 predictors::AutocompleteActionPredictor::LAST_PREDICT_ACTION,
46 ConfidenceCutoff_count_mismatch); 47 ConfidenceCutoff_count_mismatch);
47 48
48 enum DatabaseAction { 49 enum DatabaseAction {
49 DATABASE_ACTION_ADD, 50 DATABASE_ACTION_ADD,
50 DATABASE_ACTION_UPDATE, 51 DATABASE_ACTION_UPDATE,
51 DATABASE_ACTION_DELETE_SOME, 52 DATABASE_ACTION_DELETE_SOME,
52 DATABASE_ACTION_DELETE_ALL, 53 DATABASE_ACTION_DELETE_ALL,
53 DATABASE_ACTION_COUNT 54 DATABASE_ACTION_COUNT
54 }; 55 };
55 56
56 } 57 } // namespace
57 58
58 const int NetworkActionPredictor::kMaximumDaysToKeepEntry = 14; 59 namespace predictors {
59 60
60 double NetworkActionPredictor::hit_weight_ = 1.0; 61 const int AutocompleteActionPredictor::kMaximumDaysToKeepEntry = 14;
61 62
62 NetworkActionPredictor::NetworkActionPredictor(Profile* profile) 63 double AutocompleteActionPredictor::hit_weight_ = 1.0;
64
65 AutocompleteActionPredictor::AutocompleteActionPredictor(Profile* profile)
63 : profile_(profile), 66 : profile_(profile),
64 db_(new NetworkActionPredictorDatabase(profile)), 67 db_(PredictorDatabaseFactory::GetForProfile(profile)),
65 initialized_(false) { 68 initialized_(false) {
66 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
67 base::Bind(&NetworkActionPredictorDatabase::Initialize, db_));
68
69 // Request the in-memory database from the history to force it to load so it's 69 // Request the in-memory database from the history to force it to load so it's
70 // available as soon as possible. 70 // available as soon as possible.
71 HistoryService* history_service = 71 HistoryService* history_service =
72 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); 72 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS);
73 if (history_service) 73 if (history_service)
74 history_service->InMemoryDatabase(); 74 history_service->InMemoryDatabase();
75 75
76 // Create local caches using the database as loaded. We will garbage collect 76 // Create local caches using the database as loaded. We will garbage collect
77 // rows from the caches and the database once the history service is 77 // rows from the caches and the database once the history service is
78 // available. 78 // available.
79 std::vector<NetworkActionPredictorDatabase::Row>* rows = 79 std::vector<AutocompleteActionPredictorTable::Row>* rows =
80 new std::vector<NetworkActionPredictorDatabase::Row>(); 80 new std::vector<AutocompleteActionPredictorTable::Row>();
81 content::BrowserThread::PostTaskAndReply( 81 content::BrowserThread::PostTaskAndReply(
82 content::BrowserThread::DB, FROM_HERE, 82 content::BrowserThread::DB, FROM_HERE,
83 base::Bind(&NetworkActionPredictorDatabase::GetAllRows, db_, rows), 83 base::Bind(&AutocompleteActionPredictorTable::GetAllRows,
84 base::Bind(&NetworkActionPredictor::CreateCaches, AsWeakPtr(), 84 db_->autocomplete_table(),
85 rows),
86 base::Bind(&AutocompleteActionPredictor::CreateCaches, AsWeakPtr(),
85 base::Owned(rows))); 87 base::Owned(rows)));
86
87 } 88 }
88 89
89 NetworkActionPredictor::~NetworkActionPredictor() { 90 AutocompleteActionPredictor::~AutocompleteActionPredictor() {
90 } 91 }
91 92
92 void NetworkActionPredictor::RegisterTransitionalMatches( 93 void AutocompleteActionPredictor::RegisterTransitionalMatches(
93 const string16& user_text, 94 const string16& user_text,
94 const AutocompleteResult& result) { 95 const AutocompleteResult& result) {
95 if (user_text.length() < kMinimumUserTextLength) 96 if (user_text.length() < kMinimumUserTextLength)
96 return; 97 return;
97 const string16 lower_user_text(base::i18n::ToLower(user_text)); 98 const string16 lower_user_text(base::i18n::ToLower(user_text));
98 99
99 // Merge this in to an existing match if we already saw |user_text| 100 // Merge this in to an existing match if we already saw |user_text|
100 std::vector<TransitionalMatch>::iterator match_it = 101 std::vector<TransitionalMatch>::iterator match_it =
101 std::find(transitional_matches_.begin(), transitional_matches_.end(), 102 std::find(transitional_matches_.begin(), transitional_matches_.end(),
102 lower_user_text); 103 lower_user_text);
103 104
104 if (match_it == transitional_matches_.end()) { 105 if (match_it == transitional_matches_.end()) {
105 TransitionalMatch transitional_match; 106 TransitionalMatch transitional_match;
106 transitional_match.user_text = lower_user_text; 107 transitional_match.user_text = lower_user_text;
107 match_it = transitional_matches_.insert(transitional_matches_.end(), 108 match_it = transitional_matches_.insert(transitional_matches_.end(),
108 transitional_match); 109 transitional_match);
109 } 110 }
110 111
111 for (AutocompleteResult::const_iterator it = result.begin(); 112 for (AutocompleteResult::const_iterator it = result.begin();
112 it != result.end(); ++it) { 113 it != result.end(); ++it) {
113 if (std::find(match_it->urls.begin(), match_it->urls.end(), 114 if (std::find(match_it->urls.begin(), match_it->urls.end(),
114 it->destination_url) == match_it->urls.end()) { 115 it->destination_url) == match_it->urls.end()) {
115 match_it->urls.push_back(it->destination_url); 116 match_it->urls.push_back(it->destination_url);
116 } 117 }
117 } 118 }
118 } 119 }
119 120
120 void NetworkActionPredictor::ClearTransitionalMatches() { 121 void AutocompleteActionPredictor::ClearTransitionalMatches() {
121 transitional_matches_.clear(); 122 transitional_matches_.clear();
122 } 123 }
123 124
124 // Given a match, return a recommended action. 125 // Given a match, return a recommended action.
125 NetworkActionPredictor::Action NetworkActionPredictor::RecommendAction( 126 AutocompleteActionPredictor::Action
127 AutocompleteActionPredictor::RecommendAction(
dominich 2012/03/06 16:42:13 i think this should be indented?
Shishir 2012/03/14 21:14:37 Done.
126 const string16& user_text, 128 const string16& user_text,
127 const AutocompleteMatch& match) const { 129 const AutocompleteMatch& match) const {
128 bool is_in_db = false; 130 bool is_in_db = false;
129 const double confidence = CalculateConfidence(user_text, match, &is_in_db); 131 const double confidence = CalculateConfidence(user_text, match, &is_in_db);
130 DCHECK(confidence >= 0.0 && confidence <= 1.0); 132 DCHECK(confidence >= 0.0 && confidence <= 1.0);
131 133
132 UMA_HISTOGRAM_BOOLEAN("NetworkActionPredictor.MatchIsInDb", is_in_db); 134 UMA_HISTOGRAM_BOOLEAN("AutocompleteActionPredictor.MatchIsInDb", is_in_db);
133 135
134 if (is_in_db) { 136 if (is_in_db) {
135 // Multiple enties with the same URL are fine as the confidence may be 137 // Multiple enties with the same URL are fine as the confidence may be
136 // different. 138 // different.
137 tracked_urls_.push_back(std::make_pair(match.destination_url, confidence)); 139 tracked_urls_.push_back(std::make_pair(match.destination_url, confidence));
138 UMA_HISTOGRAM_COUNTS_100("NetworkActionPredictor.Confidence", 140 UMA_HISTOGRAM_COUNTS_100("AutocompleteActionPredictor.Confidence",
139 confidence * 100); 141 confidence * 100);
140 } 142 }
141 143
142 // Map the confidence to an action. 144 // Map the confidence to an action.
143 Action action = ACTION_NONE; 145 Action action = ACTION_NONE;
144 for (int i = 0; i < LAST_PREDICT_ACTION; ++i) { 146 for (int i = 0; i < LAST_PREDICT_ACTION; ++i) {
145 if (confidence >= kConfidenceCutoff[i]) { 147 if (confidence >= kConfidenceCutoff[i]) {
146 action = static_cast<Action>(i); 148 action = static_cast<Action>(i);
147 break; 149 break;
148 } 150 }
149 } 151 }
150 152
151 // Downgrade prerender to preconnect if this is a search match or if omnibox 153 // Downgrade prerender to preconnect if this is a search match or if omnibox
152 // prerendering is disabled. 154 // prerendering is disabled.
153 if (action == ACTION_PRERENDER && !prerender::IsOmniboxEnabled(profile_)) 155 if (action == ACTION_PRERENDER && !prerender::IsOmniboxEnabled(profile_))
154 action = ACTION_PRECONNECT; 156 action = ACTION_PRECONNECT;
155 157
156 return action; 158 return action;
157 } 159 }
158 160
159 // Return true if the suggestion type warrants a TCP/IP preconnection. 161 // Return true if the suggestion type warrants a TCP/IP preconnection.
160 // i.e., it is now quite likely that the user will select the related domain. 162 // i.e., it is now quite likely that the user will select the related domain.
161 // static 163 // static
162 bool NetworkActionPredictor::IsPreconnectable(const AutocompleteMatch& match) { 164 bool AutocompleteActionPredictor::IsPreconnectable(
165 const AutocompleteMatch& match) {
163 switch (match.type) { 166 switch (match.type) {
164 // Matches using the user's default search engine. 167 // Matches using the user's default search engine.
165 case AutocompleteMatch::SEARCH_WHAT_YOU_TYPED: 168 case AutocompleteMatch::SEARCH_WHAT_YOU_TYPED:
166 case AutocompleteMatch::SEARCH_HISTORY: 169 case AutocompleteMatch::SEARCH_HISTORY:
167 case AutocompleteMatch::SEARCH_SUGGEST: 170 case AutocompleteMatch::SEARCH_SUGGEST:
168 // A match that uses a non-default search engine (e.g. for tab-to-search). 171 // A match that uses a non-default search engine (e.g. for tab-to-search).
169 case AutocompleteMatch::SEARCH_OTHER_ENGINE: 172 case AutocompleteMatch::SEARCH_OTHER_ENGINE:
170 return true; 173 return true;
171 174
172 default: 175 default:
173 return false; 176 return false;
174 } 177 }
175 } 178 }
176 179
177 void NetworkActionPredictor::Shutdown() { 180 void AutocompleteActionPredictor::Shutdown() {
dominich 2012/03/06 16:42:13 note for dominic: check OnPredictorDestroyed is be
178 db_->OnPredictorDestroyed();
179 } 181 }
180 182
181 void NetworkActionPredictor::Observe( 183 void AutocompleteActionPredictor::Observe(
182 int type, 184 int type,
183 const content::NotificationSource& source, 185 const content::NotificationSource& source,
184 const content::NotificationDetails& details) { 186 const content::NotificationDetails& details) {
185 switch (type) { 187 switch (type) {
186 case chrome::NOTIFICATION_HISTORY_URLS_DELETED: { 188 case chrome::NOTIFICATION_HISTORY_URLS_DELETED: {
187 DCHECK(initialized_); 189 DCHECK(initialized_);
188 const content::Details<const history::URLsDeletedDetails> 190 const content::Details<const history::URLsDeletedDetails>
189 urls_deleted_details = 191 urls_deleted_details =
190 content::Details<const history::URLsDeletedDetails>(details); 192 content::Details<const history::URLsDeletedDetails>(details);
191 if (urls_deleted_details->all_history) 193 if (urls_deleted_details->all_history)
(...skipping 24 matching lines...) Expand all
216 content::Source<Profile>(profile_)); 218 content::Source<Profile>(profile_));
217 break; 219 break;
218 } 220 }
219 221
220 default: 222 default:
221 NOTREACHED() << "Unexpected notification observed."; 223 NOTREACHED() << "Unexpected notification observed.";
222 break; 224 break;
223 } 225 }
224 } 226 }
225 227
226 void NetworkActionPredictor::OnOmniboxOpenedUrl(const AutocompleteLog& log) { 228 void AutocompleteActionPredictor::OnOmniboxOpenedUrl(
229 const AutocompleteLog& log) {
227 if (log.text.length() < kMinimumUserTextLength) 230 if (log.text.length() < kMinimumUserTextLength)
228 return; 231 return;
229 232
230 const AutocompleteMatch& match = log.result.match_at(log.selected_index); 233 const AutocompleteMatch& match = log.result.match_at(log.selected_index);
231 234
232 UMA_HISTOGRAM_BOOLEAN( 235 UMA_HISTOGRAM_BOOLEAN(
233 StringPrintf("Prerender.OmniboxNavigationsCouldPrerender_%.1f", 236 StringPrintf("Prerender.OmniboxNavigationsCouldPrerender_%.1f",
234 get_hit_weight()).c_str(), 237 get_hit_weight()).c_str(),
235 prerender::IsOmniboxEnabled(profile_)); 238 prerender::IsOmniboxEnabled(profile_));
236 239
237 const GURL& opened_url = match.destination_url; 240 const GURL& opened_url = match.destination_url;
238 241
239 // If the Omnibox triggered a prerender but the URL doesn't match the one the 242 // If the Omnibox triggered a prerender but the URL doesn't match the one the
240 // user is navigating to, cancel the prerender. 243 // user is navigating to, cancel the prerender.
241 prerender::PrerenderManager* prerender_manager = 244 prerender::PrerenderManager* prerender_manager =
242 prerender::PrerenderManagerFactory::GetForProfile(profile_); 245 prerender::PrerenderManagerFactory::GetForProfile(profile_);
243 // |prerender_manager| can be NULL in incognito mode or if prerendering is 246 // |prerender_manager| can be NULL in incognito mode or if prerendering is
244 // otherwise disabled. 247 // otherwise disabled.
245 if (prerender_manager && !prerender_manager->IsPrerendering(opened_url)) 248 if (prerender_manager && !prerender_manager->IsPrerendering(opened_url))
246 prerender_manager->CancelOmniboxPrerenders(); 249 prerender_manager->CancelOmniboxPrerenders();
247 250
248 const string16 lower_user_text(base::i18n::ToLower(log.text)); 251 const string16 lower_user_text(base::i18n::ToLower(log.text));
249 252
250 BeginTransaction();
251 // Traverse transitional matches for those that have a user_text that is a 253 // Traverse transitional matches for those that have a user_text that is a
252 // prefix of |lower_user_text|. 254 // prefix of |lower_user_text|.
253 for (std::vector<TransitionalMatch>::const_iterator it = 255 if (initialized_) {
dominich 2012/03/06 16:42:13 before this is called there's a DCHECK that initia
Shishir 2012/03/14 21:14:37 Removed.
254 transitional_matches_.begin(); it != transitional_matches_.end(); 256 std::vector<AutocompleteActionPredictorTable::Row> rows_to_add;
255 ++it) { 257 std::vector<AutocompleteActionPredictorTable::Row> rows_to_update;
256 if (!StartsWith(lower_user_text, it->user_text, true))
257 continue;
258 258
259 // Add entries to the database for those matches. 259 for (std::vector<TransitionalMatch>::const_iterator it =
260 for (std::vector<GURL>::const_iterator url_it = it->urls.begin(); 260 transitional_matches_.begin(); it != transitional_matches_.end();
261 url_it != it->urls.end(); ++url_it) { 261 ++it) {
262 DCHECK(it->user_text.length() >= kMinimumUserTextLength); 262 if (!StartsWith(lower_user_text, it->user_text, true))
263 const DBCacheKey key = { it->user_text, *url_it }; 263 continue;
264 const bool is_hit = (*url_it == opened_url);
265 264
266 NetworkActionPredictorDatabase::Row row; 265 // Add entries to the database for those matches.
267 row.user_text = key.user_text; 266 for (std::vector<GURL>::const_iterator url_it = it->urls.begin();
268 row.url = key.url; 267 url_it != it->urls.end(); ++url_it) {
268 DCHECK(it->user_text.length() >= kMinimumUserTextLength);
269 const DBCacheKey key = { it->user_text, *url_it };
270 const bool is_hit = (*url_it == opened_url);
269 271
270 DBCacheMap::iterator it = db_cache_.find(key); 272 AutocompleteActionPredictorTable::Row row;
271 if (it == db_cache_.end()) { 273 row.user_text = key.user_text;
272 row.id = guid::GenerateGUID(); 274 row.url = key.url;
273 row.number_of_hits = is_hit ? 1 : 0;
274 row.number_of_misses = is_hit ? 0 : 1;
275 275
276 AddRow(key, row); 276 DBCacheMap::iterator it = db_cache_.find(key);
277 } else { 277 if (it == db_cache_.end()) {
278 DCHECK(db_id_cache_.find(key) != db_id_cache_.end()); 278 row.id = guid::GenerateGUID();
279 row.id = db_id_cache_.find(key)->second; 279 row.number_of_hits = is_hit ? 1 : 0;
280 row.number_of_hits = it->second.number_of_hits + (is_hit ? 1 : 0); 280 row.number_of_misses = is_hit ? 0 : 1;
281 row.number_of_misses = it->second.number_of_misses + (is_hit ? 0 : 1);
282 281
283 UpdateRow(it, row); 282 DBCacheValue value = { row.number_of_hits, row.number_of_misses };
283 db_cache_[key] = value;
284 db_id_cache_[key] = row.id;
285
286 rows_to_add.push_back(row);
287 UMA_HISTOGRAM_ENUMERATION(
288 "AutocompleteActionPredictor.DatabaseAction",
289 DATABASE_ACTION_ADD, DATABASE_ACTION_COUNT);
290 } else {
291 DCHECK(db_id_cache_.find(key) != db_id_cache_.end());
292 row.id = db_id_cache_.find(key)->second;
293 row.number_of_hits = it->second.number_of_hits + (is_hit ? 1 : 0);
294 row.number_of_misses = it->second.number_of_misses + (is_hit ? 0 : 1);
295
296 it->second.number_of_hits = row.number_of_hits;
297 it->second.number_of_misses = row.number_of_misses;
298
299 rows_to_update.push_back(row);
300 UMA_HISTOGRAM_ENUMERATION(
301 "AutocompleteActionPredictor.DatabaseAction",
302 DATABASE_ACTION_UPDATE, DATABASE_ACTION_COUNT);
303 }
284 } 304 }
285 } 305 }
306 if (rows_to_add.size() > 0 || rows_to_update.size() > 0)
307 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
308 base::Bind(&AutocompleteActionPredictorTable::AddAndUpdateRows,
309 db_->autocomplete_table(),
310 rows_to_add,
dominich 2012/03/06 16:42:13 this will cause a full copy of the vectors to be m
Shishir 2012/03/14 21:14:37 Do these vectors get very large? If not it might b
311 rows_to_update));
286 } 312 }
287 CommitTransaction();
288 313
289 ClearTransitionalMatches(); 314 ClearTransitionalMatches();
290 315
291 // Check against tracked urls and log accuracy for the confidence we 316 // Check against tracked urls and log accuracy for the confidence we
292 // predicted. 317 // predicted.
293 for (std::vector<std::pair<GURL, double> >::const_iterator it = 318 for (std::vector<std::pair<GURL, double> >::const_iterator it =
294 tracked_urls_.begin(); it != tracked_urls_.end(); 319 tracked_urls_.begin(); it != tracked_urls_.end();
295 ++it) { 320 ++it) {
296 if (opened_url == it->first) { 321 if (opened_url == it->first) {
297 UMA_HISTOGRAM_COUNTS_100("NetworkActionPredictor.AccurateCount", 322 UMA_HISTOGRAM_COUNTS_100("AutocompleteActionPredictor.AccurateCount",
298 it->second * 100); 323 it->second * 100);
299 } 324 }
300 } 325 }
301 tracked_urls_.clear(); 326 tracked_urls_.clear();
302 } 327 }
303 328
304 void NetworkActionPredictor::DeleteOldIdsFromCaches( 329 void AutocompleteActionPredictor::DeleteOldIdsFromCaches(
305 history::URLDatabase* url_db, 330 history::URLDatabase* url_db,
306 std::vector<NetworkActionPredictorDatabase::Row::Id>* id_list) { 331 std::vector<AutocompleteActionPredictorTable::Row::Id>* id_list) {
307 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 332 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
308 DCHECK(url_db); 333 DCHECK(url_db);
309 DCHECK(id_list); 334 DCHECK(id_list);
310 id_list->clear(); 335 id_list->clear();
311 for (DBCacheMap::iterator it = db_cache_.begin(); it != db_cache_.end();) { 336 for (DBCacheMap::iterator it = db_cache_.begin(); it != db_cache_.end();) {
312 history::URLRow url_row; 337 history::URLRow url_row;
313 338
314 if ((url_db->GetRowForURL(it->first.url, &url_row) == 0) || 339 if ((url_db->GetRowForURL(it->first.url, &url_row) == 0) ||
315 ((base::Time::Now() - url_row.last_visit()).InDays() > 340 ((base::Time::Now() - url_row.last_visit()).InDays() >
316 kMaximumDaysToKeepEntry)) { 341 kMaximumDaysToKeepEntry)) {
317 const DBIdCacheMap::iterator id_it = db_id_cache_.find(it->first); 342 const DBIdCacheMap::iterator id_it = db_id_cache_.find(it->first);
318 DCHECK(id_it != db_id_cache_.end()); 343 DCHECK(id_it != db_id_cache_.end());
319 id_list->push_back(id_it->second); 344 id_list->push_back(id_it->second);
320 db_id_cache_.erase(id_it); 345 db_id_cache_.erase(id_it);
321 db_cache_.erase(it++); 346 db_cache_.erase(it++);
322 } else { 347 } else {
323 ++it; 348 ++it;
324 } 349 }
325 } 350 }
326 } 351 }
327 352
328 void NetworkActionPredictor::DeleteOldEntries(history::URLDatabase* url_db) { 353 void AutocompleteActionPredictor::DeleteOldEntries(
354 history::URLDatabase* url_db) {
329 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 355 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
330 DCHECK(!initialized_); 356 DCHECK(!initialized_);
331 357
332 std::vector<NetworkActionPredictorDatabase::Row::Id> ids_to_delete; 358 std::vector<AutocompleteActionPredictorTable::Row::Id> ids_to_delete;
333 DeleteOldIdsFromCaches(url_db, &ids_to_delete); 359 DeleteOldIdsFromCaches(url_db, &ids_to_delete);
334 360
335 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE, 361 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
336 base::Bind(&NetworkActionPredictorDatabase::DeleteRows, db_, 362 base::Bind(&AutocompleteActionPredictorTable::DeleteRows,
363 db_->autocomplete_table(),
337 ids_to_delete)); 364 ids_to_delete));
338 365
339 // Register for notifications and set the |initialized_| flag. 366 // Register for notifications and set the |initialized_| flag.
340 notification_registrar_.Add(this, chrome::NOTIFICATION_OMNIBOX_OPENED_URL, 367 notification_registrar_.Add(this, chrome::NOTIFICATION_OMNIBOX_OPENED_URL,
341 content::Source<Profile>(profile_)); 368 content::Source<Profile>(profile_));
342 notification_registrar_.Add(this, chrome::NOTIFICATION_HISTORY_URLS_DELETED, 369 notification_registrar_.Add(this, chrome::NOTIFICATION_HISTORY_URLS_DELETED,
343 content::Source<Profile>(profile_)); 370 content::Source<Profile>(profile_));
344 initialized_ = true; 371 initialized_ = true;
345 } 372 }
346 373
347 void NetworkActionPredictor::CreateCaches( 374 void AutocompleteActionPredictor::CreateCaches(
348 std::vector<NetworkActionPredictorDatabase::Row>* rows) { 375 std::vector<AutocompleteActionPredictorTable::Row>* rows) {
349 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI)); 376 CHECK(content::BrowserThread::CurrentlyOn(content::BrowserThread::UI));
350 DCHECK(!initialized_); 377 DCHECK(!initialized_);
351 DCHECK(db_cache_.empty()); 378 DCHECK(db_cache_.empty());
352 DCHECK(db_id_cache_.empty()); 379 DCHECK(db_id_cache_.empty());
353 380
354 for (std::vector<NetworkActionPredictorDatabase::Row>::const_iterator it = 381 for (std::vector<AutocompleteActionPredictorTable::Row>::const_iterator it =
355 rows->begin(); it != rows->end(); ++it) { 382 rows->begin(); it != rows->end(); ++it) {
356 const DBCacheKey key = { it->user_text, it->url }; 383 const DBCacheKey key = { it->user_text, it->url };
357 const DBCacheValue value = { it->number_of_hits, it->number_of_misses }; 384 const DBCacheValue value = { it->number_of_hits, it->number_of_misses };
358 db_cache_[key] = value; 385 db_cache_[key] = value;
359 db_id_cache_[key] = it->id; 386 db_id_cache_[key] = it->id;
360 } 387 }
361 388
362 // If the history service is ready, delete any old or invalid entries. 389 // If the history service is ready, delete any old or invalid entries.
363 HistoryService* history_service = 390 HistoryService* history_service =
364 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); 391 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS);
365 if (!TryDeleteOldEntries(history_service)) { 392 if (!TryDeleteOldEntries(history_service)) {
366 // Wait for the notification that the history service is ready and the URL 393 // Wait for the notification that the history service is ready and the URL
367 // DB is loaded. 394 // DB is loaded.
368 notification_registrar_.Add(this, chrome::NOTIFICATION_HISTORY_LOADED, 395 notification_registrar_.Add(this, chrome::NOTIFICATION_HISTORY_LOADED,
369 content::Source<Profile>(profile_)); 396 content::Source<Profile>(profile_));
370 } 397 }
371 } 398 }
372 399
373 bool NetworkActionPredictor::TryDeleteOldEntries(HistoryService* service) { 400 bool AutocompleteActionPredictor::TryDeleteOldEntries(HistoryService* service) {
374 if (!service) 401 if (!service)
375 return false; 402 return false;
376 403
377 history::URLDatabase* url_db = service->InMemoryDatabase(); 404 history::URLDatabase* url_db = service->InMemoryDatabase();
378 if (!url_db) 405 if (!url_db)
379 return false; 406 return false;
380 407
381 DeleteOldEntries(url_db); 408 DeleteOldEntries(url_db);
382 return true; 409 return true;
383 } 410 }
384 411
385 double NetworkActionPredictor::CalculateConfidence( 412 double AutocompleteActionPredictor::CalculateConfidence(
386 const string16& user_text, 413 const string16& user_text,
387 const AutocompleteMatch& match, 414 const AutocompleteMatch& match,
388 bool* is_in_db) const { 415 bool* is_in_db) const {
389 const DBCacheKey key = { user_text, match.destination_url }; 416 const DBCacheKey key = { user_text, match.destination_url };
390 417
391 *is_in_db = false; 418 *is_in_db = false;
392 if (user_text.length() < kMinimumUserTextLength) 419 if (user_text.length() < kMinimumUserTextLength)
393 return 0.0; 420 return 0.0;
394 421
395 const DBCacheMap::const_iterator iter = db_cache_.find(key); 422 const DBCacheMap::const_iterator iter = db_cache_.find(key);
396 if (iter == db_cache_.end()) 423 if (iter == db_cache_.end())
397 return 0.0; 424 return 0.0;
398 425
399 *is_in_db = true; 426 *is_in_db = true;
400 return CalculateConfidenceForDbEntry(iter); 427 return CalculateConfidenceForDbEntry(iter);
401 } 428 }
402 429
403 double NetworkActionPredictor::CalculateConfidenceForDbEntry( 430 double AutocompleteActionPredictor::CalculateConfidenceForDbEntry(
404 DBCacheMap::const_iterator iter) const { 431 DBCacheMap::const_iterator iter) const {
405 const DBCacheValue& value = iter->second; 432 const DBCacheValue& value = iter->second;
406 if (value.number_of_hits < kMinimumNumberOfHits) 433 if (value.number_of_hits < kMinimumNumberOfHits)
407 return 0.0; 434 return 0.0;
408 435
409 const double number_of_hits = value.number_of_hits * hit_weight_; 436 const double number_of_hits = value.number_of_hits * hit_weight_;
410 return number_of_hits / (number_of_hits + value.number_of_misses); 437 return number_of_hits / (number_of_hits + value.number_of_misses);
411 } 438 }
412 439
413 void NetworkActionPredictor::AddRow( 440 void AutocompleteActionPredictor::AddRow(
414 const DBCacheKey& key, 441 const DBCacheKey& key,
415 const NetworkActionPredictorDatabase::Row& row) { 442 const AutocompleteActionPredictorTable::Row& row) {
416 if (!initialized_) 443 if (!initialized_)
417 return; 444 return;
418 445
419 DBCacheValue value = { row.number_of_hits, row.number_of_misses }; 446 DBCacheValue value = { row.number_of_hits, row.number_of_misses };
420 db_cache_[key] = value; 447 db_cache_[key] = value;
421 db_id_cache_[key] = row.id; 448 db_id_cache_[key] = row.id;
422 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE, 449 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
423 base::Bind(&NetworkActionPredictorDatabase::AddRow, db_, row)); 450 base::Bind(&AutocompleteActionPredictorTable::AddRow,
451 db_->autocomplete_table(),
452 row));
424 453
425 UMA_HISTOGRAM_ENUMERATION("NetworkActionPredictor.DatabaseAction", 454 UMA_HISTOGRAM_ENUMERATION("AutocompleteActionPredictor.DatabaseAction",
426 DATABASE_ACTION_ADD, DATABASE_ACTION_COUNT); 455 DATABASE_ACTION_ADD, DATABASE_ACTION_COUNT);
427 } 456 }
428 457
429 void NetworkActionPredictor::UpdateRow( 458 void AutocompleteActionPredictor::UpdateRow(
430 DBCacheMap::iterator it, 459 DBCacheMap::iterator it,
431 const NetworkActionPredictorDatabase::Row& row) { 460 const AutocompleteActionPredictorTable::Row& row) {
432 if (!initialized_) 461 if (!initialized_)
433 return; 462 return;
434 463
435 DCHECK(it != db_cache_.end()); 464 DCHECK(it != db_cache_.end());
436 it->second.number_of_hits = row.number_of_hits; 465 it->second.number_of_hits = row.number_of_hits;
437 it->second.number_of_misses = row.number_of_misses; 466 it->second.number_of_misses = row.number_of_misses;
438 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE, 467 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
439 base::Bind(&NetworkActionPredictorDatabase::UpdateRow, db_, row)); 468 base::Bind(&AutocompleteActionPredictorTable::UpdateRow,
440 UMA_HISTOGRAM_ENUMERATION("NetworkActionPredictor.DatabaseAction", 469 db_->autocomplete_table(),
470 row));
471 UMA_HISTOGRAM_ENUMERATION("AutocompleteActionPredictor.DatabaseAction",
441 DATABASE_ACTION_UPDATE, DATABASE_ACTION_COUNT); 472 DATABASE_ACTION_UPDATE, DATABASE_ACTION_COUNT);
442 } 473 }
443 474
444 void NetworkActionPredictor::DeleteAllRows() { 475 void AutocompleteActionPredictor::DeleteAllRows() {
445 if (!initialized_) 476 if (!initialized_)
446 return; 477 return;
447 478
448 db_cache_.clear(); 479 db_cache_.clear();
449 db_id_cache_.clear(); 480 db_id_cache_.clear();
450 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE, 481 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
451 base::Bind(&NetworkActionPredictorDatabase::DeleteAllRows, db_)); 482 base::Bind(&AutocompleteActionPredictorTable::DeleteAllRows,
452 UMA_HISTOGRAM_ENUMERATION("NetworkActionPredictor.DatabaseAction", 483 db_->autocomplete_table()));
484 UMA_HISTOGRAM_ENUMERATION("AutocompleteActionPredictor.DatabaseAction",
453 DATABASE_ACTION_DELETE_ALL, DATABASE_ACTION_COUNT); 485 DATABASE_ACTION_DELETE_ALL, DATABASE_ACTION_COUNT);
454 } 486 }
455 487
456 void NetworkActionPredictor::DeleteRowsWithURLs(const std::set<GURL>& urls) { 488 void AutocompleteActionPredictor::DeleteRowsWithURLs(
489 const std::set<GURL>& urls) {
457 if (!initialized_) 490 if (!initialized_)
458 return; 491 return;
459 492
460 std::vector<NetworkActionPredictorDatabase::Row::Id> id_list; 493 std::vector<AutocompleteActionPredictorTable::Row::Id> id_list;
461 494
462 for (DBCacheMap::iterator it = db_cache_.begin(); it != db_cache_.end();) { 495 for (DBCacheMap::iterator it = db_cache_.begin(); it != db_cache_.end();) {
463 if (urls.find(it->first.url) != urls.end()) { 496 if (urls.find(it->first.url) != urls.end()) {
464 const DBIdCacheMap::iterator id_it = db_id_cache_.find(it->first); 497 const DBIdCacheMap::iterator id_it = db_id_cache_.find(it->first);
465 DCHECK(id_it != db_id_cache_.end()); 498 DCHECK(id_it != db_id_cache_.end());
466 id_list.push_back(id_it->second); 499 id_list.push_back(id_it->second);
467 db_id_cache_.erase(id_it); 500 db_id_cache_.erase(id_it);
468 db_cache_.erase(it++); 501 db_cache_.erase(it++);
469 } else { 502 } else {
470 ++it; 503 ++it;
471 } 504 }
472 } 505 }
473 506
474 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE, 507 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
475 base::Bind(&NetworkActionPredictorDatabase::DeleteRows, db_, id_list)); 508 base::Bind(&AutocompleteActionPredictorTable::DeleteRows,
476 UMA_HISTOGRAM_ENUMERATION("NetworkActionPredictor.DatabaseAction", 509 db_->autocomplete_table(),
dominich 2012/03/06 16:42:13 is it worth storing the reference to the table ins
Shishir 2012/03/14 21:14:37 We didnt want to do that earlier since the table w
510 id_list));
511 UMA_HISTOGRAM_ENUMERATION("AutocompleteActionPredictor.DatabaseAction",
477 DATABASE_ACTION_DELETE_SOME, DATABASE_ACTION_COUNT); 512 DATABASE_ACTION_DELETE_SOME, DATABASE_ACTION_COUNT);
478 } 513 }
479 514
480 void NetworkActionPredictor::BeginTransaction() { 515 AutocompleteActionPredictor::TransitionalMatch::TransitionalMatch() {
481 if (!initialized_)
482 return;
483
484 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
485 base::Bind(&NetworkActionPredictorDatabase::BeginTransaction, db_));
486 } 516 }
487 517
488 void NetworkActionPredictor::CommitTransaction() { 518 AutocompleteActionPredictor::TransitionalMatch::~TransitionalMatch() {
489 if (!initialized_)
490 return;
491
492 content::BrowserThread::PostTask(content::BrowserThread::DB, FROM_HERE,
493 base::Bind(&NetworkActionPredictorDatabase::CommitTransaction, db_));
494 } 519 }
495 520
496 NetworkActionPredictor::TransitionalMatch::TransitionalMatch() { 521 } // namespace predictors
497 }
498
499 NetworkActionPredictor::TransitionalMatch::~TransitionalMatch() {
500 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698