#ifdef UNSAFE_BUFFERS_BUILD
#pragma allow_unsafe_buffers
#endif
#include "chrome/browser/media/webrtc/display_media_access_handler.h"
#include <memory>
#include <string>
#include <utility>
#include "base/functional/bind.h"
#include "base/memory/raw_ptr.h"
#include "base/run_loop.h"
#include "base/strings/utf_string_conversions.h"
#include "base/test/mock_callback.h"
#include "build/build_config.h"
#include "chrome/browser/media/webrtc/fake_desktop_media_picker_factory.h"
#include "chrome/common/pref_names.h"
#include "chrome/test/base/chrome_render_view_host_test_harness.h"
#include "components/prefs/pref_service.h"
#include "content/public/browser/browser_context.h"
#include "content/public/browser/desktop_media_id.h"
#include "content/public/browser/media_stream_request.h"
#include "content/public/browser/web_contents.h"
#include "content/public/test/browser_test_utils.h"
#include "content/public/test/navigation_simulator.h"
#include "testing/gtest/include/gtest/gtest.h"
#include "third_party/blink/public/common/mediastream/media_stream_request.h"
#include "third_party/blink/public/mojom/mediastream/media_stream.mojom-shared.h"
#include "third_party/blink/public/mojom/mediastream/media_stream.mojom.h"
#if BUILDFLAG(IS_CHROMEOS)
#include "chrome/browser/chromeos/policy/dlp/test/mock_dlp_content_manager.h"
#endif
#if !BUILDFLAG(IS_ANDROID)
#include "base/test/gmock_expected_support.h"
#include "chrome/browser/ui/web_applications/test/isolated_web_app_test_utils.h"
#include "chrome/browser/web_applications/isolated_web_apps/isolated_web_app_url_info.h"
#include "chrome/browser/web_applications/isolated_web_apps/test/isolated_web_app_builder.h"
#include "chrome/browser/web_applications/test/web_app_install_test_utils.h"
#include "services/data_decoder/public/cpp/test_support/in_process_data_decoder.h"
#endif
class DisplayMediaAccessHandlerTest : public ChromeRenderViewHostTestHarness { … };
TEST_F(DisplayMediaAccessHandlerTest, PermissionGiven) { … }
#if BUILDFLAG(IS_MAC)
TEST_F(DisplayMediaAccessHandlerTest, WindowPermissionGiven) {
blink::mojom::MediaStreamRequestResult result;
blink::mojom::StreamDevices devices;
content::DesktopMediaID desktop_media_id(content::DesktopMediaID::TYPE_WINDOW,
content::DesktopMediaID::kFakeId);
desktop_media_id.window_id = content::DesktopMediaID::kFakeId;
ProcessRequest(desktop_media_id, &result, devices, false );
EXPECT_EQ(blink::mojom::MediaStreamRequestResult::OK, result);
EXPECT_EQ(1u, blink::CountDevices(devices));
EXPECT_EQ(blink::mojom::MediaStreamType::DISPLAY_VIDEO_CAPTURE,
devices.video_device.value().type);
EXPECT_TRUE(devices.video_device.value().display_media_info);
}
#endif
TEST_F(DisplayMediaAccessHandlerTest, PermissionGivenToRequestWithAudio) { … }
TEST_F(DisplayMediaAccessHandlerTest, PermissionDenied) { … }
#if BUILDFLAG(IS_CHROMEOS)
TEST_F(DisplayMediaAccessHandlerTest, DlpRestricted) {
const content::DesktopMediaID media_id(content::DesktopMediaID::TYPE_SCREEN,
content::DesktopMediaID::kFakeId);
policy::MockDlpContentManager mock_dlp_content_manager;
policy::ScopedDlpContentObserverForTesting scoped_dlp_content_observer(
&mock_dlp_content_manager);
EXPECT_CALL(mock_dlp_content_manager, CheckScreenShareRestriction)
.WillOnce([](const content::DesktopMediaID& media_id,
const std::u16string& application_title,
base::OnceCallback<void(bool)> callback) {
std::move(callback).Run(false);
});
blink::mojom::MediaStreamRequestResult result =
blink::mojom::MediaStreamRequestResult::NOT_SUPPORTED;
blink::mojom::StreamDevices devices;
ProcessRequest(media_id, &result, devices, false);
EXPECT_EQ(blink::mojom::MediaStreamRequestResult::PERMISSION_DENIED, result);
EXPECT_EQ(0u, blink::CountDevices(devices));
}
TEST_F(DisplayMediaAccessHandlerTest, DlpNotRestricted) {
const content::DesktopMediaID media_id(content::DesktopMediaID::TYPE_SCREEN,
content::DesktopMediaID::kFakeId);
policy::MockDlpContentManager mock_dlp_content_manager;
policy::ScopedDlpContentObserverForTesting scoped_dlp_content_manager(
&mock_dlp_content_manager);
EXPECT_CALL(mock_dlp_content_manager, CheckScreenShareRestriction)
.WillOnce([](const content::DesktopMediaID& media_id,
const std::u16string& application_title,
base::OnceCallback<void(bool)> callback) {
std::move(callback).Run(true);
});
blink::mojom::MediaStreamRequestResult result =
blink::mojom::MediaStreamRequestResult::NOT_SUPPORTED;
blink::mojom::StreamDevices devices;
ProcessRequest(media_id, &result, devices, false);
EXPECT_EQ(blink::mojom::MediaStreamRequestResult::OK, result);
EXPECT_EQ(1u, blink::CountDevices(devices));
}
TEST_F(DisplayMediaAccessHandlerTest, DlpWebContentsDestroyed) {
const content::DesktopMediaID media_id(content::DesktopMediaID::TYPE_SCREEN,
content::DesktopMediaID::kFakeId);
policy::MockDlpContentManager mock_dlp_content_manager;
policy::ScopedDlpContentObserverForTesting scoped_dlp_content_manager(
&mock_dlp_content_manager);
EXPECT_CALL(mock_dlp_content_manager, CheckScreenShareRestriction)
.WillOnce([&](const content::DesktopMediaID& media_id,
const std::u16string& application_title,
base::OnceCallback<void(bool)> callback) {
DeleteContents();
std::move(callback).Run(true);
});
blink::mojom::MediaStreamRequestResult result =
blink::mojom::MediaStreamRequestResult::NOT_SUPPORTED;
blink::mojom::StreamDevices devices;
ProcessRequest(media_id, &result, devices, false,
false);
EXPECT_EQ(blink::mojom::MediaStreamRequestResult::NOT_SUPPORTED, result);
EXPECT_EQ(0u, blink::CountDevices(devices));
}
#endif
TEST_F(DisplayMediaAccessHandlerTest, UpdateMediaRequestStateWithClosing) { … }
TEST_F(DisplayMediaAccessHandlerTest, CorrectHostAsksForPermissions) { … }
TEST_F(DisplayMediaAccessHandlerTest, CorrectHostAsksForPermissionsNormalURLs) { … }
#if !BUILDFLAG(IS_ANDROID)
TEST_F(DisplayMediaAccessHandlerTest, IsolatedWebAppNameAsksForPermissions) { … }
#endif
TEST_F(DisplayMediaAccessHandlerTest, WebContentsDestroyed) { … }
TEST_F(DisplayMediaAccessHandlerTest, MultipleRequests) { … }
TEST_F(DisplayMediaAccessHandlerTest,
ChangeSourceWithoutAudioRequestPermissionGiven) { … }
TEST_F(DisplayMediaAccessHandlerTest,
ChangeSourceWithAudioRequestPermissionGiven) { … }
#if BUILDFLAG(IS_CHROMEOS)
TEST_F(DisplayMediaAccessHandlerTest, ChangeSourceDlpRestricted) {
const content::DesktopMediaID media_id(
content::DesktopMediaID::TYPE_WEB_CONTENTS,
content::DesktopMediaID::kNullId, GetWebContentsMediaCaptureId());
policy::MockDlpContentManager mock_dlp_content_manager;
policy::ScopedDlpContentObserverForTesting scoped_dlp_content_observer(
&mock_dlp_content_manager);
EXPECT_CALL(mock_dlp_content_manager, CheckScreenShareRestriction)
.WillOnce([](const content::DesktopMediaID& media_id,
const std::u16string& application_title,
base::OnceCallback<void(bool)> callback) {
std::move(callback).Run(false);
});
ChangeSourceRequestTest(
false,
blink::mojom::MediaStreamRequestResult::PERMISSION_DENIED,
0u);
}
TEST_F(DisplayMediaAccessHandlerTest, ChangeSourceDlpNotRestricted) {
const content::DesktopMediaID media_id(
content::DesktopMediaID::TYPE_WEB_CONTENTS,
content::DesktopMediaID::kNullId, GetWebContentsMediaCaptureId());
policy::MockDlpContentManager mock_dlp_content_manager;
policy::ScopedDlpContentObserverForTesting scoped_dlp_content_manager(
&mock_dlp_content_manager);
EXPECT_CALL(mock_dlp_content_manager, CheckScreenShareRestriction)
.WillOnce([](const content::DesktopMediaID& media_id,
const std::u16string& application_title,
base::OnceCallback<void(bool)> callback) {
std::move(callback).Run(true);
});
ChangeSourceRequestTest(
false,
blink::mojom::MediaStreamRequestResult::OK,
1u);
}
#endif
TEST_F(DisplayMediaAccessHandlerTest, ChangeSourceWithPendingPickerRequest) { … }
TEST_F(DisplayMediaAccessHandlerTest,
ChangeSourcePolicyViolationWithPendingPickerRequest) { … }
TEST_F(DisplayMediaAccessHandlerTest,
MalformedChangeSourceBetweenPickerRequests) { … }
class DisplayMediaAccessHandlerTestWithSelfBrowserSurface
: public DisplayMediaAccessHandlerTest,
public testing::WithParamInterface<bool> { … };
INSTANTIATE_TEST_SUITE_P(…);
TEST_P(DisplayMediaAccessHandlerTestWithSelfBrowserSurface,
CheckIsWebContentsExcluded) { … }
class DisplayMediaAccessHandlerTestWithMonitorTypeSurfaces
: public DisplayMediaAccessHandlerTest,
public testing::WithParamInterface<bool> { … };
INSTANTIATE_TEST_SUITE_P(…);
TEST_P(DisplayMediaAccessHandlerTestWithMonitorTypeSurfaces,
CheckMonitorTypeSurfacesAreExcluded) { … }