group_coordinator_unittest.cc 7.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211
  1. // Copyright 2018 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 "services/audio/test/mock_group_coordinator.h"
  5. #include "base/containers/contains.h"
  6. #include "base/unguessable_token.h"
  7. #include "services/audio/test/mock_group_member.h"
  8. #include "testing/gmock/include/gmock/gmock.h"
  9. #include "testing/gtest/include/gtest/gtest.h"
  10. using base::UnguessableToken;
  11. using testing::AtLeast;
  12. using testing::NiceMock;
  13. using testing::ReturnRef;
  14. using testing::Sequence;
  15. using testing::StrictMock;
  16. using testing::_;
  17. namespace audio {
  18. class TestGroupCoordinator : public GroupCoordinator<MockGroupMember> {
  19. public:
  20. const std::vector<MockGroupMember*>& GetCurrentMembers(
  21. const base::UnguessableToken& group_id) const {
  22. return GetCurrentMembersUnsafe(group_id);
  23. }
  24. };
  25. namespace {
  26. class MockGroupObserver : public TestGroupCoordinator::Observer {
  27. public:
  28. MockGroupObserver() = default;
  29. MockGroupObserver(const MockGroupObserver&) = delete;
  30. MockGroupObserver& operator=(const MockGroupObserver&) = delete;
  31. ~MockGroupObserver() override = default;
  32. MOCK_METHOD1(OnMemberJoinedGroup, void(MockGroupMember* member));
  33. MOCK_METHOD1(OnMemberLeftGroup, void(MockGroupMember* member));
  34. };
  35. TEST(GroupCoordinatorTest, NeverUsed) {
  36. TestGroupCoordinator coordinator;
  37. }
  38. TEST(GroupCoordinatorTest, RegistersMembersInSameGroup) {
  39. const UnguessableToken group_id = UnguessableToken::Create();
  40. StrictMock<MockGroupMember> member1;
  41. StrictMock<MockGroupMember> member2;
  42. // An observer should see each member join and leave the group once.
  43. StrictMock<MockGroupObserver> observer;
  44. Sequence join_leave_sequence;
  45. EXPECT_CALL(observer, OnMemberJoinedGroup(&member1))
  46. .InSequence(join_leave_sequence);
  47. EXPECT_CALL(observer, OnMemberJoinedGroup(&member2))
  48. .InSequence(join_leave_sequence);
  49. EXPECT_CALL(observer, OnMemberLeftGroup(&member1))
  50. .InSequence(join_leave_sequence);
  51. EXPECT_CALL(observer, OnMemberLeftGroup(&member2))
  52. .InSequence(join_leave_sequence);
  53. TestGroupCoordinator coordinator;
  54. coordinator.AddObserver(group_id, &observer);
  55. coordinator.RegisterMember(group_id, &member1);
  56. coordinator.RegisterMember(group_id, &member2);
  57. const std::vector<MockGroupMember*>& members =
  58. coordinator.GetCurrentMembers(group_id);
  59. EXPECT_EQ(2u, members.size());
  60. EXPECT_TRUE(base::Contains(members, &member1));
  61. EXPECT_TRUE(base::Contains(members, &member2));
  62. EXPECT_TRUE(
  63. coordinator.GetCurrentMembers(UnguessableToken::Create()).empty());
  64. coordinator.UnregisterMember(group_id, &member1);
  65. coordinator.UnregisterMember(group_id, &member2);
  66. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id).empty());
  67. coordinator.RemoveObserver(group_id, &observer);
  68. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id).empty());
  69. }
  70. TEST(GroupCoordinatorTest, RegistersMembersInDifferentGroups) {
  71. const UnguessableToken group_id_a = UnguessableToken::Create();
  72. StrictMock<MockGroupMember> member_a_1;
  73. StrictMock<MockGroupMember> member_a_2;
  74. StrictMock<MockGroupObserver> observer_a;
  75. Sequence join_leave_sequence_a;
  76. EXPECT_CALL(observer_a, OnMemberJoinedGroup(&member_a_1))
  77. .InSequence(join_leave_sequence_a);
  78. EXPECT_CALL(observer_a, OnMemberJoinedGroup(&member_a_2))
  79. .InSequence(join_leave_sequence_a);
  80. EXPECT_CALL(observer_a, OnMemberLeftGroup(&member_a_1))
  81. .InSequence(join_leave_sequence_a);
  82. EXPECT_CALL(observer_a, OnMemberLeftGroup(&member_a_2))
  83. .InSequence(join_leave_sequence_a);
  84. const UnguessableToken group_id_b = UnguessableToken::Create();
  85. StrictMock<MockGroupMember> member_b_1;
  86. StrictMock<MockGroupObserver> observer_b;
  87. Sequence join_leave_sequence_b;
  88. EXPECT_CALL(observer_b, OnMemberJoinedGroup(&member_b_1))
  89. .InSequence(join_leave_sequence_b);
  90. EXPECT_CALL(observer_b, OnMemberLeftGroup(&member_b_1))
  91. .InSequence(join_leave_sequence_b);
  92. TestGroupCoordinator coordinator;
  93. coordinator.AddObserver(group_id_a, &observer_a);
  94. coordinator.AddObserver(group_id_b, &observer_b);
  95. coordinator.RegisterMember(group_id_a, &member_a_1);
  96. coordinator.RegisterMember(group_id_b, &member_b_1);
  97. coordinator.RegisterMember(group_id_a, &member_a_2);
  98. const std::vector<MockGroupMember*>& members_a =
  99. coordinator.GetCurrentMembers(group_id_a);
  100. EXPECT_EQ(2u, members_a.size());
  101. EXPECT_TRUE(base::Contains(members_a, &member_a_1));
  102. EXPECT_TRUE(base::Contains(members_a, &member_a_2));
  103. EXPECT_EQ(std::vector<MockGroupMember*>({&member_b_1}),
  104. coordinator.GetCurrentMembers(group_id_b));
  105. EXPECT_TRUE(
  106. coordinator.GetCurrentMembers(UnguessableToken::Create()).empty());
  107. coordinator.UnregisterMember(group_id_a, &member_a_1);
  108. EXPECT_EQ(std::vector<MockGroupMember*>({&member_a_2}),
  109. coordinator.GetCurrentMembers(group_id_a));
  110. coordinator.UnregisterMember(group_id_b, &member_b_1);
  111. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id_b).empty());
  112. coordinator.UnregisterMember(group_id_a, &member_a_2);
  113. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id_a).empty());
  114. coordinator.RemoveObserver(group_id_a, &observer_a);
  115. coordinator.RemoveObserver(group_id_b, &observer_b);
  116. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id_a).empty());
  117. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id_b).empty());
  118. }
  119. TEST(GroupCoordinatorTest, TracksMembersWithoutAnObserverPresent) {
  120. const UnguessableToken group_id = UnguessableToken::Create();
  121. StrictMock<MockGroupMember> member1;
  122. StrictMock<MockGroupMember> member2;
  123. TestGroupCoordinator coordinator;
  124. coordinator.RegisterMember(group_id, &member1);
  125. coordinator.RegisterMember(group_id, &member2);
  126. const std::vector<MockGroupMember*>& members =
  127. coordinator.GetCurrentMembers(group_id);
  128. EXPECT_EQ(2u, members.size());
  129. EXPECT_TRUE(base::Contains(members, &member1));
  130. EXPECT_TRUE(base::Contains(members, &member2));
  131. EXPECT_TRUE(
  132. coordinator.GetCurrentMembers(UnguessableToken::Create()).empty());
  133. coordinator.UnregisterMember(group_id, &member1);
  134. coordinator.UnregisterMember(group_id, &member2);
  135. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id).empty());
  136. }
  137. TEST(GroupCoordinatorTest, NotifiesOnlyWhileObserving) {
  138. const UnguessableToken group_id = UnguessableToken::Create();
  139. StrictMock<MockGroupMember> member1;
  140. StrictMock<MockGroupMember> member2;
  141. // The observer will only be around at the time when member2 joins the group
  142. // and when member1 leaves the group.
  143. StrictMock<MockGroupObserver> observer;
  144. Sequence join_leave_sequence;
  145. EXPECT_CALL(observer, OnMemberJoinedGroup(&member1)).Times(0);
  146. EXPECT_CALL(observer, OnMemberJoinedGroup(&member2))
  147. .InSequence(join_leave_sequence);
  148. EXPECT_CALL(observer, OnMemberLeftGroup(&member1))
  149. .InSequence(join_leave_sequence);
  150. EXPECT_CALL(observer, OnMemberLeftGroup(&member2)).Times(0);
  151. TestGroupCoordinator coordinator;
  152. coordinator.RegisterMember(group_id, &member1);
  153. EXPECT_EQ(std::vector<MockGroupMember*>({&member1}),
  154. coordinator.GetCurrentMembers(group_id));
  155. coordinator.AddObserver(group_id, &observer);
  156. coordinator.RegisterMember(group_id, &member2);
  157. const std::vector<MockGroupMember*>& members =
  158. coordinator.GetCurrentMembers(group_id);
  159. EXPECT_EQ(2u, members.size());
  160. EXPECT_TRUE(base::Contains(members, &member1));
  161. EXPECT_TRUE(base::Contains(members, &member2));
  162. coordinator.UnregisterMember(group_id, &member1);
  163. EXPECT_EQ(std::vector<MockGroupMember*>({&member2}),
  164. coordinator.GetCurrentMembers(group_id));
  165. coordinator.RemoveObserver(group_id, &observer);
  166. EXPECT_EQ(std::vector<MockGroupMember*>({&member2}),
  167. coordinator.GetCurrentMembers(group_id));
  168. coordinator.UnregisterMember(group_id, &member2);
  169. EXPECT_TRUE(coordinator.GetCurrentMembers(group_id).empty());
  170. }
  171. } // namespace
  172. } // namespace audio