diff options
author | stevet@chromium.org <stevet@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-11-14 15:05:32 +0000 |
---|---|---|
committer | stevet@chromium.org <stevet@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2011-11-14 15:05:32 +0000 |
commit | defd5908a5cd5feaacc1f1c839bd2023438565cd (patch) | |
tree | ecdd975a3fc4685c741bb1a7a42816224170b261 /chrome/browser/search_engines/template_url_service.cc | |
parent | b910d07c7d8239907d7821726573e4a9f844d98c (diff) | |
download | chromium_src-defd5908a5cd5feaacc1f1c839bd2023438565cd.zip chromium_src-defd5908a5cd5feaacc1f1c839bd2023438565cd.tar.gz chromium_src-defd5908a5cd5feaacc1f1c839bd2023438565cd.tar.bz2 |
Merge search engines sync data type with Preferences. Sync the default search provider. Add some defensive measures to prevent deletion of the default search engine or unnecessarily uniquifying keywords.
TEST=Ensure that the default search provider syncs when the Preferences sync data type is enabled. Ensure that the normal search engine syncing changes (add, update, delete) all work.
BUG=15548
Review URL: http://codereview.chromium.org/8334030
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@109882 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'chrome/browser/search_engines/template_url_service.cc')
-rw-r--r-- | chrome/browser/search_engines/template_url_service.cc | 134 |
1 files changed, 120 insertions, 14 deletions
diff --git a/chrome/browser/search_engines/template_url_service.cc b/chrome/browser/search_engines/template_url_service.cc index b9ea5de..fa85ab9 100644 --- a/chrome/browser/search_engines/template_url_service.cc +++ b/chrome/browser/search_engines/template_url_service.cc @@ -113,7 +113,8 @@ TemplateURLService::TemplateURLService(Profile* profile) time_provider_(&base::Time::Now), models_associated_(false), processing_syncer_changes_(false), - sync_processor_(NULL) { + sync_processor_(NULL), + pending_synced_default_search_(false) { DCHECK(profile_); Init(NULL, 0); } @@ -131,7 +132,8 @@ TemplateURLService::TemplateURLService(const Initializer* initializers, time_provider_(&base::Time::Now), models_associated_(false), processing_syncer_changes_(false), - sync_processor_(NULL) { + sync_processor_(NULL), + pending_synced_default_search_(false) { Init(initializers, count); } @@ -457,7 +459,7 @@ const TemplateURL* TemplateURLService::FindNewDefaultSearchProvider() { scoped_ptr<TemplateURL> prepopulated_default( TemplateURLPrepopulateData::GetPrepopulatedDefaultSearch(GetPrefs())); for (TemplateURLVector::iterator i = template_urls_.begin(); - i != template_urls_.end(); ) { + i != template_urls_.end(); ++i) { if ((*i)->prepopulate_id() == prepopulated_default->prepopulate_id()) return *i; } @@ -579,12 +581,17 @@ void TemplateURLService::OnWebDataServiceRequestDone( // Note that this saves the default search provider to prefs. SetDefaultSearchProviderNoNotify(default_search_provider); } else { - // If we had a managed default, replace it with the first provider of - // the list. - if (database_specified_a_default && - NULL == default_search_provider && - !template_urls.empty()) + // If we had a managed default, replace it with the synced default if + // applicable, or the first provider of the list. + const TemplateURL* synced_default = GetPendingSyncedDefaultSearchProvider(); + if (synced_default) { + default_search_provider = synced_default; + pending_synced_default_search_ = false; + } else if (database_specified_a_default && + NULL == default_search_provider && + !template_urls.empty()) { default_search_provider = template_urls[0]; + } // If the default search provider existed previously, then just // set the member variable. Otherwise, we'll set it using the method @@ -651,6 +658,27 @@ void TemplateURLService::Observe(int type, } else if (type == chrome::NOTIFICATION_PREF_CHANGED) { const std::string* pref_name = content::Details<std::string>(details).ptr(); if (!pref_name || default_search_prefs_->IsObserved(*pref_name)) { + // Listen for changes to the default search from Sync. If it is + // specifically the synced default search provider GUID that changed, we + // have to set it (or wait for it). + PrefService* prefs = GetPrefs(); + if (pref_name && *pref_name == prefs::kSyncedDefaultSearchProviderGUID && + prefs) { + const TemplateURL* new_default_search = GetTemplateURLForGUID( + prefs->GetString(prefs::kSyncedDefaultSearchProviderGUID)); + if (new_default_search && !is_default_search_managed_) { + if (new_default_search != GetDefaultSearchProvider()) { + SetDefaultSearchProvider(new_default_search); + pending_synced_default_search_ = false; + } + } else { + // If it's not there, or if default search is currently managed, set a + // flag to indicate that we waiting on the search engine entry to come + // in through Sync. + pending_synced_default_search_ = true; + } + } + // A preference related to default search engine has changed. // Update the model if needed. UpdateDefaultSearch(); @@ -708,17 +736,35 @@ SyncError TemplateURLService::ProcessSyncChanges( GetTemplateURLForKeyword(turl->keyword()); if (iter->change_type() == SyncChange::ACTION_DELETE && existing_turl) { - Remove(existing_turl); + bool delete_default = (existing_turl == GetDefaultSearchProvider()); + + if (delete_default && is_default_search_managed_) { + NOTREACHED() << "Tried to delete managed default search provider"; + } else { + if (delete_default) + default_search_provider_ = NULL; + + Remove(existing_turl); + + if (delete_default) + SetDefaultSearchProvider(FindNewDefaultSearchProvider()); + } } else if (iter->change_type() == SyncChange::ACTION_ADD && !existing_turl) { + std::string guid = turl->sync_guid(); if (existing_keyword_turl) ResolveSyncKeywordConflict(turl.get(), &new_changes); // Force the local ID to 0 so we can add it. turl->set_id(0); Add(turl.release()); + + // Possibly set the newly added |turl| as the default search provider. + SetDefaultSearchProviderIfNewlySynced(guid); } else if (iter->change_type() == SyncChange::ACTION_UPDATE && existing_turl) { - if (existing_keyword_turl) + // Possibly resolve a keyword conflict if they have the same keywords but + // are not the same entry. + if (existing_keyword_turl && existing_keyword_turl != existing_turl) ResolveSyncKeywordConflict(turl.get(), &new_changes); ResetTemplateURL(existing_turl, turl->short_name(), turl->keyword(), turl->url() ? turl->url()->url() : std::string()); @@ -753,6 +799,18 @@ SyncError TemplateURLService::MergeDataAndStartSyncing( DCHECK(!sync_processor_); sync_processor_ = sync_processor; + // We just started syncing, so set our wait-for-default flag if we are + // expecting a default from Sync. + if (GetPrefs()) { + std::string default_guid = GetPrefs()->GetString( + prefs::kSyncedDefaultSearchProviderGUID); + const TemplateURL* current_default = GetDefaultSearchProvider(); + + if (!default_guid.empty() && + (!current_default || current_default->sync_guid() != default_guid)) + pending_synced_default_search_ = true; + } + // We do a lot of calls to Add/Remove/ResetTemplateURL here, so ensure we // don't step on our own toes. AutoReset<bool> processing_changes(&processing_syncer_changes_, true); @@ -812,6 +870,7 @@ SyncError TemplateURLService::MergeDataAndStartSyncing( &new_changes); local_data_map.erase(old_guid); } else { + std::string guid = sync_turl->sync_guid(); // Keyword conflict is possible in this case. Resolve it first before // adding the new TemplateURL. Note that we don't remove the local TURL // from local_data_map in this case as it may still need to be pushed to @@ -820,6 +879,9 @@ SyncError TemplateURLService::MergeDataAndStartSyncing( // Force the local ID to 0 so we can add it. sync_turl->set_id(0); Add(sync_turl.release()); + + // Possibly set the newly added |turl| as the default search provider. + SetDefaultSearchProviderIfNewlySynced(guid); } } } // for @@ -952,7 +1014,7 @@ void TemplateURLService::SetKeywordSearchTermsForURL(const TemplateURL* t_url, } void TemplateURLService::Init(const Initializer* initializers, - int num_initializers) { + int num_initializers) { // Register for notifications. if (profile_) { // TODO(sky): bug 1166191. The keywords should be moved into the history @@ -1488,7 +1550,14 @@ void TemplateURLService::UpdateDefaultSearch() { default_search_provider_ = NULL; RemoveNoNotify(old_default); } - SetDefaultSearchProviderNoNotify(FindNewDefaultSearchProvider()); + + // The likely default should be from Sync if we were waiting on Sync. + // Otherwise, it should be FindNewDefaultSearchProvider. + const TemplateURL* synced_default = GetPendingSyncedDefaultSearchProvider(); + if (synced_default) + pending_synced_default_search_ = false; + SetDefaultSearchProviderNoNotify(synced_default ? synced_default : + FindNewDefaultSearchProvider()); } NotifyObservers(); } @@ -1520,9 +1589,17 @@ void TemplateURLService::SetDefaultSearchProviderNoNotify( } } - if (!is_default_search_managed_) + if (!is_default_search_managed_) { SaveDefaultSearchProviderToPrefs(url); + // If we are syncing, we want to set the synced pref that will notify other + // instances to change their default to this new search provider. + if (sync_processor_ && !url->sync_guid().empty() && GetPrefs()) { + GetPrefs()->SetString(prefs::kSyncedDefaultSearchProviderGUID, + url->sync_guid()); + } + } + if (service_.get()) service_->SetDefaultSearchProvider(url); @@ -1681,7 +1758,8 @@ bool TemplateURLService::ResolveSyncKeywordConflict( const TemplateURL* existing_turl = GetTemplateURLForKeyword(sync_turl->keyword()); - if (!existing_turl) + // If there is no conflict, or it's just conflicting with itself, return. + if (!existing_turl || existing_turl->sync_guid() == sync_turl->sync_guid()) return false; if (existing_turl->last_modified() > sync_turl->last_modified() || @@ -1745,6 +1823,34 @@ void TemplateURLService::MergeSyncAndLocalURLDuplicates( } } +void TemplateURLService::SetDefaultSearchProviderIfNewlySynced( + const std::string& guid) { + // If we're not syncing or if default search is managed by policy, ignore. + if (!sync_processor_ || is_default_search_managed_) + return; + + PrefService* prefs = GetPrefs(); + if (prefs && pending_synced_default_search_ && + prefs->GetString(prefs::kSyncedDefaultSearchProviderGUID) == guid) { + // Make sure this actually exists. We should not be calling this unless we + // really just added this TemplateURL. + const TemplateURL* turl_from_sync = GetTemplateURLForGUID(guid); + DCHECK(turl_from_sync); + SetDefaultSearchProvider(turl_from_sync); + pending_synced_default_search_ = false; + } +} + +const TemplateURL* TemplateURLService::GetPendingSyncedDefaultSearchProvider() { + PrefService* prefs = GetPrefs(); + if (!prefs || !pending_synced_default_search_) + return NULL; + + // Could be NULL if no such thing exists. + return GetTemplateURLForGUID( + prefs->GetString(prefs::kSyncedDefaultSearchProviderGUID)); +} + void TemplateURLService::PatchMissingSyncGUIDs( std::vector<TemplateURL*>* template_urls) { DCHECK(template_urls); |