scoped_observation_unittest.cc 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151
  1. // Copyright 2020 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #include "base/scoped_observation.h"
  5. #include "base/containers/contains.h"
  6. #include "base/ranges/algorithm.h"
  7. #include "base/test/gtest_util.h"
  8. #include "testing/gtest/include/gtest/gtest.h"
  9. namespace base {
  10. namespace {
  11. class TestSourceObserver {};
  12. class TestSource {
  13. public:
  14. void AddObserver(TestSourceObserver* observer);
  15. void RemoveObserver(TestSourceObserver* observer);
  16. bool HasObserver(TestSourceObserver* observer) const;
  17. size_t num_observers() const { return observers_.size(); }
  18. private:
  19. std::vector<TestSourceObserver*> observers_;
  20. };
  21. void TestSource::AddObserver(TestSourceObserver* observer) {
  22. observers_.push_back(observer);
  23. }
  24. void TestSource::RemoveObserver(TestSourceObserver* observer) {
  25. auto it = base::ranges::find(observers_, observer);
  26. EXPECT_TRUE(it != observers_.end());
  27. observers_.erase(it);
  28. }
  29. bool TestSource::HasObserver(TestSourceObserver* observer) const {
  30. return base::Contains(observers_, observer);
  31. }
  32. using TestScopedObservation = ScopedObservation<TestSource, TestSourceObserver>;
  33. } // namespace
  34. TEST(ScopedObservationTest, RemovesObservationOnDestruction) {
  35. TestSource s1;
  36. {
  37. TestSourceObserver o1;
  38. TestScopedObservation obs(&o1);
  39. EXPECT_EQ(0u, s1.num_observers());
  40. EXPECT_FALSE(s1.HasObserver(&o1));
  41. obs.Observe(&s1);
  42. EXPECT_EQ(1u, s1.num_observers());
  43. EXPECT_TRUE(s1.HasObserver(&o1));
  44. }
  45. // Test that the observation is removed when it goes out of scope.
  46. EXPECT_EQ(0u, s1.num_observers());
  47. }
  48. TEST(ScopedObservationTest, Reset) {
  49. TestSource s1;
  50. TestSourceObserver o1;
  51. TestScopedObservation obs(&o1);
  52. EXPECT_EQ(0u, s1.num_observers());
  53. obs.Reset();
  54. obs.Observe(&s1);
  55. EXPECT_EQ(1u, s1.num_observers());
  56. EXPECT_TRUE(s1.HasObserver(&o1));
  57. obs.Reset();
  58. EXPECT_EQ(0u, s1.num_observers());
  59. // Safe to call with no observation.
  60. obs.Reset();
  61. EXPECT_EQ(0u, s1.num_observers());
  62. }
  63. TEST(ScopedObservationTest, IsObserving) {
  64. TestSource s1;
  65. TestSourceObserver o1;
  66. TestScopedObservation obs(&o1);
  67. EXPECT_FALSE(obs.IsObserving());
  68. obs.Observe(&s1);
  69. EXPECT_TRUE(obs.IsObserving());
  70. obs.Reset();
  71. EXPECT_FALSE(obs.IsObserving());
  72. }
  73. TEST(ScopedObservationTest, IsObservingSource) {
  74. TestSource s1;
  75. TestSource s2;
  76. TestSourceObserver o1;
  77. TestScopedObservation obs(&o1);
  78. EXPECT_FALSE(obs.IsObservingSource(&s1));
  79. EXPECT_FALSE(obs.IsObservingSource(&s2));
  80. obs.Observe(&s1);
  81. EXPECT_TRUE(obs.IsObservingSource(&s1));
  82. EXPECT_FALSE(obs.IsObservingSource(&s2));
  83. obs.Reset();
  84. EXPECT_FALSE(obs.IsObservingSource(&s1));
  85. EXPECT_FALSE(obs.IsObservingSource(&s2));
  86. }
  87. namespace {
  88. // A test source with oddly named Add/Remove functions.
  89. class TestSourceWithNonDefaultNames {
  90. public:
  91. void AddFoo(TestSourceObserver* observer) { impl_.AddObserver(observer); }
  92. void RemoveFoo(TestSourceObserver* observer) {
  93. impl_.RemoveObserver(observer);
  94. }
  95. const TestSource& impl() const { return impl_; }
  96. private:
  97. TestSource impl_;
  98. };
  99. using TestScopedObservationWithNonDefaultNames =
  100. ScopedObservation<TestSourceWithNonDefaultNames,
  101. TestSourceObserver,
  102. &TestSourceWithNonDefaultNames::AddFoo,
  103. &TestSourceWithNonDefaultNames::RemoveFoo>;
  104. } // namespace
  105. TEST(ScopedObservationTest, NonDefaultNames) {
  106. TestSourceWithNonDefaultNames s1;
  107. TestSourceObserver o1;
  108. EXPECT_EQ(0u, s1.impl().num_observers());
  109. {
  110. TestScopedObservationWithNonDefaultNames obs(&o1);
  111. obs.Observe(&s1);
  112. EXPECT_EQ(1u, s1.impl().num_observers());
  113. EXPECT_TRUE(s1.impl().HasObserver(&o1));
  114. }
  115. }
  116. } // namespace base