summaryrefslogtreecommitdiffstats
path: root/chrome/browser/engagement/site_engagement_eviction_policy_unittest.cc
blob: e621cae3a36aca5eebff41edb0385a4e95d4f73c (plain)
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
159
160
161
162
163
164
165
166
167
168
// Copyright 2015 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 <stdint.h>

#include "base/files/scoped_temp_dir.h"
#include "base/macros.h"
#include "base/memory/scoped_ptr.h"
#include "base/memory/weak_ptr.h"
#include "base/run_loop.h"
#include "base/thread_task_runner_handle.h"
#include "chrome/browser/engagement/site_engagement_eviction_policy.h"
#include "chrome/browser/engagement/site_engagement_service.h"
#include "content/public/test/mock_special_storage_policy.h"
#include "content/public/test/mock_storage_client.h"
#include "content/public/test/test_browser_thread_bundle.h"
#include "storage/browser/quota/quota_manager.h"
#include "storage/browser/quota/quota_manager_proxy.h"
#include "testing/gtest/include/gtest/gtest.h"

namespace {

const int64_t kGlobalQuota = 25 * 1024;

}  // namespace

class TestSiteEngagementScoreProvider : public SiteEngagementScoreProvider {
 public:
  TestSiteEngagementScoreProvider() {}

  virtual ~TestSiteEngagementScoreProvider() {}

  double GetScore(const GURL& url) override {
    return engagement_score_map_[url];
  }

  double GetTotalEngagementPoints() override {
    double total = 0;
    for (const auto& site : engagement_score_map_)
      total += site.second;
    return total;
  }

  void SetScore(const GURL& origin, double score) {
    engagement_score_map_[origin] = score;
  }

 private:
  std::map<GURL, double> engagement_score_map_;

  DISALLOW_COPY_AND_ASSIGN(TestSiteEngagementScoreProvider);
};

class SiteEngagementEvictionPolicyTest : public testing::Test {
 public:
  SiteEngagementEvictionPolicyTest()
      : score_provider_(new TestSiteEngagementScoreProvider()),
        storage_policy_(new content::MockSpecialStoragePolicy()) {}

  ~SiteEngagementEvictionPolicyTest() override {}

  GURL CalculateEvictionOriginWithExceptions(
      const std::map<GURL, int64_t>& usage,
      const std::set<GURL>& exceptions) {
    return SiteEngagementEvictionPolicy::CalculateEvictionOriginForTests(
        storage_policy_, score_provider_.get(), exceptions, usage,
        kGlobalQuota);
  }

  GURL CalculateEvictionOrigin(const std::map<GURL, int64_t>& usage) {
    return CalculateEvictionOriginWithExceptions(usage, std::set<GURL>());
  }

  TestSiteEngagementScoreProvider* score_provider() {
    return score_provider_.get();
  }

  content::MockSpecialStoragePolicy* storage_policy() {
    return storage_policy_.get();
  }

 private:
  scoped_ptr<TestSiteEngagementScoreProvider> score_provider_;
  scoped_refptr<content::MockSpecialStoragePolicy> storage_policy_;

  DISALLOW_COPY_AND_ASSIGN(SiteEngagementEvictionPolicyTest);
};

TEST_F(SiteEngagementEvictionPolicyTest, GetEvictionOrigin) {
  GURL url1("http://www.google.com");
  GURL url2("http://www.example.com");
  GURL url3("http://www.spam.me");

  std::map<GURL, int64_t> usage;
  usage[url1] = 10 * 1024;
  usage[url2] = 10 * 1024;
  usage[url3] = 10 * 1024;

  score_provider()->SetScore(url1, 50);
  score_provider()->SetScore(url2, 25);

  // When 3 sites have equal usage, evict the site with the least engagement.
  EXPECT_EQ(url3, CalculateEvictionOrigin(usage));

  usage[url2] = usage[url3] + 10;

  // Now |url2| has the most usage but |url3| has the least engagement score so
  // one of them should be evicted. In this case the heuristic chooses |url3|.
  EXPECT_EQ(url3, CalculateEvictionOrigin(usage));

  // But exceeding allocated usage too much will still result in being evicted
  // even though the engagement with |url2| is higher.
  usage[url2] = 15 * 1024;
  EXPECT_EQ(url2, CalculateEvictionOrigin(usage));

  // When all origins have the same engagement, the origin with the highest
  // usage is evicted.
  score_provider()->SetScore(url1, 50);
  score_provider()->SetScore(url2, 50);
  score_provider()->SetScore(url3, 50);

  usage[url2] = 10 * 1024;
  usage[url3] = 20 * 1024;
  EXPECT_EQ(url3, CalculateEvictionOrigin(usage));
}

// Test that durable and unlimited storage origins are exempt from eviction.
TEST_F(SiteEngagementEvictionPolicyTest, SpecialStoragePolicy) {
  GURL url1("http://www.google.com");
  GURL url2("http://www.example.com");

  std::map<GURL, int64_t> usage;
  usage[url1] = 10 * 1024;
  usage[url2] = 10 * 1024;

  score_provider()->SetScore(url1, 50);
  score_provider()->SetScore(url2, 25);

  EXPECT_EQ(url2, CalculateEvictionOrigin(usage));

  // Durable storage doesn't get evicted.
  storage_policy()->AddDurable(url2);
  EXPECT_EQ(url1, CalculateEvictionOrigin(usage));

  // Unlimited storage doesn't get evicted.
  storage_policy()->AddUnlimited(url1);
  EXPECT_EQ(GURL(), CalculateEvictionOrigin(usage));
}

TEST_F(SiteEngagementEvictionPolicyTest, Exceptions) {
  GURL url1("http://www.google.com");
  GURL url2("http://www.example.com");

  std::map<GURL, int64_t> usage;
  usage[url1] = 10 * 1024;
  usage[url2] = 10 * 1024;

  score_provider()->SetScore(url1, 50);
  score_provider()->SetScore(url2, 25);

  EXPECT_EQ(url2, CalculateEvictionOrigin(usage));

  // The policy should respect exceptions.
  std::set<GURL> exceptions;
  exceptions.insert(url2);
  EXPECT_EQ(url1, CalculateEvictionOriginWithExceptions(usage, exceptions));
}