chromium/content/browser/webrtc/webrtc_getusermedia_browsertest.cc

// Copyright 2014 The Chromium Authors
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <stddef.h>

#include "base/command_line.h"
#include "base/feature_list.h"
#include "base/functional/bind.h"
#include "base/json/json_reader.h"
#include "base/strings/stringprintf.h"
#include "base/test/gmock_expected_support.h"
#include "base/test/scoped_feature_list.h"
#include "base/threading/thread_restrictions.h"
#include "base/values.h"
#include "build/build_config.h"
#include "build/chromeos_buildflags.h"
#include "content/browser/browser_main_loop.h"
#include "content/browser/renderer_host/media/media_stream_manager.h"
#include "content/browser/web_contents/web_contents_impl.h"
#include "content/browser/webrtc/webrtc_content_browsertest_base.h"
#include "content/browser/webrtc/webrtc_internals.h"
#include "content/public/browser/audio_service.h"
#include "content/public/common/content_features.h"
#include "content/public/common/content_switches.h"
#include "content/public/test/browser_test.h"
#include "content/public/test/browser_test_utils.h"
#include "content/public/test/content_browser_test_utils.h"
#include "content/public/test/test_utils.h"
#include "content/shell/browser/shell.h"
#include "media/audio/audio_manager.h"
#include "media/audio/fake_audio_input_stream.h"
#include "media/base/media_switches.h"
#include "net/test/embedded_test_server/embedded_test_server.h"
#include "services/audio/public/mojom/testing_api.mojom.h"

#if BUILDFLAG(IS_WIN)
#include "base/win/windows_version.h"
#endif

namespace {

static const char kGetUserMediaAndStop[] =;
static const char kGetUserMediaAndAnalyseAndStop[] =;
static const char kGetUserMediaAndExpectFailure[] =;
static const char kRenderSameTrackMediastreamAndStop[] =;
static const char kRenderClonedMediastreamAndStop[] =;
static const char kRenderClonedTrackMediastreamAndStop[] =;
static const char kRenderDuplicatedMediastreamAndStop[] =;

std::string GenerateGetUserMediaWithMandatorySourceID(
    const std::string& function_name,
    const std::string& audio_source_id,
    const std::string& video_source_id) {}

std::string GenerateGetUserMediaWithOptionalSourceID(
    const std::string& function_name,
    const std::string& audio_source_id,
    const std::string& video_source_id) {}

// TODO(crbug.com/40841334): Bring back when
// WebRtcGetUserMediaBrowserTest.DisableLocalEchoParameter is fixed.
#if 0
std::string GenerateGetUserMediaWithDisableLocalEcho(
    const std::string& function_name,
    const std::string& disable_local_echo) {
  const std::string audio_constraint =
      "audio:{mandatory: { chromeMediaSource : 'system', disableLocalEcho : " +
      disable_local_echo + " }},";

  const std::string video_constraint =
      "video: { mandatory: { chromeMediaSource:'screen' }}";
  return function_name + "({" + audio_constraint + video_constraint + "});";
}

bool VerifyDisableLocalEcho(bool expect_value,
                            const blink::StreamControls& controls) {
  return expect_value == controls.disable_local_echo;
}
#endif

}  // namespace

namespace content {

class WebRtcGetUserMediaBrowserTest : public WebRtcContentBrowserTestBase {};

// These tests will all make a getUserMedia call with different constraints and
// see that the success callback is called. If the error callback is called or
// none of the callbacks are called the tests will simply time out and fail.

// Test fails under MSan, http://crbug.com/445745
#if defined(MEMORY_SANITIZER)
#define MAYBE_GetVideoStreamAndStop
#else
#define MAYBE_GetVideoStreamAndStop
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_GetVideoStreamAndStop) {}

// Test fails under MSan, http://crbug.com/445745
#if defined(MEMORY_SANITIZER)
#define MAYBE_RenderSameTrackMediastreamAndStop
#else
#define MAYBE_RenderSameTrackMediastreamAndStop
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_RenderSameTrackMediastreamAndStop) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       RenderClonedMediastreamAndStop) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       kRenderClonedTrackMediastreamAndStop) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       kRenderDuplicatedMediastreamAndStop) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetAudioAndVideoStreamAndStop) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetAudioAndVideoStreamAndClone) {}

// TODO(crbug.com/41365739) : Flaky on all platforms.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_RenderVideoTrackInMultipleTagsAndPause) {}

// TODO(crbug.com/571389, crbug.com/1241538): Flaky on TSAN bots and macOS.
#if BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS) || BUILDFLAG(IS_MAC)
#define MAYBE_GetUserMediaWithMandatorySourceID
#else
#define MAYBE_GetUserMediaWithMandatorySourceID
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_GetUserMediaWithMandatorySourceID) {}
#undef MAYBE_GetUserMediaWithMandatorySourceID

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetUserMediaWithInvalidMandatorySourceID) {}

// TODO(crbug.com/40784748): Flaky on Mac.
#if BUILDFLAG(IS_MAC)
#define MAYBE_GetUserMediaWithInvalidOptionalSourceID
#else
#define MAYBE_GetUserMediaWithInvalidOptionalSourceID
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_GetUserMediaWithInvalidOptionalSourceID) {}

// Sheriff 2021-08-10, test is flaky.
// See https://crbug.com/1238334.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaAndStop) {}

// Flaky. See https://crbug.com/846741.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaWithEqualConstraints) {}

// Flaky. See https://crbug.com/843844.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaWithSecondVideoCropped) {}

// Test fails under MSan, http://crbug.com/445745.
// Flaky. See https://crbug.com/846960.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaWithFirstHdSecondVga) {}

// Timing out on Windows 7 bot: http://crbug.com/443294
// Flaky: http://crbug.com/660656; possible the test is too perf sensitive.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaWithFirst1080pSecondVga) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetUserMediaWithTooHighVideoConstraintsValues) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetUserMediaFailToAccessAudioDevice) {}

// This test makes two getUserMedia requests, one with impossible constraints
// that should trigger an error, and one with valid constraints. The test
// verifies getUserMedia can succeed after being given impossible constraints.
// Flaky. See https://crbug.com/846984.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TwoGetUserMediaAndCheckCallbackAfterFailure) {}

// This test calls getUserMedia and checks for aspect ratio behavior.
// TODO(crbug.com/40229233): Flaky for tsan, mac, lacros.
#if defined(THREAD_SANITIZER) || BUILDFLAG(IS_MAC) || \
    BUILDFLAG(IS_CHROMEOS_LACROS)
#define MAYBE_TestGetUserMediaAspectRatio4To3
#else
#define MAYBE_TestGetUserMediaAspectRatio4To3
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_TestGetUserMediaAspectRatio4To3) {}

// This test calls getUserMedia and checks for aspect ratio behavior.
// Flaky: crbug.com/846582.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_TestGetUserMediaAspectRatio16To9) {}

// This test calls getUserMedia and checks for aspect ratio behavior.
// TODO(crbug.com/40229233): Flaky for tsan, mac, lacros.
#if defined(THREAD_SANITIZER) || BUILDFLAG(IS_MAC) || \
    BUILDFLAG(IS_CHROMEOS_LACROS)
#define MAYBE_TestGetUserMediaAspectRatio1To1
#else
#define MAYBE_TestGetUserMediaAspectRatio1To1
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_TestGetUserMediaAspectRatio1To1) {}

// This test calls getUserMedia in an iframe and immediately close the iframe
// in the scope of the success callback.
// Flaky: crbug.com/727601.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_AudioInIFrameAndCloseInSuccessCb) {}

// Flaky: crbug.com/807638
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_VideoInIFrameAndCloseInSuccessCb) {}

// This test calls getUserMedia in an iframe and immediately close the iframe
// in the scope of the failure callback.
// Flaky on lacros-chrome and mac bots. http://crbug.com/1196389
#if BUILDFLAG(IS_CHROMEOS_LACROS) || BUILDFLAG(IS_MAC)
#define MAYBE_VideoWithBadConstraintsInIFrameAndCloseInFailureCb
#else
#define MAYBE_VideoWithBadConstraintsInIFrameAndCloseInFailureCb
#endif
IN_PROC_BROWSER_TEST_F(
    WebRtcGetUserMediaBrowserTest,
    MAYBE_VideoWithBadConstraintsInIFrameAndCloseInFailureCb) {}

// TODO(http://crbug.com/1205560): This test is flaky on mac bots. Re-enable the
// test after fixing the issue.
#if BUILDFLAG(IS_MAC) || BUILDFLAG(IS_LINUX)
#define MAYBE_InvalidSourceIdInIFrameAndCloseInFailureCb
#else
#define MAYBE_InvalidSourceIdInIFrameAndCloseInFailureCb
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_InvalidSourceIdInIFrameAndCloseInFailureCb) {}

// TODO(crbug.com/40841334): Fix this test. It seems to be broken (no audio /
// video tracks are requested; "uncaught (in promise) undefined)") and was false
// positive before disabling.
#if 0
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DisableLocalEchoParameter) {
  base::CommandLine::ForCurrentProcess()->AppendSwitch(
      switches::kEnableExperimentalWebPlatformFeatures);
  ASSERT_TRUE(embedded_test_server()->Start());

  GURL url(embedded_test_server()->GetURL("/media/getusermedia.html"));
  EXPECT_TRUE(NavigateToURL(shell(), url));

  MediaStreamManager* manager =
      BrowserMainLoop::GetInstance()->media_stream_manager();

  manager->SetGenerateStreamsCallbackForTesting(
      base::BindOnce(&VerifyDisableLocalEcho, false));
  std::string call = GenerateGetUserMediaWithDisableLocalEcho(
      "getUserMediaAndExpectSuccess", "false");
  EXPECT_TRUE(ExecJs(shell(), call));

  manager->SetGenerateStreamsCallbackForTesting(
      base::BindOnce(&VerifyDisableLocalEcho, true));
  call = GenerateGetUserMediaWithDisableLocalEcho(
      "getUserMediaAndExpectSuccess", "true");
  EXPECT_TRUE(ExecJs(shell(), call));


  manager->SetGenerateStreamsCallbackForTesting(
      MediaStreamManager::GenerateStreamTestCallback());
}
#endif

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest, GetAudioSettingsDefault) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetAudioSettingsNoEchoCancellation) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetAudioSettingsDeviceId) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest, SrcObjectAddVideoTrack) {}

// TODO(crbug.com/41392081) Flaky on all platforms
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_SrcObjectReplaceInactiveTracks) {}

// Flaky on all platforms. https://crbug.com/835332
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_SrcObjectRemoveVideoTrack) {}

// Flaky. https://crbug.com/843844
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_SrcObjectRemoveFirstOfTwoVideoTracks) {}

// TODO(guidou): Add SrcObjectAddAudioTrack and SrcObjectRemoveAudioTrack tests
// when a straightforward mechanism to detect the presence/absence of audio in a
// media element with an assigned MediaStream becomes available.

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       SrcObjectReassignSameObject) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest, ApplyConstraintsVideo) {}

// Flaky due to https://crbug.com/1113820
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_ApplyConstraintsVideoTwoStreams) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       ApplyConstraintsVideoOverconstrained) {}

// Flaky on Win, see https://crbug.com/915135
// Flaky on Linux, see https://crbug.com/952381
#if BUILDFLAG(IS_WIN) || BUILDFLAG(IS_LINUX) || BUILDFLAG(IS_CHROMEOS)
#define MAYBE_ApplyConstraintsNonDevice
#else
#define MAYBE_ApplyConstraintsNonDevice
#endif
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       MAYBE_ApplyConstraintsNonDevice) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       ConcurrentGetUserMediaStop) {}

// TODO(crbug.com/40694651) : Flaky on all platforms.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_GetUserMediaAfterStopElementCapture) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       GetUserMediaEchoCancellationOnAndOff) {}

// TODO(crbug.com/40694651) : Flaky on all platforms.
IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       DISABLED_GetUserMediaEchoCancellationOnAndOffAndVideo) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       EnumerationAfterSameDocumentNavigation) {}

IN_PROC_BROWSER_TEST_F(WebRtcGetUserMediaBrowserTest,
                       RecoverFromCrashInAudioService) {}

}  // namespace content