Chromium Code Reviews| Index: components/ntp_snippets/remote/remote_suggestions_scheduler.cc |
| diff --git a/components/ntp_snippets/remote/remote_suggestions_scheduler.cc b/components/ntp_snippets/remote/remote_suggestions_scheduler.cc |
| new file mode 100644 |
| index 0000000000000000000000000000000000000000..7d54f537722cdab84e3aeffc1f74fb6cb9200a14 |
| --- /dev/null |
| +++ b/components/ntp_snippets/remote/remote_suggestions_scheduler.cc |
| @@ -0,0 +1,189 @@ |
| +// Copyright 2016 The Chromium Authors. All rights reserved. |
| +// Use of this source code is governed by a BSD-style license that can be |
| +// found in the LICENSE file. |
| + |
| +#include "components/ntp_snippets/remote/remote_suggestions_scheduler.h" |
| + |
| +#include <string> |
| + |
| +#include "components/ntp_snippets/features.h" |
| +#include "components/ntp_snippets/pref_names.h" |
| +#include "components/ntp_snippets/remote/remote_suggestions_hard_scheduler.h" |
| +#include "components/ntp_snippets/user_classifier.h" |
| +#include "components/prefs/pref_registry_simple.h" |
| +#include "components/prefs/pref_service.h" |
| +#include "components/variations/variations_associated_data.h" |
| + |
| +namespace ntp_snippets { |
| + |
| +namespace { |
| + |
| +// Default values for fetching intervals, fallback and wifi. |
| +const double kDefaultFetchingIntervalRareNtpUser[] = {48.0, 24.0}; |
| +const double kDefaultFetchingIntervalActiveNtpUser[] = {24.0, 6.0}; |
| +const double kDefaultFetchingIntervalActiveSuggestionsConsumer[] = {24.0, 6.0}; |
| + |
| +// Variation parameters than can override the default fetching intervals. |
| +const char* kFetchingIntervalParamNameRareNtpUser[] = { |
| + "fetching_interval_hours-fallback-rare_ntp_user", |
| + "fetching_interval_hours-wifi-rare_ntp_user"}; |
| +const char* kFetchingIntervalParamNameActiveNtpUser[] = { |
| + "fetching_interval_hours-fallback-active_ntp_user", |
| + "fetching_interval_hours-wifi-active_ntp_user"}; |
| +const char* kFetchingIntervalParamNameActiveSuggestionsConsumer[] = { |
| + "fetching_interval_hours-fallback-active_suggestions_consumer", |
| + "fetching_interval_hours-wifi-active_suggestions_consumer"}; |
| + |
| +base::TimeDelta GetCurrentUpdateInterval( |
| + bool is_wifi, |
| + UserClassifier::UserClass user_class) { |
| + double default_value_hours = 0.0; |
| + |
| + const int index = is_wifi ? 1 : 0; |
| + const char* param_name = ""; |
|
Marc Treib
2016/12/09 12:25:27
nullptr? The "empty" case can't happen anyway
jkrcal
2016/12/14 09:42:10
Done.
|
| + switch (user_class) { |
| + case UserClassifier::UserClass::RARE_NTP_USER: |
| + default_value_hours = kDefaultFetchingIntervalRareNtpUser[index]; |
| + param_name = kFetchingIntervalParamNameRareNtpUser[index]; |
| + break; |
| + case UserClassifier::UserClass::ACTIVE_NTP_USER: |
| + default_value_hours = kDefaultFetchingIntervalActiveNtpUser[index]; |
| + param_name = kFetchingIntervalParamNameActiveNtpUser[index]; |
| + break; |
| + case UserClassifier::UserClass::ACTIVE_SUGGESTIONS_CONSUMER: |
| + default_value_hours = |
| + kDefaultFetchingIntervalActiveSuggestionsConsumer[index]; |
| + param_name = kFetchingIntervalParamNameActiveSuggestionsConsumer[index]; |
| + break; |
| + } |
| + |
| + double value_hours = variations::GetVariationParamByFeatureAsDouble( |
| + ntp_snippets::kArticleSuggestionsFeature, param_name, |
| + default_value_hours); |
| + |
| + return base::TimeDelta::FromSecondsD(value_hours * 3600.0); |
| +} |
| + |
| +} // namespace |
| + |
| +RemoteSuggestionsScheduler::RemoteSuggestionsScheduler( |
| + RemoteSuggestionsHardScheduler* hard_scheduler, |
| + const UserClassifier* user_classifier, |
| + PrefService* pref_service) |
| + : hard_scheduler_(hard_scheduler), |
| + updater_(nullptr), |
| + user_classifier_(user_classifier), |
| + pref_service_(pref_service) { |
| + DCHECK(user_classifier) << "non-null UserClassifier must be provided"; |
| + DCHECK(pref_service) << "non-null pref service is needed"; |
| +} |
| + |
| +RemoteSuggestionsScheduler::~RemoteSuggestionsScheduler() = default; |
| + |
| +void RemoteSuggestionsScheduler::SetUpdater(Updater* updater) { |
| + DCHECK(updater) << "non-null Updater must be provided"; |
|
Marc Treib
2016/12/09 12:25:27
Since we have to handle a null updater_ anyway, ma
jkrcal
2016/12/14 09:42:10
Done.
|
| + updater_ = updater; |
| +} |
| + |
| +// static |
| +void RemoteSuggestionsScheduler::RegisterProfilePrefs( |
| + PrefRegistrySimple* registry) { |
| + registry->RegisterInt64Pref(prefs::kSnippetBackgroundFetchingIntervalWifi, 0); |
| + registry->RegisterInt64Pref(prefs::kSnippetBackgroundFetchingIntervalFallback, |
| + 0); |
| +} |
| + |
| +void RemoteSuggestionsScheduler::PerformHardUpdate() { |
|
tschumann
2016/12/09 17:27:28
i'm a bit confused. Does this now perform an updat
jkrcal
2016/12/14 09:42:09
It performs it. Is is clearer now in the new desig
|
| + if (!updater_) { |
| + DLOG(WARNING) << "An update is to be performed without having the updater."; |
| + return; |
| + } |
| + |
| + updater_->UpdateRemoteSuggestionsBySchedule(); |
|
Marc Treib
2016/12/09 12:25:27
Hm. So in practice, the OS-scheduled update gets h
markusheintz_
2016/12/12 14:36:16
+1 this hides a simple call and somehow implies th
jkrcal
2016/12/14 09:42:10
Done.
|
| +} |
| + |
| +void RemoteSuggestionsScheduler::Schedule() { |
| + // The scheduler only exists on Android so far, it's null on other platforms. |
| + if (!hard_scheduler_) { |
| + return; |
| + } |
| + |
| + UpdateSchedule last_schedule = GetLastUpdateSchedule(); |
| + UpdateSchedule schedule = GetCurrentUpdateSchedule(); |
| + |
| + // Reset the schedule only if the parameters have changed. |
| + if (last_schedule.interval_wifi != schedule.interval_wifi || |
| + last_schedule.interval_fallback != schedule.interval_fallback) { |
|
Marc Treib
2016/12/09 12:25:26
optional: Could put operator==/!= on the struct? I
jkrcal
2016/12/14 09:42:10
Done.
|
| + ResetUpdateScheduleFromNow(schedule); |
| + } |
| +} |
| + |
| +void RemoteSuggestionsScheduler::Unschedule() { |
| + // The scheduler only exists on Android so far, it's null on other platforms. |
| + if (!hard_scheduler_) { |
| + return; |
| + } |
| + |
| + // Do not unschedule if already switched off |
| + UpdateSchedule last_schedule = GetLastUpdateSchedule(); |
| + if (last_schedule.interval_fallback.is_zero() && |
| + last_schedule.interval_fallback.is_zero()) { |
|
Marc Treib
2016/12/09 12:25:27
Similar here, could put an accessor on the struct.
jkrcal
2016/12/14 09:42:10
Done.
|
| + return; |
| + } |
| + |
| + hard_scheduler_->Unschedule(); |
| + |
| + StoreLastUpdateSchedule(UpdateSchedule{base::TimeDelta::FromHours(0), |
| + base::TimeDelta::FromHours(0)}); |
|
Marc Treib
2016/12/09 12:25:26
Maybe make an UpdateSchedule::Empty() ?
jkrcal
2016/12/14 09:42:10
Done.
|
| +} |
| + |
| +void RemoteSuggestionsScheduler::OnSuccessfulUpdate() { |
| + // The scheduler only exists on Android so far, it's null on other platforms. |
| + if (!hard_scheduler_) { |
| + return; |
| + } |
| + |
| + ResetUpdateScheduleFromNow(GetLastUpdateSchedule()); |
| +} |
| + |
| +void RemoteSuggestionsScheduler::ResetUpdateScheduleFromNow( |
|
tschumann
2016/12/09 17:27:28
the 'fromNow' suffix seems superfluous.
Actually,
jkrcal
2016/12/14 09:42:10
Renamed to ApplyFetchingSchedule(). WDYT?
|
| + UpdateSchedule schedule) { |
| + hard_scheduler_->Schedule(schedule.interval_wifi, schedule.interval_fallback); |
| + |
| + StoreLastUpdateSchedule(schedule); |
| +} |
| + |
| +RemoteSuggestionsScheduler::UpdateSchedule |
| +RemoteSuggestionsScheduler::GetCurrentUpdateSchedule() { |
|
Marc Treib
2016/12/09 12:25:27
Hm, IMO this name is a bit misleading. I'd interpr
jkrcal
2016/12/14 09:42:10
Renamed to GetDesiredUpdateSchedule(). Better?
Marc Treib
2016/12/14 10:47:01
Yup, thanks!
|
| + UserClassifier::UserClass user_class = user_classifier_->GetUserClass(); |
| + |
| + UpdateSchedule schedule; |
| + schedule.interval_wifi = |
| + GetCurrentUpdateInterval(/*is_wifi=*/true, user_class); |
| + schedule.interval_fallback = |
| + GetCurrentUpdateInterval(/*is_wifi=*/false, user_class); |
| + return schedule; |
| +} |
| + |
| +RemoteSuggestionsScheduler::UpdateSchedule |
| +RemoteSuggestionsScheduler::GetLastUpdateSchedule() { |
| + UpdateSchedule schedule; |
| + schedule.interval_wifi = base::TimeDelta::FromInternalValue( |
| + pref_service_->GetInt64(prefs::kSnippetBackgroundFetchingIntervalWifi)); |
| + schedule.interval_fallback = |
| + base::TimeDelta::FromInternalValue(pref_service_->GetInt64( |
| + prefs::kSnippetBackgroundFetchingIntervalFallback)); |
| + return schedule; |
| +} |
| + |
| +void RemoteSuggestionsScheduler::StoreLastUpdateSchedule( |
| + RemoteSuggestionsScheduler::UpdateSchedule schedule) { |
| + pref_service_->SetInt64( |
| + prefs::kSnippetBackgroundFetchingIntervalWifi, |
| + schedule.interval_wifi.ToInternalValue()); |
| + pref_service_->SetInt64( |
| + prefs::kSnippetBackgroundFetchingIntervalFallback, |
| + schedule.interval_fallback.ToInternalValue()); |
| +} |
| + |
| +} // namespace ntp_snippets |