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
|
// Copyright 2021 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "chrome/test/base/web_feature_histogram_tester.h"
#include <utility>
#include "base/threading/platform_thread.h"
#include "base/time/time.h"
#include "components/metrics/content/subprocess_metrics_provider.h"
#include "content/public/test/browser_test_utils.h"
#include "testing/gmock/include/gmock/gmock.h"
namespace {
using blink::mojom::WebFeature;
using testing::_;
using testing::Each;
using testing::Ge;
using testing::Pair;
constexpr char kFeatureHistogramName[] = "Blink.UseCounter.Features";
void FetchCounts() {
content::FetchHistogramsFromChildProcesses();
metrics::SubprocessMetricsProvider::MergeHistogramDeltasForTesting();
}
// Returns the list of keys in the given map.
std::vector<WebFeature> Keys(const std::map<WebFeature, int>& counts) {
std::vector<WebFeature> keys;
for (const auto& entry : counts) {
keys.push_back(entry.first);
}
return keys;
}
bool AllCountsAreLessThanOrEqual(const std::map<WebFeature, int>& lhs,
const std::map<WebFeature, int>& rhs) {
// Prints both sets of keys in case of mismatch, for debugging.
EXPECT_EQ(Keys(lhs), Keys(rhs));
for (const auto& entry : lhs) {
WebFeature feature = entry.first;
int lhs_count = entry.second;
const auto it = rhs.find(feature);
if (it == rhs.end()) {
return false;
}
int rhs_count = it->second;
if (lhs_count > rhs_count) {
return false;
}
}
return true;
}
} // namespace
std::map<WebFeature, int> AllZeroFeatureCounts(
const std::vector<WebFeature>& features) {
std::map<WebFeature, int> result;
for (WebFeature feature : features) {
result.emplace(feature, 0);
}
return result;
}
std::map<WebFeature, int> AddFeatureCounts(
const std::map<WebFeature, int>& lhs,
const std::map<WebFeature, int>& rhs) {
std::map<WebFeature, int> result = lhs;
for (const auto& entry : rhs) {
result[entry.first] += entry.second;
}
return result;
}
WebFeatureHistogramTester::WebFeatureHistogramTester() = default;
WebFeatureHistogramTester::~WebFeatureHistogramTester() = default;
int WebFeatureHistogramTester::GetCountInternal(WebFeature feature) const {
return histogram_tester_.GetBucketCount(kFeatureHistogramName, feature);
}
int WebFeatureHistogramTester::GetCount(WebFeature feature) const {
FetchCounts();
return GetCountInternal(feature);
}
std::map<WebFeature, int> WebFeatureHistogramTester::GetCounts(
const std::vector<WebFeature>& features) const {
FetchCounts();
return GetCountsInternal(features, true);
}
std::map<WebFeature, int> WebFeatureHistogramTester::GetNonZeroCounts(
const std::vector<WebFeature>& features) const {
FetchCounts();
return GetCountsInternal(features, false);
}
std::map<WebFeature, int> WebFeatureHistogramTester::GetCountsInternal(
const std::vector<WebFeature>& features,
bool include_zeroes) const {
std::map<WebFeature, int> counts;
for (WebFeature feature : features) {
int count = GetCountInternal(feature);
if (count == 0 && !include_zeroes) {
continue;
}
counts.emplace(feature, count);
}
return counts;
}
std::map<WebFeature, int> WebFeatureHistogramTester::WaitForCountsAtLeast(
const std::map<WebFeature, int>& expected) const {
EXPECT_THAT(expected, Each(Pair(_, Ge(0))))
<< "All counts must be non-negative.";
std::vector<WebFeature> features = Keys(expected);
std::map<WebFeature, int> counts;
while (true) {
counts = GetCounts(features);
if (!AllCountsAreLessThanOrEqual(counts, expected) || counts == expected) {
break;
}
base::PlatformThread::Sleep(base::Milliseconds(5));
}
return expected;
}
void WebFeatureHistogramTester::ExpectCounts(
const std::map<WebFeature, int>& expected) const {
EXPECT_EQ(WaitForCountsAtLeast(expected), expected);
}
|