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

#include "third_party/blink/renderer/core/html/lazy_load_frame_observer.h"

#include <algorithm>
#include <memory>
#include <tuple>

#include "base/optional.h"
#include "third_party/blink/public/platform/web_effective_connection_type.h"
#include "third_party/blink/renderer/core/dom/element.h"
#include "third_party/blink/renderer/core/exported/web_view_impl.h"
#include "third_party/blink/renderer/core/frame/local_frame_view.h"
#include "third_party/blink/renderer/core/frame/settings.h"
#include "third_party/blink/renderer/core/html_names.h"
#include "third_party/blink/renderer/core/paint/paint_layer_scrollable_area.h"
#include "third_party/blink/renderer/core/testing/sim/sim_compositor.h"
#include "third_party/blink/renderer/core/testing/sim/sim_request.h"
#include "third_party/blink/renderer/core/testing/sim/sim_test.h"
#include "third_party/blink/renderer/platform/geometry/float_rect.h"
#include "third_party/blink/renderer/platform/network/network_state_notifier.h"
#include "third_party/blink/renderer/platform/testing/histogram_tester.h"
#include "third_party/blink/renderer/platform/testing/runtime_enabled_features_test_helpers.h"
#include "third_party/blink/renderer/platform/testing/unit_test_helpers.h"
#include "third_party/blink/renderer/platform/wtf/text/wtf_string.h"
#include "third_party/blink/renderer/platform/wtf/vector.h"

namespace blink {

namespace {

constexpr std::pair<WebEffectiveConnectionType, const char*>
    kVisibleLoadTimeAboveTheFoldHistogramNames[] = {
        {WebEffectiveConnectionType::kTypeSlow2G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.AboveTheFold.Slow2G"},
        {WebEffectiveConnectionType::kType2G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.AboveTheFold.2G"},
        {WebEffectiveConnectionType::kType3G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.AboveTheFold.3G"},
        {WebEffectiveConnectionType::kType4G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.AboveTheFold.4G"},
};

constexpr std::pair<WebEffectiveConnectionType, const char*>
    kVisibleLoadTimeBelowTheFoldHistogramNames[] = {
        {WebEffectiveConnectionType::kTypeSlow2G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.BelowTheFold.Slow2G"},
        {WebEffectiveConnectionType::kType2G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.BelowTheFold.2G"},
        {WebEffectiveConnectionType::kType3G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.BelowTheFold.3G"},
        {WebEffectiveConnectionType::kType4G,
         "Blink.VisibleLoadTime.LazyLoadEligibleFrames.BelowTheFold.4G"},
};

constexpr std::pair<WebEffectiveConnectionType, const char*>
    kInitialDeferralActionHistogramNames[] = {
        {WebEffectiveConnectionType::kTypeUnknown,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.Unknown"},
        {WebEffectiveConnectionType::kTypeOffline,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.Offline"},
        {WebEffectiveConnectionType::kTypeSlow2G,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.Slow2G"},
        {WebEffectiveConnectionType::kType2G,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.2G"},
        {WebEffectiveConnectionType::kType3G,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.3G"},
        {WebEffectiveConnectionType::kType4G,
         "Blink.LazyLoad.CrossOriginFrames.InitialDeferralAction.4G"},
};

// Convenience enums to make it easy to access the appropriate value of the
// tuple parameters in the parameterized tests below, e.g. so that
// std::get<LazyFrameLoadingFeatureStatus>(GetParam()) can be used instead of
// std::get<0>(GetParam()) if they were just booleans.
enum class LazyFrameLoadingFeatureStatus { kDisabled, kEnabled };
enum class LazyFrameVisibleLoadTimeFeatureStatus { kDisabled, kEnabled };

class LazyLoadFramesParamsTest
    : public SimTest,
      public ::testing::WithParamInterface<
          std::tuple<LazyFrameLoadingFeatureStatus,
                     LazyFrameVisibleLoadTimeFeatureStatus,
                     WebEffectiveConnectionType>> {
 public:
  static constexpr int kViewportWidth = 800;
  static constexpr int kViewportHeight = 600;

  LazyLoadFramesParamsTest()
      : scoped_lazy_frame_loading_for_test_(
            std::get<LazyFrameLoadingFeatureStatus>(GetParam()) ==
            LazyFrameLoadingFeatureStatus::kEnabled),
        scoped_lazy_frame_visible_load_time_metrics_for_test_(
            std::get<LazyFrameVisibleLoadTimeFeatureStatus>(GetParam()) ==
            LazyFrameVisibleLoadTimeFeatureStatus::kEnabled),
        scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(false) {}

  void SetUp() override {
    SetEffectiveConnectionTypeForTesting(
        std::get<WebEffectiveConnectionType>(GetParam()));

    SimTest::SetUp();
    WebView().MainFrameWidget()->Resize(
        WebSize(kViewportWidth, kViewportHeight));

    Settings& settings = WebView().GetPage()->GetSettings();

    // These should match the values that would be returned by
    // GetLoadingDistanceThreshold().
    settings.SetLazyFrameLoadingDistanceThresholdPxUnknown(200);
    settings.SetLazyFrameLoadingDistanceThresholdPxOffline(300);
    settings.SetLazyFrameLoadingDistanceThresholdPxSlow2G(400);
    settings.SetLazyFrameLoadingDistanceThresholdPx2G(500);
    settings.SetLazyFrameLoadingDistanceThresholdPx3G(600);
    settings.SetLazyFrameLoadingDistanceThresholdPx4G(700);
    settings.SetLazyLoadEnabled(true);
  }

  int GetLoadingDistanceThreshold() const {
    static constexpr int kDistanceThresholdByEffectiveConnectionType[] = {
        200, 300, 400, 500, 600, 700};
    return kDistanceThresholdByEffectiveConnectionType[static_cast<int>(
        std::get<WebEffectiveConnectionType>(GetParam()))];
  }

  void ExpectVisibleLoadTimeHistogramSamplesIfApplicable(
      int expected_above_the_fold_count,
      int expected_below_the_fold_count) {
    if (!RuntimeEnabledFeatures::LazyFrameVisibleLoadTimeMetricsEnabled()) {
      // Expect zero samples if the visible load time metrics feature is
      // disabled.
      expected_above_the_fold_count = 0;
      expected_below_the_fold_count = 0;
    }

    for (const auto& pair : kVisibleLoadTimeAboveTheFoldHistogramNames) {
      histogram_tester()->ExpectTotalCount(
          pair.second,
          std::get<WebEffectiveConnectionType>(GetParam()) == pair.first
              ? expected_above_the_fold_count
              : 0);
    }
    for (const auto& pair : kVisibleLoadTimeBelowTheFoldHistogramNames) {
      histogram_tester()->ExpectTotalCount(
          pair.second,
          std::get<WebEffectiveConnectionType>(GetParam()) == pair.first
              ? expected_below_the_fold_count
              : 0);
    }
  }

  void ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction action,
      int expected_count) {
    for (const auto& pair : kInitialDeferralActionHistogramNames) {
      if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled() &&
          std::get<WebEffectiveConnectionType>(GetParam()) == pair.first) {
        histogram_tester()->ExpectUniqueSample(
            pair.second, static_cast<int>(action), expected_count);
      } else {
        histogram_tester()->ExpectTotalCount(pair.second, 0);
      }
    }
  }

  void ExpectLoadStartedAfterDeferredSamplesIfApplicable(int expected_count) {
    if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
      histogram_tester()->ExpectUniqueSample(
          "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred",
          static_cast<int>(std::get<WebEffectiveConnectionType>(GetParam())),
          expected_count);
    } else {
      histogram_tester()->ExpectTotalCount(
          "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
    }
  }

  void ExpectVisibleAfterDeferredSamplesIfApplicable(int expected_count) {
    if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled() &&
        RuntimeEnabledFeatures::LazyFrameVisibleLoadTimeMetricsEnabled()) {
      histogram_tester()->ExpectUniqueSample(
          "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred",
          static_cast<int>(std::get<WebEffectiveConnectionType>(GetParam())),
          expected_count);
    } else {
      histogram_tester()->ExpectTotalCount(
          "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
    }
  }

  HistogramTester* histogram_tester() { return &histogram_tester_; }

  // Convenience function to load a page with a cross origin frame far down the
  // page such that it's not near the viewport.
  std::unique_ptr<SimRequest> LoadPageWithCrossOriginFrameFarFromViewport() {
    SimRequest main_resource("https://example.com/", "text/html");
    std::unique_ptr<SimRequest> child_frame_resource;

    if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
      // This SimRequest needs to be created now if the frame won't actually be
      // lazily loaded. Otherwise, it'll be defined later to ensure that the
      // subframe resource isn't requested until the page is scrolled down.
      child_frame_resource.reset(
          new SimRequest("https://crossorigin.com/subframe.html", "text/html"));
    }

    LoadURL("https://example.com/");

    main_resource.Complete(String::Format(
        R"HTML(
          <body onload='console.log("main body onload");'>
          <div style='height: %dpx;'></div>
          <iframe src='https://crossorigin.com/subframe.html'
               style='width: 400px; height: 400px;'
               onload='console.log("child frame element onload");'></iframe>
          </body>)HTML",
        kViewportHeight + GetLoadingDistanceThreshold() + 100));

    Compositor().BeginFrame();
    test::RunPendingTasks();

    // If the child frame is being lazy loaded, then the body's load event
    // should have already fired.
    EXPECT_EQ(RuntimeEnabledFeatures::LazyFrameLoadingEnabled(),
              ConsoleMessages().Contains("main body onload"));
    EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));

    ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

    ExpectInitialDeferralActionHistogramSamplesIfApplicable(
        LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
    histogram_tester()->ExpectTotalCount(
        "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
    histogram_tester()->ExpectTotalCount(
        "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);

    if (!child_frame_resource) {
      child_frame_resource.reset(
          new SimRequest("https://crossorigin.com/subframe.html", "text/html"));
    }

    return child_frame_resource;
  }

 private:
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test_;
  ScopedLazyFrameVisibleLoadTimeMetricsForTest
      scoped_lazy_frame_visible_load_time_metrics_for_test_;
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_;

  HistogramTester histogram_tester_;
};

TEST_P(LazyLoadFramesParamsTest, SameOriginFrame) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://example.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://example.com/subframe.html'
             style='width: 200px; height: 200px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  child_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  for (const auto& pair : kInitialDeferralActionHistogramNames)
    histogram_tester()->ExpectTotalCount(pair.second, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, AboveTheFoldFrame) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://crossorigin.com/subframe.html'
             style='width: 200px; height: 200px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight - 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  // The child frame is visible, but hasn't finished loading yet, so no visible
  // load time samples should have been recorded yet.
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  child_frame_resource.Complete("");
  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(1, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::
          kLoadedNearOrInViewport,
      1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, BelowTheFoldButNearViewportFrame) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://crossorigin.com/subframe.html'
             style='width: 200px; height: 200px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  child_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  // The frame is below the fold, but hasn't been scrolled down to yet, so there
  // should be no samples in any of the below the fold visible load time
  // histograms yet.
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  // Scroll down until the child frame is visible.
  GetDocument().View()->LayoutViewport()->SetScrollOffset(ScrollOffset(0, 150),
                                                          kProgrammaticScroll);

  Compositor().BeginFrame();
  test::RunPendingTasks();

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 1);

  // The frame finished loading before it became visible, so there should be no
  // samples in the VisibleBeforeLoaded histogram.
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::
          kLoadedNearOrInViewport,
      1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, HiddenAndTinyFrames) {
  SimRequest main_resource("https://example.com/", "text/html");

  SimRequest display_none_frame_resource(
      "https://crossorigin.com/display_none.html", "text/html");
  SimRequest visibility_hidden_frame_resource(
      "https://crossorigin.com/visibility_hidden.html", "text/html");
  SimRequest tiny_frame_resource("https://crossorigin.com/tiny.html",
                                 "text/html");
  SimRequest tiny_width_frame_resource(
      "https://crossorigin.com/tiny_width.html", "text/html");
  SimRequest tiny_height_frame_resource(
      "https://crossorigin.com/tiny_height.html", "text/html");
  SimRequest off_screen_left_frame_resource(
      "https://crossorigin.com/off_screen_left.html", "text/html");
  SimRequest off_screen_top_frame_resource(
      "https://crossorigin.com/off_screen_top.html", "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <head><style>
          /* Chrome by default sets borders for iframes, so explicitly specify
           * no borders, padding, or margins here so that the dimensions of the
           * tiny frames aren't artifically inflated past the dimensions that
           * the lazy loading logic considers "tiny". */
          iframe { border-style: none; padding: 0px; margin: 0px; }
        </style></head>

        <body onload='console.log("main body onload");'>
        <div style='height: %dpx'></div>
        <iframe src='https://crossorigin.com/display_none.html'
             style='display: none;'
             onload='console.log("display none element onload");'></iframe>
        <iframe src='https://crossorigin.com/visibility_hidden.html'
             style='visibility:hidden;width:100px;height:100px;'
             onload='console.log("visibility hidden element onload");'></iframe>
        <iframe src='https://crossorigin.com/tiny.html'
             style='width: 4px; height: 4px;'
             onload='console.log("tiny element onload");'></iframe>
        <iframe src='https://crossorigin.com/tiny_width.html'
             style='width: 0px; height: 50px;'
             onload='console.log("tiny width element onload");'></iframe>
        <iframe src='https://crossorigin.com/tiny_height.html'
             style='width: 50px; height: 0px;'
             onload='console.log("tiny height element onload");'></iframe>
        <iframe src='https://crossorigin.com/off_screen_left.html'
             style='position:relative;right:9000px;width:50px;height:50px;'
             onload='console.log("off screen left element onload");'></iframe>
        <iframe src='https://crossorigin.com/off_screen_top.html'
             style='position:relative;bottom:9000px;width:50px;height:50px;'
             onload='console.log("off screen top element onload");'></iframe>
        </body>
      )HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  display_none_frame_resource.Complete("");
  visibility_hidden_frame_resource.Complete("");
  tiny_frame_resource.Complete("");
  tiny_width_frame_resource.Complete("");
  tiny_height_frame_resource.Complete("");
  off_screen_left_frame_resource.Complete("");
  off_screen_top_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("display none element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("visibility hidden element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("tiny element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("tiny width element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("tiny height element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("off screen left element onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("off screen top element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  // Scroll down to where the hidden frames are.
  GetDocument().View()->LayoutViewport()->SetScrollOffset(
      ScrollOffset(0, kViewportHeight + GetLoadingDistanceThreshold()),
      kProgrammaticScroll);

  // All of the frames on the page are hidden or tiny, so no visible load time
  // samples should have been recorded for them.
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kLoadedHidden, 7);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, LoadCrossOriginFrameFarFromViewport) {
  std::unique_ptr<SimRequest> child_frame_resource =
      LoadPageWithCrossOriginFrameFarFromViewport();

  if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // If LazyFrameLoading is enabled, then scroll down near the child frame to
    // cause the child frame to start loading.
    GetDocument().View()->LayoutViewport()->SetScrollOffset(
        ScrollOffset(0, 150), kProgrammaticScroll);

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);

  child_frame_resource->Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  // Scroll down so that the child frame is visible.
  GetDocument().View()->LayoutViewport()->SetScrollOffset(
      ScrollOffset(0, GetLoadingDistanceThreshold() + 150),
      kProgrammaticScroll);

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 1);

  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  ExpectVisibleAfterDeferredSamplesIfApplicable(1);
}

TEST_P(LazyLoadFramesParamsTest,
       CrossOriginFrameFarFromViewportBecomesVisibleBeforeFinishedLoading) {
  std::unique_ptr<SimRequest> child_frame_resource =
      LoadPageWithCrossOriginFrameFarFromViewport();

  // Scroll down so that the child frame is visible.
  GetDocument().View()->LayoutViewport()->SetScrollOffset(
      ScrollOffset(0, GetLoadingDistanceThreshold() + 150),
      kProgrammaticScroll);

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  if (RuntimeEnabledFeatures::LazyFrameVisibleLoadTimeMetricsEnabled()) {
    // Even though the child frame hasn't loaded yet, a sample should still have
    // been recorded for VisibleBeforeLoaded.
    histogram_tester()->ExpectUniqueSample(
        "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold",
        static_cast<int>(std::get<WebEffectiveConnectionType>(GetParam())), 1);
  } else {
    histogram_tester()->ExpectTotalCount(
        "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);
  }

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  ExpectVisibleAfterDeferredSamplesIfApplicable(1);

  child_frame_resource->Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 1);

  // The samples recorded for VisibleBeforeLoaded should be unchanged.
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold",
      RuntimeEnabledFeatures::LazyFrameVisibleLoadTimeMetricsEnabled() ? 1 : 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  ExpectVisibleAfterDeferredSamplesIfApplicable(1);
}

TEST_P(LazyLoadFramesParamsTest, NestedFrameInCrossOriginFrameFarFromViewport) {
  std::unique_ptr<SimRequest> child_frame_resource =
      LoadPageWithCrossOriginFrameFarFromViewport();

  if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // If LazyFrameLoading is enabled, then scroll down near the child frame to
    // cause the child frame to start loading.
    GetDocument().View()->LayoutViewport()->SetScrollOffset(
        ScrollOffset(0, 150), kProgrammaticScroll);

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  // There's another nested cross origin iframe inside the first child frame,
  // even further down such that it's not near the viewport. It should start
  // loading immediately, even if LazyFrameLoading is enabled, since it's nested
  // inside a frame that was previously deferred.
  SimRequest nested_frame_resource("https://test.com/", "text/html");
  child_frame_resource->Complete(String::Format(
      "<div style='height: %dpx;'></div>"
      "<iframe src='https://test.com/' style='width: 200px; height: 200px;'>"
      "</iframe>",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  nested_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  // The child frame isn't visible, so no visible load time samples should have
  // been recorded.
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, AboutBlankChildFrameNavigation) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='BodyOnload()'>
        <script>
          function BodyOnload() {
            console.log('main body onload');
            document.getElementsByTagName('iframe')[0].src =
                'https://crossorigin.com/subframe.html';
          }
        </script>

        <div style='height: %dpx;'></div>
        <iframe
             style='width: 200px; height: 200px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_EQ(1, static_cast<int>(std::count(ConsoleMessages().begin(),
                                           ConsoleMessages().end(),
                                           "child frame element onload")));

  child_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_EQ(2, static_cast<int>(std::count(ConsoleMessages().begin(),
                                           ConsoleMessages().end(),
                                           "child frame element onload")));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  for (const auto& pair : kInitialDeferralActionHistogramNames)
    histogram_tester()->ExpectTotalCount(pair.second, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest, JavascriptStringFrameUrl) {
  SimRequest main_resource("https://example.com/", "text/html");
  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='javascript:"Hello World!";'
             style='width: 200px; height: 200px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  for (const auto& pair : kInitialDeferralActionHistogramNames)
    histogram_tester()->ExpectTotalCount(pair.second, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest,
       CrossOriginFrameFarFromViewportWithLazyLoadAttrOff) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://crossorigin.com/subframe.html'
             style='width: 200px; height: 200px;' lazyload='off'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  child_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  for (const auto& pair : kInitialDeferralActionHistogramNames)
    histogram_tester()->ExpectTotalCount(pair.second, 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest,
       LoadSameOriginFrameFarFromViewportWithLazyLoadAttributeOn) {
  SimRequest main_resource("https://example.com/", "text/html");
  base::Optional<SimRequest> child_frame_resource;

  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // This SimRequest needs to be created now if the frame won't actually be
    // lazily loaded. Otherwise, it'll be defined later to ensure that the
    // subframe resource isn't requested until the page is scrolled down.
    child_frame_resource.emplace("https://example.com/subframe.html",
                                 "text/html");
  }

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
          <body onload='console.log("main body onload");'>
          <div style='height: %dpx;'></div>
          <iframe src='https://example.com/subframe.html'
               style='width: 400px; height: 400px;' lazyload='on'
               onload='console.log("child frame element onload");'></iframe>
          </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  // If the child frame is being lazy loaded, then the body's load event
  // should have already fired.
  EXPECT_EQ(RuntimeEnabledFeatures::LazyFrameLoadingEnabled(),
            ConsoleMessages().Contains("main body onload"));
  EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.LoadStartedAfterBeingDeferred", 0);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);

  if (!child_frame_resource) {
    child_frame_resource.emplace("https://example.com/subframe.html",
                                 "text/html");
  }

  if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // If LazyFrameLoading is enabled, then scroll down near the child frame to
    // cause the child frame to start loading.
    GetDocument().View()->LayoutViewport()->SetScrollOffset(
        ScrollOffset(0, 150), kProgrammaticScroll);

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);

  child_frame_resource->Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  // Scroll down so that the child frame is visible.
  GetDocument().View()->LayoutViewport()->SetScrollOffset(
      ScrollOffset(0, GetLoadingDistanceThreshold() + 150),
      kProgrammaticScroll);

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 1);

  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  ExpectVisibleAfterDeferredSamplesIfApplicable(1);
}

TEST_P(LazyLoadFramesParamsTest,
       LoadCrossOriginFrameFarFromViewportThenSetLazyLoadAttributeOff) {
  SimRequest main_resource("https://example.com/", "text/html");
  base::Optional<SimRequest> child_frame_resource;

  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // This SimRequest needs to be created now if the frame won't actually be
    // lazily loaded. Otherwise, it'll be defined later to ensure that the
    // subframe resource isn't requested until the page is scrolled down.
    child_frame_resource.emplace("https://crossorigin.com/subframe.html",
                                 "text/html");
  }

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe id='child_frame' src='https://crossorigin.com/subframe.html'
             style='width: 400px; height: 400px;'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  // If the child frame is being lazy loaded, then the body's load event
  // should have already fired.
  EXPECT_EQ(RuntimeEnabledFeatures::LazyFrameLoadingEnabled(),
            ConsoleMessages().Contains("main body onload"));
  EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));

  if (!child_frame_resource) {
    child_frame_resource.emplace("https://crossorigin.com/subframe.html",
                                 "text/html");
  }

  Element* child_frame_element = GetDocument().getElementById("child_frame");
  ASSERT_TRUE(child_frame_element);
  child_frame_element->setAttribute(html_names::kLazyloadAttr, "off");

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);

  child_frame_resource->Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));

  ExpectVisibleLoadTimeHistogramSamplesIfApplicable(0, 0);

  histogram_tester()->ExpectTotalCount(
      "Blink.VisibleBeforeLoaded.LazyLoadEligibleFrames.BelowTheFold", 0);

  ExpectInitialDeferralActionHistogramSamplesIfApplicable(
      LazyLoadFrameObserver::FrameInitialDeferralAction::kDeferred, 1);
  ExpectLoadStartedAfterDeferredSamplesIfApplicable(1);
  histogram_tester()->ExpectTotalCount(
      "Blink.LazyLoad.CrossOriginFrames.VisibleAfterBeingDeferred", 0);
}

TEST_P(LazyLoadFramesParamsTest,
       NestedFrameWithLazyLoadAttributeOnInFrameWithNoLazyLoadAttribute) {
  std::unique_ptr<SimRequest> child_frame_resource =
      LoadPageWithCrossOriginFrameFarFromViewport();

  if (RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    // If LazyFrameLoading is enabled, then scroll down near the child frame to
    // cause the child frame to start loading.
    GetDocument().View()->LayoutViewport()->SetScrollOffset(
        ScrollOffset(0, 150), kProgrammaticScroll);

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  // There's another nested cross origin iframe inside the first child frame,
  // even further down such that it's not near the viewport. If LazyLoad is
  // enabled, it should be deferred even though it's nested inside a frame that
  // was previously deferred, because it has the attribute lazyload=on.
  base::Optional<SimRequest> nested_frame_resource;
  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled())
    nested_frame_resource.emplace("https://test.com/", "text/html");

  child_frame_resource->Complete(
      String::Format("<div style='height: %dpx;'></div>"
                     "<iframe src='https://test.com/' lazyload='on'"
                     "     style='width: 200px; height: 200px;'>"
                     "</iframe>",
                     kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    nested_frame_resource->Complete("");

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
}

TEST_P(LazyLoadFramesParamsTest,
       NestedFrameWithLazyLoadAttributeOnInFrameWithLazyLoadAttributeOff) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://crossorigin.com/subframe.html'
             style='width: 200px; height: 200px;' lazyload='off'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  // There's another nested cross origin iframe inside the first child frame,
  // even further down such that it's not near the viewport. If LazyLoad is
  // enabled, it should be deferred because it has the attribute lazyload=on,
  // even though it's nested inside a frame that has the attribute lazyload=off.
  base::Optional<SimRequest> nested_frame_resource;
  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled())
    nested_frame_resource.emplace("https://test.com/", "text/html");

  child_frame_resource.Complete(
      String::Format("<div style='height: %dpx;'></div>"
                     "<iframe src='https://test.com/' lazyload='on'"
                     "     style='width: 200px; height: 200px;'>"
                     "</iframe>",
                     kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  if (!RuntimeEnabledFeatures::LazyFrameLoadingEnabled()) {
    nested_frame_resource->Complete("");

    Compositor().BeginFrame();
    test::RunPendingTasks();
  }

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
}

TEST_P(LazyLoadFramesParamsTest,
       NestedFrameWithLazyLoadAttributeOffInFrameWithLazyLoadAttributeOff) {
  SimRequest main_resource("https://example.com/", "text/html");
  SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                  "text/html");

  LoadURL("https://example.com/");

  main_resource.Complete(String::Format(
      R"HTML(
        <body onload='console.log("main body onload");'>
        <div style='height: %dpx;'></div>
        <iframe src='https://crossorigin.com/subframe.html'
             style='width: 200px; height: 200px;' lazyload='off'
             onload='console.log("child frame element onload");'></iframe>
        </body>)HTML",
      kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  // There's another nested cross origin iframe inside the first child frame,
  // even further down such that it's not near the viewport. Since it has the
  // attribute lazyload=off, it shouldn't be deferred. Note that this also
  // matches the default behavior that would happen if the lazyload attribute
  // was omitted on the nested iframe entirely.
  SimRequest nested_frame_resource("https://test.com/", "text/html");

  child_frame_resource.Complete(
      String::Format("<div style='height: %dpx;'></div>"
                     "<iframe src='https://test.com/' lazyload='off'"
                     "     style='width: 200px; height: 200px;'>"
                     "</iframe>",
                     kViewportHeight + GetLoadingDistanceThreshold() + 100));

  Compositor().BeginFrame();
  test::RunPendingTasks();

  nested_frame_resource.Complete("");

  Compositor().BeginFrame();
  test::RunPendingTasks();

  EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
  EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
}

INSTANTIATE_TEST_CASE_P(
    LazyFrameLoading,
    LazyLoadFramesParamsTest,
    ::testing::Combine(
        ::testing::Values(LazyFrameLoadingFeatureStatus::kDisabled,
                          LazyFrameLoadingFeatureStatus::kEnabled),
        ::testing::Values(LazyFrameVisibleLoadTimeFeatureStatus::kDisabled,
                          LazyFrameVisibleLoadTimeFeatureStatus::kEnabled),
        ::testing::Values(WebEffectiveConnectionType::kTypeUnknown,
                          WebEffectiveConnectionType::kTypeOffline,
                          WebEffectiveConnectionType::kTypeSlow2G,
                          WebEffectiveConnectionType::kType2G,
                          WebEffectiveConnectionType::kType3G,
                          WebEffectiveConnectionType::kType4G)));

class LazyLoadFramesTest : public SimTest {
 public:
  static constexpr int kViewportWidth = 800;
  static constexpr int kViewportHeight = 600;
  static constexpr int kLoadingDistanceThresholdPx = 1000;

  void SetUp() override {
    SetEffectiveConnectionTypeForTesting(
        WebEffectiveConnectionType::kTypeUnknown);

    SimTest::SetUp();
    WebView().MainFrameWidget()->Resize(
        WebSize(kViewportWidth, kViewportHeight));

    Settings& settings = WebView().GetPage()->GetSettings();
    settings.SetLazyFrameLoadingDistanceThresholdPxUnknown(
        kLoadingDistanceThresholdPx);
    settings.SetLazyLoadEnabled(true);
  }

  void TearDown() override {
    GetNetworkStateNotifier().SetSaveDataEnabled(false);
    SimTest::TearDown();
  }

  void TestCrossOriginFrameIsImmediatelyLoaded(const char* iframe_attributes) {
    SimRequest main_resource("https://example.com/", "text/html");
    SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                    "text/html");
    LoadURL("https://example.com/");

    main_resource.Complete(String::Format(
        R"HTML(
          <body onload='console.log("main body onload");'>
          <div style='height: %dpx;'></div>
          <iframe src='https://crossorigin.com/subframe.html'
               style='width: 200px; height: 200px;' %s
               onload='console.log("child frame element onload");'></iframe>
          </body>)HTML",
        kViewportHeight + kLoadingDistanceThresholdPx + 100,
        iframe_attributes));

    Compositor().BeginFrame();
    test::RunPendingTasks();

    child_frame_resource.Complete("");
    Compositor().BeginFrame();
    test::RunPendingTasks();

    EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
    EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  }

  void TestCrossOriginFrameIsLazilyLoaded(const char* iframe_attributes) {
    SimRequest main_resource("https://example.com/", "text/html");
    LoadURL("https://example.com/");

    main_resource.Complete(String::Format(
        R"HTML(
          <body onload='console.log("main body onload");'>
          <div style='height: %dpx;'></div>
          <iframe src='https://crossorigin.com/subframe.html'
               style='width: 200px; height: 200px;' %s
               onload='console.log("child frame element onload");'></iframe>
          </body>)HTML",
        kViewportHeight + kLoadingDistanceThresholdPx + 100,
        iframe_attributes));

    Compositor().BeginFrame();
    test::RunPendingTasks();

    // The body's load event should have already fired.
    EXPECT_TRUE(ConsoleMessages().Contains("main body onload"));
    EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));

    SimRequest child_frame_resource("https://crossorigin.com/subframe.html",
                                    "text/html");

    // Scroll down near the child frame to cause the child frame to start
    // loading.
    GetDocument().View()->LayoutViewport()->SetScrollOffset(
        ScrollOffset(0, 150), kProgrammaticScroll);

    Compositor().BeginFrame();
    test::RunPendingTasks();

    EXPECT_FALSE(ConsoleMessages().Contains("child frame element onload"));

    child_frame_resource.Complete("");

    Compositor().BeginFrame();
    test::RunPendingTasks();

    EXPECT_TRUE(ConsoleMessages().Contains("child frame element onload"));
  }
};

TEST_F(LazyLoadFramesTest, LazyLoadWhenNotRestricted) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(false);

  TestCrossOriginFrameIsLazilyLoaded("");
}

TEST_F(LazyLoadFramesTest,
       LazyLoadWhenDataSaverDisabledAndNotRestrictedAttrOff) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(false);

  TestCrossOriginFrameIsImmediatelyLoaded("lazyload='off'");
}

TEST_F(LazyLoadFramesTest, LazyLoadWhenDataSaverDisabledAndRestricted) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(true);

  GetNetworkStateNotifier().SetSaveDataEnabled(false);
  WebView().GetPage()->GetSettings().SetDataSaverHoldbackWebApi(false);
  TestCrossOriginFrameIsImmediatelyLoaded("");
}

TEST_F(LazyLoadFramesTest, LazyLoadWhenDataSaverEnabledHoldbackAndRestricted) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(true);

  GetNetworkStateNotifier().SetSaveDataEnabled(true);
  WebView().GetPage()->GetSettings().SetDataSaverHoldbackWebApi(true);
  TestCrossOriginFrameIsImmediatelyLoaded("");
}

TEST_F(LazyLoadFramesTest, LazyLoadWhenDataSaverEnabledAndRestricted) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(true);

  GetNetworkStateNotifier().SetSaveDataEnabled(true);
  WebView().GetPage()->GetSettings().SetDataSaverHoldbackWebApi(false);
  TestCrossOriginFrameIsLazilyLoaded("");
}

TEST_F(LazyLoadFramesTest, LazyLoadWhenDataSaverDisabledAndRestrictedAttrOn) {
  ScopedLazyFrameLoadingForTest scoped_lazy_frame_loading_for_test(true);
  ScopedRestrictLazyFrameLoadingToDataSaverForTest
      scoped_restrict_lazy_frame_loading_to_data_saver_for_test_(true);

  GetNetworkStateNotifier().SetSaveDataEnabled(false);
  WebView().GetPage()->GetSettings().SetDataSaverHoldbackWebApi(false);
  TestCrossOriginFrameIsLazilyLoaded("lazyload='on'");
}

}  // namespace

}  // namespace blink
