Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include <string> | |
| 6 #include <vector> | |
| 7 | |
| 5 #include "base/bind.h" | 8 #include "base/bind.h" |
| 6 #include "base/memory/scoped_ptr.h" | 9 #include "base/memory/scoped_ptr.h" |
| 7 #include "base/message_loop/message_loop.h" | 10 #include "base/message_loop/message_loop.h" |
| 8 #include "base/test/simple_test_tick_clock.h" | 11 #include "base/test/simple_test_tick_clock.h" |
| 9 #include "base/timer/mock_timer.h" | 12 #include "base/timer/mock_timer.h" |
| 10 #include "components/copresence/handlers/audio/audio_directive_handler_impl.h" | 13 #include "components/copresence/handlers/audio/audio_directive_handler_impl.h" |
| 11 #include "components/copresence/handlers/audio/tick_clock_ref_counted.h" | 14 #include "components/copresence/handlers/audio/tick_clock_ref_counted.h" |
| 12 #include "components/copresence/mediums/audio/audio_manager.h" | 15 #include "components/copresence/mediums/audio/audio_manager.h" |
| 13 #include "components/copresence/proto/data.pb.h" | 16 #include "components/copresence/proto/data.pb.h" |
| 14 #include "components/copresence/test/audio_test_support.h" | 17 #include "components/copresence/test/audio_test_support.h" |
| 15 #include "testing/gtest/include/gtest/gtest.h" | 18 #include "testing/gtest/include/gtest/gtest.h" |
| 16 | 19 |
| 17 namespace copresence { | 20 namespace copresence { |
| 18 | 21 |
| 22 namespace { | |
| 23 | |
| 24 const Directive CreateDirective(TokenInstructionType type, | |
| 25 bool audible, | |
| 26 int64 ttl) { | |
| 27 Directive directive; | |
| 28 directive.mutable_token_instruction()->set_token_instruction_type(type); | |
| 29 directive.mutable_token_instruction()->set_token_id("token"); | |
| 30 directive.mutable_token_instruction()->set_medium(audible ? | |
| 31 AUDIO_AUDIBLE_DTMF : AUDIO_ULTRASOUND_PASSBAND); | |
| 32 directive.set_ttl_millis(ttl); | |
| 33 return directive; | |
| 34 } | |
| 35 | |
| 36 | |
|
xiyuan
2014/12/18 18:10:52
nit: nuke one empty line
Charlie
2014/12/19 03:53:33
Done.
| |
| 37 } // namespace | |
| 38 | |
| 19 class AudioManagerStub final : public AudioManager { | 39 class AudioManagerStub final : public AudioManager { |
| 20 public: | 40 public: |
| 21 AudioManagerStub() {} | 41 AudioManagerStub() {} |
| 22 ~AudioManagerStub() override {} | 42 ~AudioManagerStub() override {} |
| 23 | 43 |
| 24 // AudioManager overrides: | 44 // AudioManager overrides: |
| 25 void Initialize(WhispernetClient* whispernet_client, | 45 void Initialize(WhispernetClient* whispernet_client, |
| 26 const TokensCallback& tokens_cb) override {} | 46 const TokensCallback& tokens_cb) override {} |
| 27 void StartPlaying(AudioType type) override { playing_[type] = true; } | 47 void StartPlaying(AudioType type) override { playing_[type] = true; } |
| 28 void StopPlaying(AudioType type) override { playing_[type] = false; } | 48 void StopPlaying(AudioType type) override { playing_[type] = false; } |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 43 }; | 63 }; |
| 44 | 64 |
| 45 class AudioDirectiveHandlerTest : public testing::Test { | 65 class AudioDirectiveHandlerTest : public testing::Test { |
| 46 public: | 66 public: |
| 47 AudioDirectiveHandlerTest() { | 67 AudioDirectiveHandlerTest() { |
| 48 manager_ptr_ = new AudioManagerStub; | 68 manager_ptr_ = new AudioManagerStub; |
| 49 timer_ptr_ = new base::MockTimer(false, false); | 69 timer_ptr_ = new base::MockTimer(false, false); |
| 50 clock_ptr_ = new base::SimpleTestTickClock; | 70 clock_ptr_ = new base::SimpleTestTickClock; |
| 51 | 71 |
| 52 directive_handler_.reset(new AudioDirectiveHandlerImpl( | 72 directive_handler_.reset(new AudioDirectiveHandlerImpl( |
| 73 base::Bind(&AudioDirectiveHandlerTest::GetDirectiveUpdates, | |
| 74 base::Unretained(this)), | |
| 53 make_scoped_ptr<AudioManager>(manager_ptr_), | 75 make_scoped_ptr<AudioManager>(manager_ptr_), |
| 54 make_scoped_ptr<base::Timer>(timer_ptr_), | 76 make_scoped_ptr<base::Timer>(timer_ptr_), |
| 55 make_scoped_refptr(new TickClockRefCounted(clock_ptr_)))); | 77 make_scoped_refptr(new TickClockRefCounted(clock_ptr_)))); |
| 56 directive_handler_->Initialize(nullptr, TokensCallback()); | 78 directive_handler_->Initialize(nullptr, TokensCallback()); |
| 57 } | 79 } |
| 58 ~AudioDirectiveHandlerTest() override {} | 80 ~AudioDirectiveHandlerTest() override {} |
| 59 | 81 |
| 60 protected: | 82 protected: |
| 61 TokenInstruction CreateTransmitInstruction(const std::string& token, | 83 const std::vector<Directive>& current_directives() { |
| 62 bool audible) { | 84 return current_directives_; |
| 63 TokenInstruction instruction; | |
| 64 instruction.set_token_instruction_type(TRANSMIT); | |
| 65 instruction.set_token_id(token); | |
| 66 instruction.set_medium(audible ? AUDIO_AUDIBLE_DTMF | |
| 67 : AUDIO_ULTRASOUND_PASSBAND); | |
| 68 return instruction; | |
| 69 } | |
| 70 | |
| 71 TokenInstruction CreateReceiveInstruction(bool audible) { | |
| 72 TokenInstruction instruction; | |
| 73 instruction.set_token_instruction_type(RECEIVE); | |
| 74 instruction.set_medium(audible ? AUDIO_AUDIBLE_DTMF | |
| 75 : AUDIO_ULTRASOUND_PASSBAND); | |
| 76 return instruction; | |
| 77 } | 85 } |
| 78 | 86 |
| 79 bool IsPlaying(AudioType type) { return manager_ptr_->IsPlaying(type); } | 87 bool IsPlaying(AudioType type) { return manager_ptr_->IsPlaying(type); } |
| 80 | 88 |
| 81 bool IsRecording(AudioType type) { return manager_ptr_->IsRecording(type); } | 89 bool IsRecording(AudioType type) { return manager_ptr_->IsRecording(type); } |
| 82 | 90 |
| 83 // This order is important. We want the message loop to get created before | 91 // This order is important. We want the message loop to get created before |
| 84 // our the audio directive handler since the directive list ctor (invoked | 92 // our the audio directive handler since the directive list ctor (invoked |
| 85 // from the directive handler ctor) will post tasks. | 93 // from the directive handler ctor) will post tasks. |
| 86 base::MessageLoop message_loop_; | 94 base::MessageLoop message_loop_; |
| 87 scoped_ptr<AudioDirectiveHandler> directive_handler_; | 95 scoped_ptr<AudioDirectiveHandler> directive_handler_; |
| 88 | 96 |
| 97 std::vector<Directive> current_directives_; | |
| 98 | |
| 89 // Unowned. | 99 // Unowned. |
| 90 AudioManagerStub* manager_ptr_; | 100 AudioManagerStub* manager_ptr_; |
| 91 base::MockTimer* timer_ptr_; | 101 base::MockTimer* timer_ptr_; |
| 92 base::SimpleTestTickClock* clock_ptr_; | 102 base::SimpleTestTickClock* clock_ptr_; |
| 93 | 103 |
| 94 private: | 104 private: |
| 105 void GetDirectiveUpdates(const std::vector<Directive>& current_directives) { | |
| 106 current_directives_ = current_directives; | |
| 107 } | |
| 108 | |
| 95 DISALLOW_COPY_AND_ASSIGN(AudioDirectiveHandlerTest); | 109 DISALLOW_COPY_AND_ASSIGN(AudioDirectiveHandlerTest); |
| 96 }; | 110 }; |
| 97 | 111 |
| 98 TEST_F(AudioDirectiveHandlerTest, Basic) { | 112 TEST_F(AudioDirectiveHandlerTest, Basic) { |
| 99 const base::TimeDelta kTtl = base::TimeDelta::FromMilliseconds(9999); | 113 const int64 kTtl = 10; |
| 100 directive_handler_->AddInstruction( | 114 directive_handler_->AddInstruction(CreateDirective(TRANSMIT, true, kTtl), |
| 101 CreateTransmitInstruction("token", true), "op_id1", kTtl); | 115 "op_id1"); |
| 102 directive_handler_->AddInstruction( | 116 directive_handler_->AddInstruction(CreateDirective(TRANSMIT, false, kTtl), |
| 103 CreateTransmitInstruction("token", false), "op_id1", kTtl); | 117 "op_id1"); |
| 104 directive_handler_->AddInstruction( | 118 directive_handler_->AddInstruction(CreateDirective(TRANSMIT, false, kTtl), |
| 105 CreateTransmitInstruction("token", false), "op_id2", kTtl); | 119 "op_id2"); |
| 106 directive_handler_->AddInstruction( | 120 directive_handler_->AddInstruction(CreateDirective(RECEIVE, false, kTtl), |
| 107 CreateReceiveInstruction(false), "op_id1", kTtl); | 121 "op_id1"); |
| 108 directive_handler_->AddInstruction( | 122 directive_handler_->AddInstruction(CreateDirective(RECEIVE, true, kTtl), |
| 109 CreateReceiveInstruction(true), "op_id2", kTtl); | 123 "op_id2"); |
| 110 directive_handler_->AddInstruction( | 124 directive_handler_->AddInstruction(CreateDirective(RECEIVE, false, kTtl), |
| 111 CreateReceiveInstruction(false), "op_id3", kTtl); | 125 "op_id3"); |
| 112 | 126 |
| 113 EXPECT_TRUE(IsPlaying(AUDIBLE)); | 127 EXPECT_TRUE(IsPlaying(AUDIBLE)); |
| 114 EXPECT_TRUE(IsPlaying(INAUDIBLE)); | 128 EXPECT_TRUE(IsPlaying(INAUDIBLE)); |
| 115 EXPECT_TRUE(IsRecording(AUDIBLE)); | 129 EXPECT_TRUE(IsRecording(AUDIBLE)); |
| 116 EXPECT_TRUE(IsRecording(INAUDIBLE)); | 130 EXPECT_TRUE(IsRecording(INAUDIBLE)); |
| 117 | 131 |
| 118 directive_handler_->RemoveInstructions("op_id1"); | 132 directive_handler_->RemoveInstructions("op_id1"); |
| 119 EXPECT_FALSE(IsPlaying(AUDIBLE)); | 133 EXPECT_FALSE(IsPlaying(AUDIBLE)); |
| 120 EXPECT_TRUE(IsPlaying(INAUDIBLE)); | 134 EXPECT_TRUE(IsPlaying(INAUDIBLE)); |
| 121 EXPECT_TRUE(IsRecording(AUDIBLE)); | 135 EXPECT_TRUE(IsRecording(AUDIBLE)); |
| 122 EXPECT_TRUE(IsRecording(INAUDIBLE)); | 136 EXPECT_TRUE(IsRecording(INAUDIBLE)); |
| 123 | 137 |
| 124 directive_handler_->RemoveInstructions("op_id2"); | 138 directive_handler_->RemoveInstructions("op_id2"); |
| 125 EXPECT_FALSE(IsPlaying(INAUDIBLE)); | 139 EXPECT_FALSE(IsPlaying(INAUDIBLE)); |
| 126 EXPECT_FALSE(IsRecording(AUDIBLE)); | 140 EXPECT_FALSE(IsRecording(AUDIBLE)); |
| 127 EXPECT_TRUE(IsRecording(INAUDIBLE)); | 141 EXPECT_TRUE(IsRecording(INAUDIBLE)); |
| 128 | 142 |
| 129 directive_handler_->RemoveInstructions("op_id3"); | 143 directive_handler_->RemoveInstructions("op_id3"); |
| 130 EXPECT_FALSE(IsRecording(INAUDIBLE)); | 144 EXPECT_FALSE(IsRecording(INAUDIBLE)); |
| 131 } | 145 } |
| 132 | 146 |
| 133 TEST_F(AudioDirectiveHandlerTest, Timed) { | 147 TEST_F(AudioDirectiveHandlerTest, Timed) { |
| 134 const base::TimeDelta kTtl1 = base::TimeDelta::FromMilliseconds(1337); | 148 directive_handler_->AddInstruction(CreateDirective(TRANSMIT, true, 6), |
| 135 directive_handler_->AddInstruction( | 149 "op_id1"); |
| 136 CreateTransmitInstruction("token", true), "op_id1", kTtl1); | 150 directive_handler_->AddInstruction(CreateDirective(TRANSMIT, false, 8), |
| 151 "op_id1"); | |
| 152 directive_handler_->AddInstruction(CreateDirective(RECEIVE, false, 4), | |
| 153 "op_id3"); | |
| 137 | 154 |
| 138 const base::TimeDelta kTtl2 = base::TimeDelta::FromMilliseconds(1338); | |
| 139 directive_handler_->AddInstruction( | |
| 140 CreateTransmitInstruction("token", false), "op_id1", kTtl2); | |
| 141 | |
| 142 const base::TimeDelta kTtl3 = base::TimeDelta::FromMilliseconds(1336); | |
| 143 directive_handler_->AddInstruction( | |
| 144 CreateReceiveInstruction(false), "op_id3", kTtl3); | |
| 145 EXPECT_TRUE(IsPlaying(AUDIBLE)); | 155 EXPECT_TRUE(IsPlaying(AUDIBLE)); |
| 146 EXPECT_TRUE(IsPlaying(INAUDIBLE)); | 156 EXPECT_TRUE(IsPlaying(INAUDIBLE)); |
| 147 EXPECT_FALSE(IsRecording(AUDIBLE)); | 157 EXPECT_FALSE(IsRecording(AUDIBLE)); |
| 148 EXPECT_TRUE(IsRecording(INAUDIBLE)); | 158 EXPECT_TRUE(IsRecording(INAUDIBLE)); |
| 149 | 159 |
| 150 // We *have* to call an operation on the directive handler after we advance | 160 // Every time we advance and a directive expires, the timer should fire also. |
| 151 // time to trigger the next set of operations, so ensure that after calling | 161 clock_ptr_->Advance(base::TimeDelta::FromMilliseconds(5)); |
| 152 // advance, we are also calling another operation. | 162 timer_ptr_->Fire(); |
| 153 clock_ptr_->Advance(kTtl3 + base::TimeDelta::FromMilliseconds(1)); | |
| 154 | 163 |
| 155 // We are now at base + 1337ms. | 164 // We are now at +5ms. This instruction expires at +10ms. |
| 156 // This instruction expires at base + (1337 + 1337 = 2674) | 165 directive_handler_->AddInstruction(CreateDirective(RECEIVE, true, 5), |
| 157 directive_handler_->AddInstruction( | 166 "op_id4"); |
| 158 CreateReceiveInstruction(true), "op_id4", kTtl1); | |
| 159 EXPECT_TRUE(IsPlaying(AUDIBLE)); | 167 EXPECT_TRUE(IsPlaying(AUDIBLE)); |
| 160 EXPECT_TRUE(IsPlaying(INAUDIBLE)); | 168 EXPECT_TRUE(IsPlaying(INAUDIBLE)); |
| 161 EXPECT_TRUE(IsRecording(AUDIBLE)); | 169 EXPECT_TRUE(IsRecording(AUDIBLE)); |
| 162 EXPECT_FALSE(IsRecording(INAUDIBLE)); | 170 EXPECT_FALSE(IsRecording(INAUDIBLE)); |
| 163 | 171 |
| 164 clock_ptr_->Advance(base::TimeDelta::FromMilliseconds(1)); | 172 // Advance to +7ms. |
| 173 const base::TimeDelta twoMs = base::TimeDelta::FromMilliseconds(2); | |
| 174 clock_ptr_->Advance(twoMs); | |
| 175 timer_ptr_->Fire(); | |
| 165 | 176 |
| 166 // We are now at base + 1338ms. | |
| 167 timer_ptr_->Fire(); | |
| 168 EXPECT_FALSE(IsPlaying(AUDIBLE)); | 177 EXPECT_FALSE(IsPlaying(AUDIBLE)); |
| 169 EXPECT_TRUE(IsPlaying(INAUDIBLE)); | 178 EXPECT_TRUE(IsPlaying(INAUDIBLE)); |
| 170 EXPECT_TRUE(IsRecording(AUDIBLE)); | 179 EXPECT_TRUE(IsRecording(AUDIBLE)); |
| 171 | 180 |
| 172 clock_ptr_->Advance(base::TimeDelta::FromMilliseconds(1)); | 181 // Advance to +9ms. |
| 173 | 182 clock_ptr_->Advance(twoMs); |
| 174 // We are now at base + 1339ms. | |
| 175 timer_ptr_->Fire(); | 183 timer_ptr_->Fire(); |
| 176 EXPECT_FALSE(IsPlaying(INAUDIBLE)); | 184 EXPECT_FALSE(IsPlaying(INAUDIBLE)); |
| 177 EXPECT_TRUE(IsRecording(AUDIBLE)); | 185 EXPECT_TRUE(IsRecording(AUDIBLE)); |
| 178 | 186 |
| 179 clock_ptr_->Advance(kTtl3); | 187 // Advance to +11ms. |
| 180 | 188 clock_ptr_->Advance(twoMs); |
| 181 // We are now at base + 2676ms. | |
| 182 timer_ptr_->Fire(); | 189 timer_ptr_->Fire(); |
| 183 EXPECT_FALSE(IsRecording(AUDIBLE)); | 190 EXPECT_FALSE(IsRecording(AUDIBLE)); |
| 184 } | 191 } |
| 185 | 192 |
| 186 // TODO(rkc): Write more tests that check more convoluted sequences of | 193 // TODO(rkc): Write more tests that check more convoluted sequences of |
| 187 // transmits/receives. | 194 // transmits/receives. |
| 188 | 195 |
| 189 } // namespace copresence | 196 } // namespace copresence |
| OLD | NEW |