1 // Copyright 2015 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.
6 #include "base/memory/scoped_ptr.h"
7 #include "base/strings/stringprintf.h"
8 #include "chrome/browser/media/router/media_route.h"
9 #include "chrome/browser/media/router/media_source_helper.h"
10 #include "chrome/browser/media/router/mock_media_router.h"
11 #include "chrome/browser/media/router/presentation_session_state_observer.h"
12 #include "content/public/browser/presentation_session.h"
13 #include "testing/gmock/include/gmock/gmock.h"
14 #include "testing/gtest/include/gtest/gtest.h"
18 namespace media_router
{
22 const char kPresentationUrl
[] = "http://foo";
23 const char kPresentationId
[] = "presentationId";
25 MediaRoute::Id
CreateRouteId(const char* presentation_url
,
26 const char* presentation_id
) {
27 return base::StringPrintf("urn:x-org.chromium:media:route:%s/cast-sink1/%s",
28 presentation_id
, presentation_url
);
31 MATCHER_P(PresentationSessionInfoEquals
, expected
, "") {
32 return arg
.presentation_url
== expected
.presentation_url
&&
33 arg
.presentation_id
== expected
.presentation_id
;
38 class PresentationSessionStateObserverTest
: public testing::Test
{
40 PresentationSessionStateObserverTest() {}
41 ~PresentationSessionStateObserverTest() override
{}
44 void SetUp() override
{
45 EXPECT_CALL(router_
, RegisterMediaRoutesObserver(_
));
46 observer_
.reset(new PresentationSessionStateObserver(
47 base::Bind(&PresentationSessionStateObserverTest::OnSessionStateChanged
,
48 base::Unretained(this)),
49 &route_id_to_presentation_
, &router_
));
50 MediaRoute::Id
route_id(CreateRouteId(kPresentationUrl
, kPresentationId
));
51 content::PresentationSessionInfo
session_info(kPresentationUrl
,
53 route_id_to_presentation_
.Add(route_id
, session_info
);
56 void TearDown() override
{
58 EXPECT_CALL(router_
, UnregisterMediaRoutesObserver(_
));
63 MOCK_METHOD2(OnSessionStateChanged
,
64 void(const content::PresentationSessionInfo
& session_info
,
65 content::PresentationSessionState new_state
));
67 MockMediaRouter router_
;
68 MediaRouteIdToPresentationSessionMapping route_id_to_presentation_
;
69 scoped_ptr
<PresentationSessionStateObserver
> observer_
;
72 TEST_F(PresentationSessionStateObserverTest
, InvokeCallbackWithConnected
) {
74 *this, OnSessionStateChanged(
75 PresentationSessionInfoEquals(content::PresentationSessionInfo(
76 kPresentationUrl
, kPresentationId
)),
77 content::PRESENTATION_SESSION_STATE_CONNECTED
));
78 MediaRoute::Id
route_id(CreateRouteId(kPresentationUrl
, kPresentationId
));
79 observer_
->OnPresentationSessionConnected(route_id
);
82 TEST_F(PresentationSessionStateObserverTest
, InvokeCallbackWithDisconnected
) {
83 content::PresentationSessionInfo
session_info(kPresentationUrl
,
85 EXPECT_CALL(*this, OnSessionStateChanged(
86 PresentationSessionInfoEquals(session_info
),
87 content::PRESENTATION_SESSION_STATE_CONNECTED
));
88 MediaRoute::Id
route_id(CreateRouteId(kPresentationUrl
, kPresentationId
));
89 observer_
->OnPresentationSessionConnected(route_id
);
91 // Route list update is expected to follow creation of route.
92 std::vector
<MediaRoute
> routes
;
94 MediaRoute(route_id
, MediaSourceForPresentationUrl(kPresentationUrl
),
95 MediaSink("sinkId", "A sink"), "Description", true, ""));
96 observer_
->OnRoutesUpdated(routes
);
98 // New route list does not contain |route_id|, which means it is disconnected.
99 EXPECT_CALL(*this, OnSessionStateChanged(
100 PresentationSessionInfoEquals(session_info
),
101 content::PRESENTATION_SESSION_STATE_DISCONNECTED
));
102 observer_
->OnRoutesUpdated(std::vector
<MediaRoute
>());
104 // Note that it is normally not possible for |route_id| to reappear. But in
105 // case it does, test that it does NOT invoke the callback with CONNECTED.
106 EXPECT_TRUE(testing::Mock::VerifyAndClearExpectations(this));
107 observer_
->OnRoutesUpdated(routes
);
110 TEST_F(PresentationSessionStateObserverTest
, Reset
) {
111 content::PresentationSessionInfo
session_info(kPresentationUrl
,
113 EXPECT_CALL(*this, OnSessionStateChanged(
114 PresentationSessionInfoEquals(session_info
),
115 content::PRESENTATION_SESSION_STATE_CONNECTED
));
116 MediaRoute::Id
route_id(CreateRouteId(kPresentationUrl
, kPresentationId
));
117 observer_
->OnPresentationSessionConnected(route_id
);
119 // Route list update is expected to follow creation of route.
120 std::vector
<MediaRoute
> routes
;
122 MediaRoute(route_id
, MediaSourceForPresentationUrl(kPresentationUrl
),
123 MediaSink("sinkId", "A sink"), "Description", true, ""));
124 observer_
->OnRoutesUpdated(routes
);
126 // |route_id| is no longer being tracked.
128 EXPECT_TRUE(testing::Mock::VerifyAndClearExpectations(this));
129 observer_
->OnRoutesUpdated(std::vector
<MediaRoute
>());
132 } // namespace media_router