Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(656)

Side by Side Diff: content/browser/media/session/media_session_impl_visibility_browsertest.cc

Issue 2453623003: Decouple MediaSession messages from WebContents (full patch) (Closed)
Patch Set: nit Created 4 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 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 <tuple> 5 #include <tuple>
6 6
7 #include "base/command_line.h" 7 #include "base/command_line.h"
8 #include "base/location.h" 8 #include "base/location.h"
9 #include "base/logging.h" 9 #include "base/logging.h"
10 #include "base/single_thread_task_runner.h" 10 #include "base/single_thread_task_runner.h"
11 #include "base/threading/thread_task_runner_handle.h" 11 #include "base/threading/thread_task_runner_handle.h"
12 #include "content/browser/media/session/media_session.h" 12 #include "content/browser/media/session/media_session_impl.h"
13 #include "content/public/browser/web_contents.h" 13 #include "content/public/browser/web_contents.h"
14 #include "content/public/common/content_switches.h" 14 #include "content/public/common/content_switches.h"
15 #include "content/public/test/browser_test_utils.h" 15 #include "content/public/test/browser_test_utils.h"
16 #include "content/public/test/content_browser_test.h" 16 #include "content/public/test/content_browser_test.h"
17 #include "content/public/test/content_browser_test_utils.h" 17 #include "content/public/test/content_browser_test_utils.h"
18 #include "content/public/test/test_navigation_observer.h" 18 #include "content/public/test/test_navigation_observer.h"
19 #include "content/shell/browser/shell.h" 19 #include "content/shell/browser/shell.h"
20 #include "media/base/media_switches.h" 20 #include "media/base/media_switches.h"
21 #include "testing/gtest/include/gtest/gtest.h" 21 #include "testing/gtest/include/gtest/gtest.h"
22 22
(...skipping 24 matching lines...) Expand all
47 SUSPENDED, 47 SUSPENDED,
48 INACTIVE, 48 INACTIVE,
49 }; 49 };
50 50
51 struct VisibilityTestData { 51 struct VisibilityTestData {
52 MediaSuspend media_suspend; 52 MediaSuspend media_suspend;
53 BackgroundResuming background_resuming; 53 BackgroundResuming background_resuming;
54 SessionState session_state_before_hide; 54 SessionState session_state_before_hide;
55 SessionState session_state_after_hide; 55 SessionState session_state_after_hide;
56 }; 56 };
57
58 } 57 }
59 58
60
61 // Base class of MediaSession visibility tests. The class is intended 59 // Base class of MediaSession visibility tests. The class is intended
62 // to be used to run tests under different configurations. Tests 60 // to be used to run tests under different configurations. Tests
63 // should inheret from this class, set up their own command line per 61 // should inheret from this class, set up their own command line per
64 // their configuration, and use macro INCLUDE_TEST_FROM_BASE_CLASS to 62 // their configuration, and use macro INCLUDE_TEST_FROM_BASE_CLASS to
65 // include required tests. See 63 // include required tests. See
66 // media_session_visibility_browsertest_instances.cc for examples. 64 // media_session_visibility_browsertest_instances.cc for examples.
67 class MediaSessionVisibilityBrowserTest 65 class MediaSessionImplVisibilityBrowserTest
68 : public ContentBrowserTest, 66 : public ContentBrowserTest,
69 public ::testing::WithParamInterface< 67 public ::testing::WithParamInterface<
70 std::tr1::tuple<VisibilityTestData, Pipeline>> { 68 std::tr1::tuple<VisibilityTestData, Pipeline>> {
71 public: 69 public:
72 MediaSessionVisibilityBrowserTest() = default; 70 MediaSessionImplVisibilityBrowserTest() = default;
73 ~MediaSessionVisibilityBrowserTest() override = default; 71 ~MediaSessionImplVisibilityBrowserTest() override = default;
74 72
75 void SetUpOnMainThread() override { 73 void SetUpOnMainThread() override {
76 ContentBrowserTest::SetUpOnMainThread(); 74 ContentBrowserTest::SetUpOnMainThread();
77 web_contents_ = shell()->web_contents(); 75 web_contents_ = shell()->web_contents();
78 media_session_ = MediaSession::Get(web_contents_); 76 media_session_ = MediaSessionImpl::Get(web_contents_);
79 77
80 media_session_state_loop_runners_[MediaSession::State::ACTIVE] = 78 media_session_state_loop_runners_[MediaSessionImpl::State::ACTIVE] =
81 new MessageLoopRunner(); 79 new MessageLoopRunner();
82 media_session_state_loop_runners_[MediaSession::State::SUSPENDED] = 80 media_session_state_loop_runners_[MediaSessionImpl::State::SUSPENDED] =
83 new MessageLoopRunner(); 81 new MessageLoopRunner();
84 media_session_state_loop_runners_[MediaSession::State::INACTIVE] = 82 media_session_state_loop_runners_[MediaSessionImpl::State::INACTIVE] =
85 new MessageLoopRunner(); 83 new MessageLoopRunner();
86 media_session_state_callback_subscription_ = 84 media_session_state_callback_subscription_ =
87 media_session_->RegisterMediaSessionStateChangedCallbackForTest( 85 media_session_->RegisterMediaSessionStateChangedCallbackForTest(
88 base::Bind(&MediaSessionVisibilityBrowserTest:: 86 base::Bind(&MediaSessionImplVisibilityBrowserTest::
89 OnMediaSessionStateChanged, 87 OnMediaSessionStateChanged,
90 base::Unretained(this))); 88 base::Unretained(this)));
91 } 89 }
92 90
93 void TearDownOnMainThread() override { 91 void TearDownOnMainThread() override {
94 // Unsubscribe the callback subscription before tearing down, so that the 92 // Unsubscribe the callback subscription before tearing down, so that the
95 // CallbackList in MediaSession will be empty when it is destroyed. 93 // CallbackList in MediaSession will be empty when it is destroyed.
96 media_session_state_callback_subscription_.reset(); 94 media_session_state_callback_subscription_.reset();
97 } 95 }
98 96
99 void EnableDisableResumingBackgroundVideos(bool enable) { 97 void EnableDisableResumingBackgroundVideos(bool enable) {
100 std::string enabled_features; 98 std::string enabled_features;
101 std::string disabled_features; 99 std::string disabled_features;
102 if (enable) 100 if (enable)
103 enabled_features = media::kResumeBackgroundVideo.name; 101 enabled_features = media::kResumeBackgroundVideo.name;
104 else 102 else
105 disabled_features = media::kResumeBackgroundVideo.name; 103 disabled_features = media::kResumeBackgroundVideo.name;
106 104
107 std::unique_ptr<base::FeatureList> feature_list(new base::FeatureList); 105 std::unique_ptr<base::FeatureList> feature_list(new base::FeatureList);
108 feature_list->InitializeFromCommandLine( 106 feature_list->InitializeFromCommandLine(enabled_features,
109 enabled_features, disabled_features); 107 disabled_features);
110 base::FeatureList::ClearInstanceForTesting(); 108 base::FeatureList::ClearInstanceForTesting();
111 base::FeatureList::SetInstance(std::move(feature_list)); 109 base::FeatureList::SetInstance(std::move(feature_list));
112 } 110 }
113 111
114 void SetUpCommandLine(base::CommandLine* command_line) override { 112 void SetUpCommandLine(base::CommandLine* command_line) override {
115 command_line->AppendSwitch( 113 command_line->AppendSwitch(
116 switches::kDisableGestureRequirementForMediaPlayback); 114 switches::kDisableGestureRequirementForMediaPlayback);
117 #if !defined(OS_ANDROID) 115 #if !defined(OS_ANDROID)
118 command_line->AppendSwitch( 116 command_line->AppendSwitch(switches::kEnableDefaultMediaSession);
119 switches::kEnableDefaultMediaSession);
120 #endif // !defined(OS_ANDROID) 117 #endif // !defined(OS_ANDROID)
121 118
122 VisibilityTestData params = GetVisibilityTestData(); 119 VisibilityTestData params = GetVisibilityTestData();
123 120
124 if (params.media_suspend == MediaSuspend::ENABLED) 121 if (params.media_suspend == MediaSuspend::ENABLED)
125 command_line->AppendSwitch(switches::kEnableMediaSuspend); 122 command_line->AppendSwitch(switches::kEnableMediaSuspend);
126 else 123 else
127 command_line->AppendSwitch(switches::kDisableMediaSuspend); 124 command_line->AppendSwitch(switches::kDisableMediaSuspend);
128 125
129 #if defined(OS_ANDROID) 126 #if defined(OS_ANDROID)
(...skipping 15 matching lines...) Expand all
145 return std::tr1::get<0>(GetParam()); 142 return std::tr1::get<0>(GetParam());
146 } 143 }
147 144
148 void StartPlayer() { 145 void StartPlayer() {
149 LoadTestPage(); 146 LoadTestPage();
150 147
151 LOG(INFO) << "Starting player"; 148 LOG(INFO) << "Starting player";
152 ClearMediaSessionStateLoopRunners(); 149 ClearMediaSessionStateLoopRunners();
153 RunScript(kStartPlayerScript); 150 RunScript(kStartPlayerScript);
154 LOG(INFO) << "Waiting for session to be active"; 151 LOG(INFO) << "Waiting for session to be active";
155 WaitForMediaSessionState(MediaSession::State::ACTIVE); 152 WaitForMediaSessionState(MediaSessionImpl::State::ACTIVE);
156 } 153 }
157 154
158 // Maybe pause the player depending on whether the session state before hide 155 // Maybe pause the player depending on whether the session state before hide
159 // is SUSPENDED. 156 // is SUSPENDED.
160 void MaybePausePlayer() { 157 void MaybePausePlayer() {
161 ASSERT_TRUE(GetVisibilityTestData().session_state_before_hide 158 ASSERT_TRUE(GetVisibilityTestData().session_state_before_hide !=
162 != SessionState::INACTIVE); 159 SessionState::INACTIVE);
163 if (GetVisibilityTestData().session_state_before_hide 160 if (GetVisibilityTestData().session_state_before_hide ==
164 == SessionState::ACTIVE) 161 SessionState::ACTIVE)
165 return; 162 return;
166 163
167 LOG(INFO) << "Pausing player"; 164 LOG(INFO) << "Pausing player";
168 ClearMediaSessionStateLoopRunners(); 165 ClearMediaSessionStateLoopRunners();
169 RunScript(kPausePlayerScript); 166 RunScript(kPausePlayerScript);
170 LOG(INFO) << "Waiting for session to be suspended"; 167 LOG(INFO) << "Waiting for session to be suspended";
171 WaitForMediaSessionState(MediaSession::State::SUSPENDED); 168 WaitForMediaSessionState(MediaSessionImpl::State::SUSPENDED);
172 } 169 }
173 170
174 void HideTab() { 171 void HideTab() {
175 LOG(INFO) << "Hiding the tab"; 172 LOG(INFO) << "Hiding the tab";
176 ClearMediaSessionStateLoopRunners(); 173 ClearMediaSessionStateLoopRunners();
177 web_contents_->WasHidden(); 174 web_contents_->WasHidden();
178 } 175 }
179 176
180 void CheckSessionStateAfterHide() { 177 void CheckSessionStateAfterHide() {
181 MediaSession::State state_before_hide = 178 MediaSessionImpl::State state_before_hide =
182 ToMediaSessionState(GetVisibilityTestData().session_state_before_hide); 179 ToMediaSessionState(GetVisibilityTestData().session_state_before_hide);
183 MediaSession::State state_after_hide = 180 MediaSessionImpl::State state_after_hide =
184 ToMediaSessionState(GetVisibilityTestData().session_state_after_hide); 181 ToMediaSessionState(GetVisibilityTestData().session_state_after_hide);
185 182
186 if (state_before_hide == state_after_hide) { 183 if (state_before_hide == state_after_hide) {
187 LOG(INFO) << "Waiting for 1 second and check session state is unchanged"; 184 LOG(INFO) << "Waiting for 1 second and check session state is unchanged";
188 Wait(base::TimeDelta::FromSeconds(1)); 185 Wait(base::TimeDelta::FromSeconds(1));
189 ASSERT_EQ(media_session_->audio_focus_state_, state_after_hide); 186 ASSERT_EQ(media_session_->audio_focus_state_, state_after_hide);
190 } else { 187 } else {
191 LOG(INFO) << "Waiting for Session to change"; 188 LOG(INFO) << "Waiting for Session to change";
192 WaitForMediaSessionState(state_after_hide); 189 WaitForMediaSessionState(state_after_hide);
193 } 190 }
(...skipping 10 matching lines...) Expand all
204 201
205 void RunScript(const std::string& script) { 202 void RunScript(const std::string& script) {
206 ASSERT_TRUE(ExecuteScript(web_contents_->GetMainFrame(), script)); 203 ASSERT_TRUE(ExecuteScript(web_contents_->GetMainFrame(), script));
207 } 204 }
208 205
209 void ClearMediaSessionStateLoopRunners() { 206 void ClearMediaSessionStateLoopRunners() {
210 for (auto& state_loop_runner : media_session_state_loop_runners_) 207 for (auto& state_loop_runner : media_session_state_loop_runners_)
211 state_loop_runner.second = new MessageLoopRunner(); 208 state_loop_runner.second = new MessageLoopRunner();
212 } 209 }
213 210
214 void OnMediaSessionStateChanged(MediaSession::State state) { 211 void OnMediaSessionStateChanged(MediaSessionImpl::State state) {
215 ASSERT_TRUE(media_session_state_loop_runners_.count(state)); 212 ASSERT_TRUE(media_session_state_loop_runners_.count(state));
216 media_session_state_loop_runners_[state]->Quit(); 213 media_session_state_loop_runners_[state]->Quit();
217 } 214 }
218 215
219 // TODO(zqzhang): This method is shared with 216 // TODO(zqzhang): This method is shared with
220 // MediaRouterIntegrationTests. Move it into a general place. 217 // MediaRouterIntegrationTests. Move it into a general place.
221 void Wait(base::TimeDelta timeout) { 218 void Wait(base::TimeDelta timeout) {
222 base::RunLoop run_loop; 219 base::RunLoop run_loop;
223 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask( 220 base::ThreadTaskRunnerHandle::Get()->PostDelayedTask(
224 FROM_HERE, run_loop.QuitClosure(), timeout); 221 FROM_HERE, run_loop.QuitClosure(), timeout);
225 run_loop.Run(); 222 run_loop.Run();
226 } 223 }
227 224
228 void WaitForMediaSessionState(MediaSession::State state) { 225 void WaitForMediaSessionState(MediaSessionImpl::State state) {
229 ASSERT_TRUE(media_session_state_loop_runners_.count(state)); 226 ASSERT_TRUE(media_session_state_loop_runners_.count(state));
230 media_session_state_loop_runners_[state]->Run(); 227 media_session_state_loop_runners_[state]->Run();
231 } 228 }
232 229
233 MediaSession::State ToMediaSessionState(SessionState state) { 230 MediaSessionImpl::State ToMediaSessionState(SessionState state) {
234 switch (state) { 231 switch (state) {
235 case SessionState::ACTIVE: 232 case SessionState::ACTIVE:
236 return MediaSession::State::ACTIVE; 233 return MediaSessionImpl::State::ACTIVE;
237 break; 234 break;
238 case SessionState::SUSPENDED: 235 case SessionState::SUSPENDED:
239 return MediaSession::State::SUSPENDED; 236 return MediaSessionImpl::State::SUSPENDED;
240 break; 237 break;
241 case SessionState::INACTIVE: 238 case SessionState::INACTIVE:
242 return MediaSession::State::INACTIVE; 239 return MediaSessionImpl::State::INACTIVE;
243 break; 240 break;
244 default: 241 default:
245 ADD_FAILURE() << "invalid SessionState to convert"; 242 ADD_FAILURE() << "invalid SessionState to convert";
246 return MediaSession::State::INACTIVE; 243 return MediaSessionImpl::State::INACTIVE;
247 } 244 }
248 } 245 }
249 246
250 WebContents* web_contents_; 247 WebContents* web_contents_;
251 MediaSession* media_session_; 248 MediaSessionImpl* media_session_;
252 // MessageLoopRunners for waiting MediaSession state to change. Note that the 249 // MessageLoopRunners for waiting MediaSession state to change. Note that the
253 // MessageLoopRunners can accept Quit() before calling Run(), thus the state 250 // MessageLoopRunners can accept Quit() before calling Run(), thus the state
254 // change can still be captured before waiting. For example, the MediaSession 251 // change can still be captured before waiting. For example, the MediaSession
255 // might go active immediately after calling HTMLMediaElement.play(). A test 252 // might go active immediately after calling HTMLMediaElement.play(). A test
256 // can listen to the state change before calling play(), and then wait for the 253 // can listen to the state change before calling play(), and then wait for the
257 // state change after play(). 254 // state change after play().
258 std::map<MediaSession::State, scoped_refptr<MessageLoopRunner> > 255 std::map<MediaSessionImpl::State, scoped_refptr<MessageLoopRunner>>
259 media_session_state_loop_runners_; 256 media_session_state_loop_runners_;
260 std::unique_ptr<base::CallbackList<void(MediaSession::State)>::Subscription> 257 std::unique_ptr<
258 base::CallbackList<void(MediaSessionImpl::State)>::Subscription>
261 media_session_state_callback_subscription_; 259 media_session_state_callback_subscription_;
262 260
263 DISALLOW_COPY_AND_ASSIGN(MediaSessionVisibilityBrowserTest); 261 DISALLOW_COPY_AND_ASSIGN(MediaSessionImplVisibilityBrowserTest);
264 }; 262 };
265 263
266 namespace { 264 namespace {
267 265
268 VisibilityTestData kTestParams[] = { 266 VisibilityTestData kTestParams[] = {
269 { MediaSuspend::ENABLED, BackgroundResuming::DISABLED, 267 {MediaSuspend::ENABLED, BackgroundResuming::DISABLED,
270 SessionState::SUSPENDED, SessionState::INACTIVE }, 268 SessionState::SUSPENDED, SessionState::INACTIVE},
271 { MediaSuspend::ENABLED, BackgroundResuming::DISABLED, 269 {MediaSuspend::ENABLED, BackgroundResuming::DISABLED, SessionState::ACTIVE,
272 SessionState::ACTIVE, SessionState::INACTIVE }, 270 SessionState::INACTIVE},
273 { MediaSuspend::ENABLED, BackgroundResuming::ENABLED, 271 {MediaSuspend::ENABLED, BackgroundResuming::ENABLED, SessionState::ACTIVE,
274 SessionState::ACTIVE, SessionState::SUSPENDED }, 272 SessionState::SUSPENDED},
275 { MediaSuspend::ENABLED, BackgroundResuming::ENABLED, 273 {MediaSuspend::ENABLED, BackgroundResuming::ENABLED,
276 SessionState::SUSPENDED, SessionState::SUSPENDED }, 274 SessionState::SUSPENDED, SessionState::SUSPENDED},
277 { MediaSuspend::DISABLED, BackgroundResuming::DISABLED, 275 {MediaSuspend::DISABLED, BackgroundResuming::DISABLED,
278 SessionState::SUSPENDED, SessionState::SUSPENDED }, 276 SessionState::SUSPENDED, SessionState::SUSPENDED},
279 { MediaSuspend::DISABLED, BackgroundResuming::DISABLED, 277 {MediaSuspend::DISABLED, BackgroundResuming::DISABLED, SessionState::ACTIVE,
280 SessionState::ACTIVE, SessionState::ACTIVE }, 278 SessionState::ACTIVE},
281 { MediaSuspend::DISABLED, BackgroundResuming::ENABLED, 279 {MediaSuspend::DISABLED, BackgroundResuming::ENABLED, SessionState::ACTIVE,
282 SessionState::ACTIVE, SessionState::ACTIVE }, 280 SessionState::ACTIVE},
283 { MediaSuspend::DISABLED, BackgroundResuming::ENABLED, 281 {MediaSuspend::DISABLED, BackgroundResuming::ENABLED,
284 SessionState::SUSPENDED, SessionState::SUSPENDED }, 282 SessionState::SUSPENDED, SessionState::SUSPENDED},
285 }; 283 };
286 284
287 Pipeline kPipelines[] = { 285 Pipeline kPipelines[] = {
288 Pipeline::WMPI, 286 Pipeline::WMPI,
289 #if defined(OS_ANDROID) 287 #if defined(OS_ANDROID)
290 // Disabling WMPA tests because of https://crbug.com/646312 288 // Disabling WMPA tests because of https://crbug.com/646312
291 // Pipeline::WMPA, 289 // Pipeline::WMPA,
292 #endif // defined(OS_ANDROID) 290 #endif // defined(OS_ANDROID)
293 }; 291 };
294 292
295 } // anonymous namespace 293 } // anonymous namespace
296 294
297 IN_PROC_BROWSER_TEST_P(MediaSessionVisibilityBrowserTest, 295 IN_PROC_BROWSER_TEST_P(MediaSessionImplVisibilityBrowserTest, TestEntryPoint) {
298 TestEntryPoint) {
299 StartPlayer(); 296 StartPlayer();
300 MaybePausePlayer(); 297 MaybePausePlayer();
301 HideTab(); 298 HideTab();
302 CheckSessionStateAfterHide(); 299 CheckSessionStateAfterHide();
303 } 300 }
304 301
305 INSTANTIATE_TEST_CASE_P(MediaSessionVisibilityBrowserTestInstances, 302 INSTANTIATE_TEST_CASE_P(MediaSessionImplVisibilityBrowserTestInstances,
306 MediaSessionVisibilityBrowserTest, 303 MediaSessionImplVisibilityBrowserTest,
307 ::testing::Combine(::testing::ValuesIn(kTestParams), 304 ::testing::Combine(::testing::ValuesIn(kTestParams),
308 ::testing::ValuesIn(kPipelines))); 305 ::testing::ValuesIn(kPipelines)));
309 306
310 } // namespace content 307 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698