1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158
|
// Copyright 2022 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef COMPONENTS_BROWSING_TOPICS_BROWSING_TOPICS_CALCULATOR_H_
#define COMPONENTS_BROWSING_TOPICS_BROWSING_TOPICS_CALCULATOR_H_
#include <map>
#include <set>
#include "base/containers/queue.h"
#include "base/functional/callback.h"
#include "base/memory/raw_ptr.h"
#include "base/task/cancelable_task_tracker.h"
#include "base/time/time.h"
#include "base/timer/timer.h"
#include "components/browsing_topics/annotator.h"
#include "components/browsing_topics/common/common_types.h"
#include "components/browsing_topics/epoch_topics.h"
#include "components/history/core/browser/history_types.h"
namespace privacy_sandbox {
class PrivacySandboxSettings;
} // namespace privacy_sandbox
namespace history {
class HistoryService;
} // namespace history
namespace content {
class BrowsingTopicsSiteDataManager;
} // namespace content
namespace browsing_topics {
// Responsible for doing a one-off browsing topics calculation. It will:
// 1) Check the user settings for calculation permissions.
// 2) Query the `BrowsingTopicsSiteDataManager` for the contexts where the
// Topics API was called on.
// 3) Query the `HistoryService` for the hosts of the pages the API was called
// on.
// 4) Query the `Annotator` with a set of hosts, to get the corresponding
// topics.
// 5) Derive `EpochTopics` (i.e. the top topics and the their observed-by
// contexts), and return it as the final result.
class BrowsingTopicsCalculator {
public:
using CalculateCompletedCallback = base::OnceCallback<void(EpochTopics)>;
BrowsingTopicsCalculator(
privacy_sandbox::PrivacySandboxSettings* privacy_sandbox_settings,
history::HistoryService* history_service,
content::BrowsingTopicsSiteDataManager* site_data_manager,
Annotator* annotator,
const base::circular_deque<EpochTopics>& epochs,
bool is_manually_triggered,
int previous_timeout_count,
base::Time session_start_time,
CalculateCompletedCallback callback);
BrowsingTopicsCalculator(const BrowsingTopicsCalculator&) = delete;
BrowsingTopicsCalculator& operator=(const BrowsingTopicsCalculator&) = delete;
BrowsingTopicsCalculator(BrowsingTopicsCalculator&&) = delete;
BrowsingTopicsCalculator& operator=(BrowsingTopicsCalculator&&) = delete;
virtual ~BrowsingTopicsCalculator();
bool is_manually_triggered() const { return is_manually_triggered_; }
int previous_timeout_count() const { return previous_timeout_count_; }
protected:
// This method exists for the purposes of overriding in tests.
virtual uint64_t GenerateRandUint64();
virtual void CheckCanCalculate();
private:
enum class Progress {
kStarted,
kApiUsageRequested,
kHistoryRequested,
kModelRequested,
kAnnotationRequested,
kCompleted,
};
// Get the top `kBrowsingTopicsNumberOfTopTopicsPerEpoch` topics. If there
// aren't enough topics, pad with random ones. Return the result topics, and
// the starting index of the padded topics (or
// `kBrowsingTopicsNumberOfTopTopicsPerEpoch` if there's no padded topics),
// and the number of topics associated with `history_hosts_count`.
void DeriveTopTopics(
const std::map<HashedHost, size_t>& history_hosts_count,
const std::map<HashedHost, std::set<Topic>>& host_topics_map,
std::vector<Topic>& top_topics,
size_t& padded_top_topics_start_index,
size_t& history_topics_count);
void OnGetRecentBrowsingTopicsApiUsagesCompleted(
browsing_topics::ApiUsageContextQueryResult result);
void OnGetRecentlyVisitedURLsCompleted(history::QueryResults results);
void OnRequestModelCompleted(std::vector<std::string> raw_hosts);
void OnGetTopicsForHostsCompleted(const std::vector<Annotation>& results);
void OnCalculateCompleted(EpochTopics epoch_topics);
void OnCalculationHanging();
// Those pointers are safe to hold and use throughout the lifetime of
// `BrowsingTopicsService`, which owns this object.
raw_ptr<privacy_sandbox::PrivacySandboxSettings> privacy_sandbox_settings_;
raw_ptr<history::HistoryService> history_service_;
raw_ptr<content::BrowsingTopicsSiteDataManager> site_data_manager_;
raw_ptr<Annotator> annotator_;
CalculateCompletedCallback calculate_completed_callback_;
// The calculation start time.
base::Time calculation_time_;
base::Time history_data_start_time_;
base::Time api_usage_context_data_start_time_;
Progress progress_ = Progress::kStarted;
// The history hosts over
// `kBrowsingTopicsNumberOfEpochsOfObservationDataToUseForFiltering` epochs,
// and the calling context domains that used the Topics API in each main frame
// host.
std::map<HashedHost, std::vector<HashedDomain>> host_context_domains_map_;
// The hashed history hosts and their count over the last epoch.
std::map<HashedHost, size_t> history_hosts_count_;
// Used for the async tasks querying the HistoryService.
base::CancelableTaskTracker history_task_tracker_;
// Whether this calculator was generated via the topics-internals page rather
// than via a scheduled task.
bool is_manually_triggered_;
// The number of previous hanging calculations.
int previous_timeout_count_;
// The timeout timer for each async operation.
base::OneShotTimer timeout_timer_;
base::Time session_start_time_;
base::WeakPtrFactory<BrowsingTopicsCalculator> weak_ptr_factory_{this};
};
} // namespace browsing_topics
#endif // COMPONENTS_BROWSING_TOPICS_BROWSING_TOPICS_CALCULATOR_H_
|