blob: 00370143e0facc86657772669c0997ba27d40e9c [file] [log] [blame]
// 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 CONTENT_PUBLIC_TEST_PRELOADING_TEST_UTIL_H_
#define CONTENT_PUBLIC_TEST_PRELOADING_TEST_UTIL_H_
#include <vector>
#include "base/memory/raw_ptr.h"
#include "components/ukm/test_ukm_recorder.h"
#include "content/public/browser/preloading.h"
#include "content/public/browser/preloading_data.h"
#include "services/metrics/public/cpp/ukm_source_id.h"
#include "third_party/blink/public/mojom/speculation_rules/speculation_rules.mojom-shared.h"
namespace content {
class PreloadingConfig;
namespace test {
// The set of UKM metric names in the PreloadingAttempt and PreloadingPrediction
// UKM logs. This is useful for calling TestUkmRecorder::GetEntries.
extern const std::vector<std::string> kPreloadingAttemptUkmMetrics;
extern const std::vector<std::string> kPreloadingPredictionUkmMetrics;
// Utility class to make building expected
// TestUkmRecorder::HumanReadableUkmEntry for EXPECT_EQ for PreloadingAttempt.
class PreloadingAttemptUkmEntryBuilder {
public:
explicit PreloadingAttemptUkmEntryBuilder(PreloadingPredictor predictor);
// This method assumes a navigation has occurred thus `TimeToNextNavigation`
// is set. Install `base::ScopedMockElapsedTimersForTest` into the test
// fixture to assert the entry's latency values' correctness.
//
// Optional `ready_time` should be set by the caller, if this attempt ever
// reaches `PreloadingTriggeringOutcome::kReady` state, at the time of
// reporting.
ukm::TestUkmRecorder::HumanReadableUkmEntry BuildEntry(
ukm::SourceId source_id,
PreloadingType preloading_type,
PreloadingEligibility eligibility,
PreloadingHoldbackStatus holdback_status,
PreloadingTriggeringOutcome triggering_outcome,
PreloadingFailureReason failure_reason,
bool accurate,
std::optional<base::TimeDelta> ready_time = std::nullopt,
std::optional<blink::mojom::SpeculationEagerness> eagerness =
std::nullopt) const;
private:
PreloadingPredictor predictor_;
};
// Utility class to make building expected
// TestUkmRecorder::HumanReadableUkmEntry for EXPECT_EQ for
// PreloadingPrediction.
class PreloadingPredictionUkmEntryBuilder {
public:
explicit PreloadingPredictionUkmEntryBuilder(PreloadingPredictor predictor);
// This method assumes a navigation has occurred thus `TimeToNextNavigation`
// is set. Install `base::ScopedMockElapsedTimersForTest` into the test
// fixture to assert the entry's latency values' correctness.
ukm::TestUkmRecorder::HumanReadableUkmEntry BuildEntry(
ukm::SourceId source_id,
int64_t confidence,
bool accurate_prediction) const;
private:
PreloadingPredictor predictor_;
};
// Checks if `ukm_recorder` recorded `expected_attempt_entries`. Doesn't care
// about the recording order.
void ExpectPreloadingAttemptUkm(
ukm::TestAutoSetUkmRecorder& ukm_recorder,
const std::vector<ukm::TestUkmRecorder::HumanReadableUkmEntry>&
expected_attempt_entries);
// Checks if `ukm_recorder` recorded `expected_prediction_entries`. Doesn't care
// about the recording order.
void ExpectPreloadingPredictionUkm(
ukm::TestAutoSetUkmRecorder& ukm_recorder,
const std::vector<ukm::TestUkmRecorder::HumanReadableUkmEntry>&
expected_prediction_entries);
// Turns a UKM entry into a human-readable string.
std::string UkmEntryToString(
const ukm::TestUkmRecorder::HumanReadableUkmEntry& entry);
// Turns two UKM entries into a human-readable string.
std::string ActualVsExpectedUkmEntryToString(
const ukm::TestUkmRecorder::HumanReadableUkmEntry& actual,
const ukm::TestUkmRecorder::HumanReadableUkmEntry& expected);
// Turns two collections of UKM entries into human-readable strings.
std::string ActualVsExpectedUkmEntriesToString(
const std::vector<ukm::TestUkmRecorder::HumanReadableUkmEntry>& actual,
const std::vector<ukm::TestUkmRecorder::HumanReadableUkmEntry>& expected);
// Utility class to access internal state from a PreloadingAttempt.
class PreloadingAttemptAccessor {
public:
explicit PreloadingAttemptAccessor(PreloadingAttempt* preloading_attempt);
PreloadingTriggeringOutcome GetTriggeringOutcome();
PreloadingFailureReason GetFailureReason();
private:
raw_ptr<PreloadingAttempt> preloading_attempt_;
};
// Creating a PreloadingConfigOverride will override the current
// PreloadingConfig (which is normally configured via field trial) until
// PreloadingConfigOverride is destroyed. By default the configuration disables
// sampling UKM preloading logs (some log types are sampled by default, which
// can make preloading tests that verify UKM logs flaky) but enables (i.e. does
// not hold back) all preloading features. For testing holdbacks, SetHoldback
// can be called to disable a particular preloading feature.
class PreloadingConfigOverride {
public:
PreloadingConfigOverride();
~PreloadingConfigOverride();
void SetHoldback(PreloadingType preloading_type,
PreloadingPredictor predictor,
bool holdback);
void SetHoldback(std::string_view preloading_type,
std::string_view predictor,
bool holdback);
private:
std::unique_ptr<PreloadingConfig> preloading_config_;
raw_ptr<PreloadingConfig> overridden_config_;
};
} // namespace test
} // namespace content
#endif // CONTENT_PUBLIC_TEST_PRELOADING_TEST_UTIL_H_