| OLD | NEW |
| 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 // The history system runs on a background thread so that potentially slow | 5 // The history system runs on a background thread so that potentially slow |
| 6 // database operations don't delay the browser. This backend processing is | 6 // database operations don't delay the browser. This backend processing is |
| 7 // represented by HistoryBackend. The HistoryService's job is to dispatch to | 7 // represented by HistoryBackend. The HistoryService's job is to dispatch to |
| 8 // that thread. | 8 // that thread. |
| 9 // | 9 // |
| 10 // Main thread History thread | 10 // Main thread History thread |
| (...skipping 12 matching lines...) Expand all Loading... |
| 23 #include "base/command_line.h" | 23 #include "base/command_line.h" |
| 24 #include "base/compiler_specific.h" | 24 #include "base/compiler_specific.h" |
| 25 #include "base/location.h" | 25 #include "base/location.h" |
| 26 #include "base/memory/ref_counted.h" | 26 #include "base/memory/ref_counted.h" |
| 27 #include "base/message_loop/message_loop.h" | 27 #include "base/message_loop/message_loop.h" |
| 28 #include "base/prefs/pref_service.h" | 28 #include "base/prefs/pref_service.h" |
| 29 #include "base/thread_task_runner_handle.h" | 29 #include "base/thread_task_runner_handle.h" |
| 30 #include "base/threading/thread.h" | 30 #include "base/threading/thread.h" |
| 31 #include "base/time/time.h" | 31 #include "base/time/time.h" |
| 32 #include "chrome/browser/browser_process.h" | 32 #include "chrome/browser/browser_process.h" |
| 33 #include "chrome/browser/chrome_notification_types.h" | |
| 34 #include "chrome/browser/history/download_row.h" | 33 #include "chrome/browser/history/download_row.h" |
| 35 #include "chrome/browser/history/history_backend.h" | 34 #include "chrome/browser/history/history_backend.h" |
| 36 #include "chrome/browser/history/history_notifications.h" | |
| 37 #include "chrome/browser/history/in_memory_history_backend.h" | 35 #include "chrome/browser/history/in_memory_history_backend.h" |
| 38 #include "chrome/browser/history/in_memory_url_index.h" | 36 #include "chrome/browser/history/in_memory_url_index.h" |
| 39 #include "chrome/browser/history/top_sites.h" | 37 #include "chrome/browser/history/top_sites.h" |
| 40 #include "chrome/browser/history/visit_database.h" | 38 #include "chrome/browser/history/visit_database.h" |
| 41 #include "chrome/browser/history/visit_filter.h" | 39 #include "chrome/browser/history/visit_filter.h" |
| 42 #include "chrome/browser/history/web_history_service.h" | 40 #include "chrome/browser/history/web_history_service.h" |
| 43 #include "chrome/browser/history/web_history_service_factory.h" | 41 #include "chrome/browser/history/web_history_service_factory.h" |
| 44 #include "chrome/browser/profiles/profile.h" | 42 #include "chrome/browser/profiles/profile.h" |
| 45 #include "chrome/common/chrome_constants.h" | 43 #include "chrome/common/chrome_constants.h" |
| 46 #include "chrome/common/chrome_switches.h" | 44 #include "chrome/common/chrome_switches.h" |
| (...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 176 base::Bind(&HistoryService::NotifyURLVisited, | 174 base::Bind(&HistoryService::NotifyURLVisited, |
| 177 history_service_, | 175 history_service_, |
| 178 transition, | 176 transition, |
| 179 row, | 177 row, |
| 180 redirects, | 178 redirects, |
| 181 visit_time)); | 179 visit_time)); |
| 182 } | 180 } |
| 183 | 181 |
| 184 void NotifyURLsModified(const history::URLRows& changed_urls) override { | 182 void NotifyURLsModified(const history::URLRows& changed_urls) override { |
| 185 service_task_runner_->PostTask( | 183 service_task_runner_->PostTask( |
| 184 FROM_HERE, base::Bind(&HistoryService::NotifyURLsModified, |
| 185 history_service_, changed_urls)); |
| 186 } |
| 187 |
| 188 void NotifyURLsDeleted(bool all_history, |
| 189 bool expired, |
| 190 const history::URLRows& deleted_rows, |
| 191 const std::set<GURL>& favicon_urls) override { |
| 192 service_task_runner_->PostTask( |
| 186 FROM_HERE, | 193 FROM_HERE, |
| 187 base::Bind(&HistoryService::NotifyURLsModified, | 194 base::Bind(&HistoryService::NotifyURLsDeleted, history_service_, |
| 188 history_service_, | 195 all_history, expired, deleted_rows, favicon_urls)); |
| 189 changed_urls)); | |
| 190 } | 196 } |
| 191 | 197 |
| 192 void BroadcastNotifications( | 198 void BroadcastNotifications( |
| 193 int type, | 199 int type, |
| 194 scoped_ptr<history::HistoryDetails> details) override { | 200 scoped_ptr<history::HistoryDetails> details) override { |
| 195 // Send the notification on the history thread. | 201 // Send the notification on the history thread. |
| 196 if (content::NotificationService::current()) { | 202 if (content::NotificationService::current()) { |
| 197 content::Details<history::HistoryDetails> det(details.get()); | 203 content::Details<history::HistoryDetails> det(details.get()); |
| 198 content::NotificationService::current()->Notify( | 204 content::NotificationService::current()->Notify( |
| 199 type, content::Source<Profile>(profile_), det); | 205 type, content::Source<Profile>(profile_), det); |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 232 HistoryService::HistoryService(history::HistoryClient* client, Profile* profile) | 238 HistoryService::HistoryService(history::HistoryClient* client, Profile* profile) |
| 233 : thread_(new base::Thread(kHistoryThreadName)), | 239 : thread_(new base::Thread(kHistoryThreadName)), |
| 234 history_client_(client), | 240 history_client_(client), |
| 235 profile_(profile), | 241 profile_(profile), |
| 236 visitedlink_master_(new visitedlink::VisitedLinkMaster( | 242 visitedlink_master_(new visitedlink::VisitedLinkMaster( |
| 237 profile, this, true)), | 243 profile, this, true)), |
| 238 backend_loaded_(false), | 244 backend_loaded_(false), |
| 239 no_db_(false), | 245 no_db_(false), |
| 240 weak_ptr_factory_(this) { | 246 weak_ptr_factory_(this) { |
| 241 DCHECK(profile_); | 247 DCHECK(profile_); |
| 242 registrar_.Add(this, chrome::NOTIFICATION_HISTORY_URLS_DELETED, | |
| 243 content::Source<Profile>(profile_)); | |
| 244 } | 248 } |
| 245 | 249 |
| 246 HistoryService::~HistoryService() { | 250 HistoryService::~HistoryService() { |
| 247 DCHECK(thread_checker_.CalledOnValidThread()); | 251 DCHECK(thread_checker_.CalledOnValidThread()); |
| 248 // Shutdown the backend. This does nothing if Cleanup was already invoked. | 252 // Shutdown the backend. This does nothing if Cleanup was already invoked. |
| 249 Cleanup(); | 253 Cleanup(); |
| 250 } | 254 } |
| 251 | 255 |
| 252 bool HistoryService::BackendLoaded() { | 256 bool HistoryService::BackendLoaded() { |
| 253 DCHECK(thread_checker_.CalledOnValidThread()); | 257 DCHECK(thread_checker_.CalledOnValidThread()); |
| (...skipping 679 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 933 } | 937 } |
| 934 | 938 |
| 935 // Delete the thread, which joins with the background thread. We defensively | 939 // Delete the thread, which joins with the background thread. We defensively |
| 936 // NULL the pointer before deleting it in case somebody tries to use it | 940 // NULL the pointer before deleting it in case somebody tries to use it |
| 937 // during shutdown, but this shouldn't happen. | 941 // during shutdown, but this shouldn't happen. |
| 938 base::Thread* thread = thread_; | 942 base::Thread* thread = thread_; |
| 939 thread_ = NULL; | 943 thread_ = NULL; |
| 940 delete thread; | 944 delete thread; |
| 941 } | 945 } |
| 942 | 946 |
| 943 void HistoryService::Observe(int type, | |
| 944 const content::NotificationSource& source, | |
| 945 const content::NotificationDetails& details) { | |
| 946 DCHECK(thread_checker_.CalledOnValidThread()); | |
| 947 if (!thread_) | |
| 948 return; | |
| 949 | |
| 950 switch (type) { | |
| 951 case chrome::NOTIFICATION_HISTORY_URLS_DELETED: { | |
| 952 // Update the visited link system for deleted URLs. We will update the | |
| 953 // visited link system for added URLs as soon as we get the add | |
| 954 // notification (we don't have to wait for the backend, which allows us to | |
| 955 // be faster to update the state). | |
| 956 // | |
| 957 // For deleted URLs, we don't typically know what will be deleted since | |
| 958 // delete notifications are by time. We would also like to be more | |
| 959 // respectful of privacy and never tell the user something is gone when it | |
| 960 // isn't. Therefore, we update the delete URLs after the fact. | |
| 961 if (visitedlink_master_) { | |
| 962 content::Details<history::URLsDeletedDetails> deleted_details(details); | |
| 963 | |
| 964 if (deleted_details->all_history) { | |
| 965 visitedlink_master_->DeleteAllURLs(); | |
| 966 } else { | |
| 967 URLIteratorFromURLRows iterator(deleted_details->rows); | |
| 968 visitedlink_master_->DeleteURLs(&iterator); | |
| 969 } | |
| 970 } | |
| 971 break; | |
| 972 } | |
| 973 | |
| 974 default: | |
| 975 NOTREACHED(); | |
| 976 } | |
| 977 } | |
| 978 | |
| 979 void HistoryService::RebuildTable( | 947 void HistoryService::RebuildTable( |
| 980 const scoped_refptr<URLEnumerator>& enumerator) { | 948 const scoped_refptr<URLEnumerator>& enumerator) { |
| 981 DCHECK(thread_) << "History service being called after cleanup"; | 949 DCHECK(thread_) << "History service being called after cleanup"; |
| 982 DCHECK(thread_checker_.CalledOnValidThread()); | 950 DCHECK(thread_checker_.CalledOnValidThread()); |
| 983 ScheduleAndForget(PRIORITY_NORMAL, &HistoryBackend::IterateURLs, enumerator); | 951 ScheduleAndForget(PRIORITY_NORMAL, &HistoryBackend::IterateURLs, enumerator); |
| 984 } | 952 } |
| 985 | 953 |
| 986 bool HistoryService::Init(const base::FilePath& history_dir, bool no_db) { | 954 bool HistoryService::Init(const base::FilePath& history_dir, bool no_db) { |
| 987 DCHECK(thread_) << "History service being called after cleanup"; | 955 DCHECK(thread_) << "History service being called after cleanup"; |
| 988 DCHECK(thread_checker_.CalledOnValidThread()); | 956 DCHECK(thread_checker_.CalledOnValidThread()); |
| (...skipping 272 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1261 OnURLVisited(this, transition, row, redirects, visit_time)); | 1229 OnURLVisited(this, transition, row, redirects, visit_time)); |
| 1262 } | 1230 } |
| 1263 | 1231 |
| 1264 void HistoryService::NotifyURLsModified(const history::URLRows& changed_urls) { | 1232 void HistoryService::NotifyURLsModified(const history::URLRows& changed_urls) { |
| 1265 DCHECK(thread_checker_.CalledOnValidThread()); | 1233 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1266 FOR_EACH_OBSERVER(history::HistoryServiceObserver, | 1234 FOR_EACH_OBSERVER(history::HistoryServiceObserver, |
| 1267 observers_, | 1235 observers_, |
| 1268 OnURLsModified(this, changed_urls)); | 1236 OnURLsModified(this, changed_urls)); |
| 1269 } | 1237 } |
| 1270 | 1238 |
| 1239 void HistoryService::NotifyURLsDeleted(bool all_history, |
| 1240 bool expired, |
| 1241 const history::URLRows& deleted_rows, |
| 1242 const std::set<GURL>& favicon_urls) { |
| 1243 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1244 if (!thread_) |
| 1245 return; |
| 1246 |
| 1247 // Update the visited link system for deleted URLs. We will update the |
| 1248 // visited link system for added URLs as soon as we get the add |
| 1249 // notification (we don't have to wait for the backend, which allows us to |
| 1250 // be faster to update the state). |
| 1251 // |
| 1252 // For deleted URLs, we don't typically know what will be deleted since |
| 1253 // delete notifications are by time. We would also like to be more |
| 1254 // respectful of privacy and never tell the user something is gone when it |
| 1255 // isn't. Therefore, we update the delete URLs after the fact. |
| 1256 if (visitedlink_master_) { |
| 1257 if (all_history) { |
| 1258 visitedlink_master_->DeleteAllURLs(); |
| 1259 } else { |
| 1260 URLIteratorFromURLRows iterator(deleted_rows); |
| 1261 visitedlink_master_->DeleteURLs(&iterator); |
| 1262 } |
| 1263 } |
| 1264 |
| 1265 FOR_EACH_OBSERVER( |
| 1266 history::HistoryServiceObserver, observers_, |
| 1267 OnURLsDeleted(this, all_history, expired, deleted_rows, favicon_urls)); |
| 1268 } |
| 1269 |
| 1271 void HistoryService::NotifyHistoryServiceLoaded() { | 1270 void HistoryService::NotifyHistoryServiceLoaded() { |
| 1272 DCHECK(thread_checker_.CalledOnValidThread()); | 1271 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1273 FOR_EACH_OBSERVER(history::HistoryServiceObserver, observers_, | 1272 FOR_EACH_OBSERVER(history::HistoryServiceObserver, observers_, |
| 1274 OnHistoryServiceLoaded(this)); | 1273 OnHistoryServiceLoaded(this)); |
| 1275 } | 1274 } |
| 1276 | 1275 |
| 1277 void HistoryService::NotifyHistoryServiceBeingDeleted() { | 1276 void HistoryService::NotifyHistoryServiceBeingDeleted() { |
| 1278 DCHECK(thread_checker_.CalledOnValidThread()); | 1277 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1279 FOR_EACH_OBSERVER(history::HistoryServiceObserver, observers_, | 1278 FOR_EACH_OBSERVER(history::HistoryServiceObserver, observers_, |
| 1280 HistoryServiceBeingDeleted(this)); | 1279 HistoryServiceBeingDeleted(this)); |
| 1281 } | 1280 } |
| 1282 | 1281 |
| 1283 scoped_ptr<base::CallbackList<void(const std::set<GURL>&)>::Subscription> | 1282 scoped_ptr<base::CallbackList<void(const std::set<GURL>&)>::Subscription> |
| 1284 HistoryService::AddFaviconChangedCallback( | 1283 HistoryService::AddFaviconChangedCallback( |
| 1285 const HistoryService::OnFaviconChangedCallback& callback) { | 1284 const HistoryService::OnFaviconChangedCallback& callback) { |
| 1286 DCHECK(thread_checker_.CalledOnValidThread()); | 1285 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1287 return favicon_changed_callback_list_.Add(callback); | 1286 return favicon_changed_callback_list_.Add(callback); |
| 1288 } | 1287 } |
| 1289 | 1288 |
| 1290 void HistoryService::NotifyFaviconChanged( | 1289 void HistoryService::NotifyFaviconChanged( |
| 1291 const std::set<GURL>& changed_favicons) { | 1290 const std::set<GURL>& changed_favicons) { |
| 1292 DCHECK(thread_checker_.CalledOnValidThread()); | 1291 DCHECK(thread_checker_.CalledOnValidThread()); |
| 1293 favicon_changed_callback_list_.Notify(changed_favicons); | 1292 favicon_changed_callback_list_.Notify(changed_favicons); |
| 1294 } | 1293 } |
| OLD | NEW |