Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 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 "components/ntp_snippets/ntp_snippets_service.h" | 5 #include "components/ntp_snippets/ntp_snippets_service.h" |
| 6 | 6 |
| 7 #include <algorithm> | |
| 8 #include <utility> | |
| 9 | |
| 7 #include "base/command_line.h" | 10 #include "base/command_line.h" |
| 8 #include "base/files/file_path.h" | 11 #include "base/files/file_path.h" |
| 9 #include "base/files/file_util.h" | 12 #include "base/files/file_util.h" |
| 10 #include "base/json/json_reader.h" | 13 #include "base/json/json_reader.h" |
| 11 #include "base/location.h" | 14 #include "base/location.h" |
| 12 #include "base/path_service.h" | 15 #include "base/path_service.h" |
| 13 #include "base/strings/string_number_conversions.h" | 16 #include "base/strings/string_number_conversions.h" |
| 14 #include "base/task_runner_util.h" | 17 #include "base/task_runner_util.h" |
| 15 #include "base/time/time.h" | 18 #include "base/time/time.h" |
| 16 #include "base/values.h" | 19 #include "base/values.h" |
| (...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 57 base::TimeDelta GetFetchingIntervalWifi() { | 60 base::TimeDelta GetFetchingIntervalWifi() { |
| 58 return GetFetchingInterval(switches::kFetchingIntervalWifiSeconds, | 61 return GetFetchingInterval(switches::kFetchingIntervalWifiSeconds, |
| 59 kFetchingIntervalWifiSeconds); | 62 kFetchingIntervalWifiSeconds); |
| 60 } | 63 } |
| 61 | 64 |
| 62 base::TimeDelta GetFetchingIntervalFallback() { | 65 base::TimeDelta GetFetchingIntervalFallback() { |
| 63 return GetFetchingInterval(switches::kFetchingIntervalFallbackSeconds, | 66 return GetFetchingInterval(switches::kFetchingIntervalFallbackSeconds, |
| 64 kFetchingIntervalFallbackSeconds); | 67 kFetchingIntervalFallbackSeconds); |
| 65 } | 68 } |
| 66 | 69 |
| 70 // Extracts the hosts from |suggestions| and returns them in a sorted vector. | |
| 67 std::vector<std::string> GetSuggestionsHosts( | 71 std::vector<std::string> GetSuggestionsHosts( |
| 68 const SuggestionsProfile& suggestions) { | 72 const SuggestionsProfile& suggestions) { |
| 69 std::vector<std::string> hosts; | 73 std::vector<std::string> hosts; |
| 70 for (int i = 0; i < suggestions.suggestions_size(); ++i) { | 74 for (int i = 0; i < suggestions.suggestions_size(); ++i) { |
| 71 const ChromeSuggestion& suggestion = suggestions.suggestions(i); | 75 const ChromeSuggestion& suggestion = suggestions.suggestions(i); |
| 72 GURL url(suggestion.url()); | 76 GURL url(suggestion.url()); |
| 73 if (url.is_valid()) | 77 if (url.is_valid()) |
| 74 hosts.push_back(url.host()); | 78 hosts.push_back(url.host()); |
| 75 } | 79 } |
| 80 std::sort(hosts.begin(), hosts.end()); | |
| 76 return hosts; | 81 return hosts; |
| 77 } | 82 } |
| 78 | 83 |
| 79 const char kContentInfo[] = "contentInfo"; | 84 const char kContentInfo[] = "contentInfo"; |
| 80 | 85 |
| 81 // Parses snippets from |list| and adds them to |snippets|. Returns true on | 86 // Parses snippets from |list| and adds them to |snippets|. Returns true on |
| 82 // success, false if anything went wrong. | 87 // success, false if anything went wrong. |
| 83 bool AddSnippetsFromListValue(const base::ListValue& list, | 88 bool AddSnippetsFromListValue(const base::ListValue& list, |
| 84 NTPSnippetsService::NTPSnippetStorage* snippets) { | 89 NTPSnippetsService::NTPSnippetStorage* snippets) { |
| 85 for (const base::Value* const value : list) { | 90 for (const base::Value* const value : list) { |
| (...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 132 snippets_fetcher_subscription_ = snippets_fetcher_->AddCallback(base::Bind( | 137 snippets_fetcher_subscription_ = snippets_fetcher_->AddCallback(base::Bind( |
| 133 &NTPSnippetsService::OnSnippetsDownloaded, base::Unretained(this))); | 138 &NTPSnippetsService::OnSnippetsDownloaded, base::Unretained(this))); |
| 134 } | 139 } |
| 135 | 140 |
| 136 NTPSnippetsService::~NTPSnippetsService() {} | 141 NTPSnippetsService::~NTPSnippetsService() {} |
| 137 | 142 |
| 138 // static | 143 // static |
| 139 void NTPSnippetsService::RegisterProfilePrefs(PrefRegistrySimple* registry) { | 144 void NTPSnippetsService::RegisterProfilePrefs(PrefRegistrySimple* registry) { |
| 140 registry->RegisterListPref(prefs::kSnippets); | 145 registry->RegisterListPref(prefs::kSnippets); |
| 141 registry->RegisterListPref(prefs::kDiscardedSnippets); | 146 registry->RegisterListPref(prefs::kDiscardedSnippets); |
| 147 registry->RegisterListPref(prefs::kSnippetHosts); | |
| 142 } | 148 } |
| 143 | 149 |
| 144 void NTPSnippetsService::Init(bool enabled) { | 150 void NTPSnippetsService::Init(bool enabled) { |
| 145 if (enabled) { | 151 if (enabled) { |
| 146 // |suggestions_service_| can be null in tests. | 152 // |suggestions_service_| can be null in tests. |
| 147 if (suggestions_service_) { | 153 if (suggestions_service_) { |
| 148 suggestions_service_subscription_ = suggestions_service_->AddCallback( | 154 suggestions_service_subscription_ = suggestions_service_->AddCallback( |
| 149 base::Bind(&NTPSnippetsService::OnSuggestionsChanged, | 155 base::Bind(&NTPSnippetsService::OnSuggestionsChanged, |
| 150 base::Unretained(this))); | 156 base::Unretained(this))); |
| 151 } | 157 } |
| (...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 207 observer->NTPSnippetsServiceLoaded(this); | 213 observer->NTPSnippetsServiceLoaded(this); |
| 208 } | 214 } |
| 209 | 215 |
| 210 void NTPSnippetsService::RemoveObserver(NTPSnippetsServiceObserver* observer) { | 216 void NTPSnippetsService::RemoveObserver(NTPSnippetsServiceObserver* observer) { |
| 211 observers_.RemoveObserver(observer); | 217 observers_.RemoveObserver(observer); |
| 212 } | 218 } |
| 213 | 219 |
| 214 void NTPSnippetsService::OnSuggestionsChanged( | 220 void NTPSnippetsService::OnSuggestionsChanged( |
| 215 const SuggestionsProfile& suggestions) { | 221 const SuggestionsProfile& suggestions) { |
| 216 std::vector<std::string> hosts = GetSuggestionsHosts(suggestions); | 222 std::vector<std::string> hosts = GetSuggestionsHosts(suggestions); |
| 223 if (hosts == GetSnippetHostsFromPrefs()) | |
| 224 return; | |
| 217 | 225 |
| 218 // Remove existing snippets that aren't in the suggestions anymore. | 226 // Remove existing snippets that aren't in the suggestions anymore. |
| 219 snippets_.erase( | 227 snippets_.erase( |
| 220 std::remove_if(snippets_.begin(), snippets_.end(), | 228 std::remove_if(snippets_.begin(), snippets_.end(), |
| 221 [&hosts](const scoped_ptr<NTPSnippet>& snippet) { | 229 [&hosts](const scoped_ptr<NTPSnippet>& snippet) { |
| 222 return std::find(hosts.begin(), hosts.end(), | 230 return !std::binary_search(hosts.begin(), hosts.end(), |
|
Marc Treib
2016/04/06 16:14:55
Side-effect of the hosts now being sorted :)
Bernhard Bauer
2016/04/07 12:28:12
Neat! :) But could we make the hosts a set instead
Marc Treib
2016/04/07 13:19:54
Eh.. sure. Done.
| |
| 223 snippet->url().host()) == hosts.end(); | 231 snippet->url().host()); |
| 224 }), | 232 }), |
| 225 snippets_.end()); | 233 snippets_.end()); |
| 226 | 234 |
| 227 StoreSnippetsToPrefs(); | 235 StoreSnippetsToPrefs(); |
| 236 StoreSnippetHostsToPrefs(hosts); | |
| 228 | 237 |
| 229 FOR_EACH_OBSERVER(NTPSnippetsServiceObserver, observers_, | 238 FOR_EACH_OBSERVER(NTPSnippetsServiceObserver, observers_, |
| 230 NTPSnippetsServiceLoaded(this)); | 239 NTPSnippetsServiceLoaded(this)); |
| 231 | 240 |
| 232 FetchSnippetsImpl(hosts); | 241 FetchSnippetsImpl(hosts); |
| 233 } | 242 } |
| 234 | 243 |
| 235 void NTPSnippetsService::OnSnippetsDownloaded( | 244 void NTPSnippetsService::OnSnippetsDownloaded( |
| 236 const std::string& snippets_json) { | 245 const std::string& snippets_json) { |
| 237 parse_json_callback_.Run( | 246 parse_json_callback_.Run( |
| (...skipping 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 329 *pref_service_->GetList(prefs::kDiscardedSnippets), | 338 *pref_service_->GetList(prefs::kDiscardedSnippets), |
| 330 &discarded_snippets_); | 339 &discarded_snippets_); |
| 331 DCHECK(success) << "Failed to parse discarded snippets from prefs"; | 340 DCHECK(success) << "Failed to parse discarded snippets from prefs"; |
| 332 } | 341 } |
| 333 | 342 |
| 334 void NTPSnippetsService::StoreDiscardedSnippetsToPrefs() { | 343 void NTPSnippetsService::StoreDiscardedSnippetsToPrefs() { |
| 335 pref_service_->Set(prefs::kDiscardedSnippets, | 344 pref_service_->Set(prefs::kDiscardedSnippets, |
| 336 *SnippetsToListValue(discarded_snippets_)); | 345 *SnippetsToListValue(discarded_snippets_)); |
| 337 } | 346 } |
| 338 | 347 |
| 348 std::vector<std::string> NTPSnippetsService::GetSnippetHostsFromPrefs() const { | |
| 349 std::vector<std::string> hosts; | |
| 350 const base::ListValue* list = pref_service_->GetList(prefs::kSnippetHosts); | |
| 351 for (const base::Value* value : *list) { | |
| 352 std::string str; | |
| 353 bool success = value->GetAsString(&str); | |
| 354 DCHECK(success) << "Failed to parse snippet host from prefs"; | |
| 355 hosts.push_back(std::move(str)); | |
| 356 } | |
| 357 return hosts; | |
| 358 } | |
| 359 | |
| 360 void NTPSnippetsService::StoreSnippetHostsToPrefs( | |
| 361 const std::vector<std::string>& hosts) { | |
| 362 base::ListValue list; | |
| 363 list.AppendStrings(hosts); | |
| 364 pref_service_->Set(prefs::kSnippetHosts, list); | |
| 365 } | |
| 366 | |
| 339 bool NTPSnippetsService::HasDiscardedSnippet(const GURL& url) const { | 367 bool NTPSnippetsService::HasDiscardedSnippet(const GURL& url) const { |
| 340 auto it = std::find_if(discarded_snippets_.begin(), discarded_snippets_.end(), | 368 auto it = std::find_if(discarded_snippets_.begin(), discarded_snippets_.end(), |
| 341 [&url](const scoped_ptr<NTPSnippet>& snippet) { | 369 [&url](const scoped_ptr<NTPSnippet>& snippet) { |
| 342 return snippet->url() == url; | 370 return snippet->url() == url; |
| 343 }); | 371 }); |
| 344 return it != discarded_snippets_.end(); | 372 return it != discarded_snippets_.end(); |
| 345 } | 373 } |
| 346 | 374 |
| 347 void NTPSnippetsService::RemoveExpiredSnippets() { | 375 void NTPSnippetsService::RemoveExpiredSnippets() { |
| 348 base::Time expiry = base::Time::Now(); | 376 base::Time expiry = base::Time::Now(); |
| (...skipping 30 matching lines...) Expand all Loading... | |
| 379 if (snippet->expiry_date() < next_expiry) | 407 if (snippet->expiry_date() < next_expiry) |
| 380 next_expiry = snippet->expiry_date(); | 408 next_expiry = snippet->expiry_date(); |
| 381 } | 409 } |
| 382 DCHECK_GT(next_expiry, expiry); | 410 DCHECK_GT(next_expiry, expiry); |
| 383 expiry_timer_.Start(FROM_HERE, next_expiry - expiry, | 411 expiry_timer_.Start(FROM_HERE, next_expiry - expiry, |
| 384 base::Bind(&NTPSnippetsService::RemoveExpiredSnippets, | 412 base::Bind(&NTPSnippetsService::RemoveExpiredSnippets, |
| 385 base::Unretained(this))); | 413 base::Unretained(this))); |
| 386 } | 414 } |
| 387 | 415 |
| 388 } // namespace ntp_snippets | 416 } // namespace ntp_snippets |
| OLD | NEW |