blob: 3a88cdca33791cc6a036d7b0ef4a3b97be41c440 [file] [log] [blame]
// Copyright 2017 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/contextual/contextual_content_suggestions_service.h"
#include <iterator>
#include <memory>
#include <set>
#include <utility>
#include "base/bind.h"
#include "base/memory/ptr_util.h"
#include "components/ntp_snippets/contextual/contextual_content_suggestions_service_proxy.h"
#include "components/ntp_snippets/contextual/contextual_suggestions_features.h"
#include "components/ntp_snippets/contextual/contextual_suggestions_result.h"
#include "components/ntp_snippets/remote/remote_suggestions_provider_impl.h"
namespace contextual_suggestions {
using ntp_snippets::ContentSuggestion;
using ntp_snippets::RemoteSuggestionsDatabase;
namespace {
bool IsEligibleURL(const GURL& url) {
return url.is_valid() && url.SchemeIsHTTPOrHTTPS() && !url.HostIsIPAddress();
}
} // namespace
ContextualContentSuggestionsService::ContextualContentSuggestionsService(
std::unique_ptr<ContextualSuggestionsFetcher>
contextual_suggestions_fetcher,
std::unique_ptr<ContextualSuggestionsReporterProvider> reporter_provider)
: fetch_cache_(kFetchCacheCapacity),
contextual_suggestions_fetcher_(
std::move(contextual_suggestions_fetcher)),
reporter_provider_(std::move(reporter_provider)) {}
ContextualContentSuggestionsService::~ContextualContentSuggestionsService() =
default;
void ContextualContentSuggestionsService::FetchContextualSuggestionClusters(
const GURL& url,
FetchClustersCallback callback,
ReportFetchMetricsCallback metrics_callback) {
// TODO(pnoland): Also check that the url is safe.
ContextualSuggestionsResult result;
if (IsEligibleURL(url) && !fetch_cache_.GetSuggestionsResult(url, &result)) {
FetchClustersCallback internal_callback = base::BindOnce(
&ContextualContentSuggestionsService::FetchDone, base::Unretained(this),
url, std::move(callback), metrics_callback);
contextual_suggestions_fetcher_->FetchContextualSuggestionsClusters(
url, std::move(internal_callback), metrics_callback);
} else if (result.peek_conditions.confidence < GetMinimumConfidence()) {
BelowConfidenceThresholdFetchDone(std::move(callback), metrics_callback);
} else {
std::move(callback).Run(result);
}
}
void ContextualContentSuggestionsService::FetchDone(
const GURL& url,
FetchClustersCallback callback,
ReportFetchMetricsCallback metrics_callback,
ContextualSuggestionsResult result) {
// We still want to cache low confidence results so that we avoid doing
// unnecessary fetches.
if (result.clusters.size() > 0) {
fetch_cache_.AddSuggestionsResult(url, result);
}
if (result.peek_conditions.confidence < GetMinimumConfidence()) {
BelowConfidenceThresholdFetchDone(std::move(callback), metrics_callback);
return;
}
std::move(callback).Run(result);
}
ContextualSuggestionsDebuggingReporter*
ContextualContentSuggestionsService::GetDebuggingReporter() {
return reporter_provider_->GetDebuggingReporter();
}
base::flat_map<GURL, ContextualSuggestionsResult>
ContextualContentSuggestionsService::GetAllCachedResultsForDebugging() {
return fetch_cache_.GetAllCachedResultsForDebugging();
}
void ContextualContentSuggestionsService::ClearCachedResultsForDebugging() {
fetch_cache_.Clear();
}
std::unique_ptr<
contextual_suggestions::ContextualContentSuggestionsServiceProxy>
ContextualContentSuggestionsService::CreateProxy() {
return std::make_unique<
contextual_suggestions::ContextualContentSuggestionsServiceProxy>(
this, reporter_provider_->CreateReporter());
}
void ContextualContentSuggestionsService::BelowConfidenceThresholdFetchDone(
FetchClustersCallback callback,
ReportFetchMetricsCallback metrics_callback) {
metrics_callback.Run(contextual_suggestions::FETCH_BELOW_THRESHOLD);
std::move(callback).Run(ContextualSuggestionsResult("", {}, PeekConditions(),
ServerExperimentInfos()));
}
} // namespace contextual_suggestions