| Index: chrome/browser/history/top_sites.cc
|
| ===================================================================
|
| --- chrome/browser/history/top_sites.cc (revision 61074)
|
| +++ chrome/browser/history/top_sites.cc (working copy)
|
| @@ -51,7 +51,8 @@
|
| migration_in_progress_(false),
|
| waiting_for_results_(true),
|
| blacklist_(NULL),
|
| - pinned_urls_(NULL) {
|
| + pinned_urls_(NULL),
|
| + handle_to_wait_for_(NULL) {
|
| if (!profile_)
|
| return;
|
|
|
| @@ -90,7 +91,7 @@
|
|
|
| // Start the one-shot timer.
|
| timer_.Start(base::TimeDelta::FromSeconds(kUpdateIntervalSecs), this,
|
| - &TopSites::StartQueryForMostVisited);
|
| + &TopSites::TimerFired);
|
| }
|
|
|
| void TopSites::ReadDatabase() {
|
| @@ -449,7 +450,7 @@
|
|
|
| timer_.Stop();
|
| timer_.Start(GetUpdateDelay(), this,
|
| - &TopSites::StartQueryForMostVisited);
|
| + &TopSites::TimerFired);
|
| }
|
|
|
| void TopSites::OnMigrationDone() {
|
| @@ -638,23 +639,21 @@
|
| }
|
| }
|
|
|
| -void TopSites::StartQueryForMostVisited() {
|
| +CancelableRequestProvider::Handle TopSites::StartQueryForMostVisited() {
|
| + CancelableRequestProvider::Handle request_handle = NULL;
|
| if (mock_history_service_) {
|
| // Testing with a mockup.
|
| // QueryMostVisitedURLs is not virtual, so we have to duplicate the code.
|
| - mock_history_service_->QueryMostVisitedURLs(
|
| + request_handle = mock_history_service_->QueryMostVisitedURLs(
|
| kTopSitesNumber + blacklist_->size(),
|
| kDaysOfHistory,
|
| &cancelable_consumer_,
|
| NewCallback(this, &TopSites::OnTopSitesAvailable));
|
| - } else {
|
| - if (!profile_)
|
| - return;
|
| -
|
| + } else if (profile_) {
|
| HistoryService* hs = profile_->GetHistoryService(Profile::EXPLICIT_ACCESS);
|
| // |hs| may be null during unit tests.
|
| if (hs) {
|
| - hs->QueryMostVisitedURLs(
|
| + request_handle = hs->QueryMostVisitedURLs(
|
| kTopSitesNumber + blacklist_->size(),
|
| kDaysOfHistory,
|
| &cancelable_consumer_,
|
| @@ -663,8 +662,13 @@
|
| LOG(INFO) << "History Service not available.";
|
| }
|
| }
|
| + return request_handle;
|
| }
|
|
|
| +void TopSites::TimerFired() {
|
| + StartQueryForMostVisited();
|
| +}
|
| +
|
| void TopSites::StartMigration() {
|
| LOG(INFO) << "Starting migration to TopSites.";
|
| migration_in_progress_ = true;
|
| @@ -760,6 +764,19 @@
|
| }
|
| }
|
|
|
| +void TopSites::RefreshAndCallback(CancelableRequestConsumer* consumer,
|
| + Callback0::Type* callback) {
|
| + if (refresh_callback_) {
|
| + DLOG(ERROR) << "Waiting for refresh before previous refresh finished";
|
| + return;
|
| + }
|
| + scoped_refptr<CancelableRequest<Callback0::Type> > request(
|
| + new CancelableRequest<Callback0::Type>(callback));
|
| + AddRequest(request, consumer);
|
| + refresh_callback_ = request;
|
| + handle_to_wait_for_ = StartQueryForMostVisited();
|
| +}
|
| +
|
| void TopSites::ClearProfile() {
|
| profile_ = NULL;
|
| }
|
| @@ -781,6 +798,19 @@
|
| AddPrepopulatedPages(&pages);
|
| ChromeThread::PostTask(ChromeThread::DB, FROM_HERE, NewRunnableMethod(
|
| this, &TopSites::UpdateMostVisited, pages));
|
| +
|
| + if (handle == handle_to_wait_for_) {
|
| + if (ChromeThread::IsWellKnownThread(ChromeThread::UI)) {
|
| + DCHECK(ChromeThread::CurrentlyOn(ChromeThread::UI));
|
| + // Posting this task after the one above should guarantee that
|
| + // |top_sites_| is completely refreshed.
|
| + ChromeThread::PostTask(ChromeThread::DB, FROM_HERE, NewRunnableMethod(
|
| + this, &TopSites::InvokeRefreshCallback));
|
| + } else {
|
| + // This will happen in unit tests when we don't have a real UI thread.
|
| + InvokeRefreshCallbackOnUIThread();
|
| + }
|
| + }
|
| }
|
|
|
| // static
|
| @@ -893,4 +923,19 @@
|
| }
|
| }
|
|
|
| +void TopSites::InvokeRefreshCallback() {
|
| + ChromeThread::PostTask(ChromeThread::UI, FROM_HERE,
|
| + NewRunnableMethod(this, &TopSites::InvokeRefreshCallbackOnUIThread));
|
| +}
|
| +
|
| +void TopSites::InvokeRefreshCallbackOnUIThread() {
|
| + if (refresh_callback_) {
|
| + if (!refresh_callback_->canceled())
|
| + refresh_callback_->ForwardResult(Callback0::Type::TupleType());
|
| + refresh_callback_.release();
|
| + } else {
|
| + LOG(DFATAL) << "No refresh callback was set.";
|
| + }
|
| +}
|
| +
|
| } // namespace history
|
|
|