// Copyright (c) 2015 The Chromium Embedded Framework 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 "include/base/cef_callback.h"
#include "include/cef_pack_resources.h"
#include "include/cef_request_context_handler.h"
#include "include/wrapper/cef_closure_task.h"
#include "include/wrapper/cef_stream_resource_handler.h"
#include "tests/ceftests/test_handler.h"
#include "tests/ceftests/test_util.h"
#include "tests/gtest/include/gtest/gtest.h"
#include "tests/shared/browser/client_app_browser.h"
#include "tests/shared/browser/resource_util.h"

namespace {

const char kPdfHtmlUrl[] = "https://tests/pdf.html";
const char kPdfDirectUrl[] = "https://tests/pdf.pdf";

// Delay waiting for iframe tests to load the PDF file.
#if defined(OS_LINUX)
const int64_t kPdfLoadDelayMs = 7000;
#else
const int64_t kPdfLoadDelayMs = 5000;
#endif

// Browser-side test handler.
class PdfViewerTestHandler : public TestHandler, public CefContextMenuHandler {
 public:
  enum Mode {
    // No specified context or handler (implicitly uses the global context).
    GLOBAL_DEFAULT,

    // Global context with no handler.
    GLOBAL_NO_HANDLER,

    // Custom context with no handler.
    CUSTOM_NO_HANDLER,
  };

  PdfViewerTestHandler(Mode mode, const std::string& url)
      : mode_(mode), url_(url) {}

  // Loading the PDF directly in the main frame instead of a sub-frame.
  bool HasDirectPdfLoad() const { return url_ == kPdfDirectUrl; }

  CefRefPtr<CefContextMenuHandler> GetContextMenuHandler() override {
    return this;
  }

  void RunTest() override {
    CefRefPtr<CefRequestContext> request_context;

    if (mode_ == GLOBAL_NO_HANDLER) {
      // Use the global request context.
      request_context = CefRequestContext::CreateContext(
          CefRequestContext::GetGlobalContext(), nullptr);
    } else if (mode_ == CUSTOM_NO_HANDLER) {
      // Create the request context that will use an in-memory cache.
      CefRequestContextSettings settings;
      request_context = CefRequestContext::CreateContext(settings, nullptr);
    }

    // Create the browser.
    CreateBrowser(url_, request_context);

    // Time out the test after a reasonable period of time.
    SetTestTimeout(5000 + kPdfLoadDelayMs);
  }

  CefRefPtr<CefResourceHandler> GetResourceHandler(
      CefRefPtr<CefBrowser> browser,
      CefRefPtr<CefFrame> frame,
      CefRefPtr<CefRequest> request) override {
    const std::string& url = request->GetURL();
    if (url == kPdfHtmlUrl) {
      CefRefPtr<CefStreamReader> stream =
          client::GetBinaryResourceReader("pdf.html");
      return new CefStreamResourceHandler("text/html", stream);
    } else if (url == kPdfDirectUrl) {
      CefRefPtr<CefStreamReader> stream =
          client::GetBinaryResourceReader("pdf.pdf");
      return new CefStreamResourceHandler("application/pdf", stream);
    }

    return nullptr;
  }

  void OnLoadEnd(CefRefPtr<CefBrowser> browser,
                 CefRefPtr<CefFrame> frame,
                 int httpStatusCode) override {
    bool is_pdf1 = false;
    const std::string& url = frame->GetURL();
    if (url == "about:blank") {
      return;
    }

    if (url == kPdfHtmlUrl) {
      if (!got_on_load_end_html_) {
        got_on_load_end_html_.yes();
      } else {
        NOTREACHED();
      }
    } else if (url == kPdfDirectUrl) {
      if (!got_on_load_end_pdf1_) {
        got_on_load_end_pdf1_.yes();
        is_pdf1 = true;
      } else if (!got_on_load_end_pdf2_) {
        got_on_load_end_pdf2_.yes();
      } else {
        NOTREACHED();
      }
    } else {
      NOTREACHED() << "url=" << url;
    }

    if (is_pdf1) {
      // The first PDF document has loaded.
      // TODO(chrome): Add support for custom context menus.
      if (IsChromeRuntimeEnabled() || got_context_menu_dismissed_) {
        // After context menu display. Destroy the test.
        CefPostDelayedTask(
            TID_UI, base::BindOnce(&PdfViewerTestHandler::DestroyTest, this),
            kPdfLoadDelayMs);
      } else {
        // Trigger the context menu.
        CefPostDelayedTask(
            TID_UI,
            base::BindOnce(&PdfViewerTestHandler::TriggerContextMenu, this,
                           frame->GetBrowser()),
            kPdfLoadDelayMs);
      }
    }
  }

  void TriggerContextMenu(CefRefPtr<CefBrowser> browser) {
    CefMouseEvent mouse_event;

    if (HasDirectPdfLoad()) {
      // Somewhere in the main PDF viewing area (avoid left preview bar).
      mouse_event.x = 400;
      mouse_event.y = 200;
    } else {
      // Somewhere in the first PDF viewing area.
      mouse_event.x = 100;
      mouse_event.y = 100;
    }

    // Send right-click mouse down and mouse up to tigger context menu.
    SendMouseClickEvent(browser, mouse_event, MBT_RIGHT);
  }

  bool RunContextMenu(CefRefPtr<CefBrowser> browser,
                      CefRefPtr<CefFrame> frame,
                      CefRefPtr<CefContextMenuParams> params,
                      CefRefPtr<CefMenuModel> model,
                      CefRefPtr<CefRunContextMenuCallback> callback) override {
    EXPECT_FALSE(got_run_context_menu_);
    got_run_context_menu_.yes();

    // Do nothing with the context menu.
    callback->Cancel();

    return true;
  }

  void OnContextMenuDismissed(CefRefPtr<CefBrowser> browser,
                              CefRefPtr<CefFrame> frame) override {
    EXPECT_FALSE(got_context_menu_dismissed_);
    got_context_menu_dismissed_.yes();

    CefPostTask(TID_UI,
                base::BindOnce(&PdfViewerTestHandler::DestroyTest, this));
  }

  void DestroyTest() override {
    // TODO(chrome): Add support for custom context menus.
    if (!IsChromeRuntimeEnabled()) {
      EXPECT_TRUE(got_run_context_menu_);
      EXPECT_TRUE(got_context_menu_dismissed_);
    } else {
      EXPECT_FALSE(got_run_context_menu_);
      EXPECT_FALSE(got_context_menu_dismissed_);
    }

    if (url_ == kPdfHtmlUrl) {
      // The HTML file will load the PDF twice in iframes.
      EXPECT_TRUE(got_on_load_end_html_);
      EXPECT_TRUE(got_on_load_end_pdf1_);
      EXPECT_TRUE(got_on_load_end_pdf2_);
    } else if (url_ == kPdfDirectUrl) {
      // Load the PDF file directly.
      EXPECT_FALSE(got_on_load_end_html_);
      EXPECT_TRUE(got_on_load_end_pdf1_);
      EXPECT_FALSE(got_on_load_end_pdf2_);
    } else {
      NOTREACHED();
    }

    TestHandler::DestroyTest();
  }

  const Mode mode_;
  const std::string url_;

  TrackCallback got_on_load_end_html_;
  TrackCallback got_on_load_end_pdf1_;
  TrackCallback got_on_load_end_pdf2_;
  TrackCallback got_run_context_menu_;
  TrackCallback got_context_menu_dismissed_;

  IMPLEMENT_REFCOUNTING(PdfViewerTestHandler);
};

}  // namespace

#define RUN_TEST(name, type, url)                                  \
  TEST(PdfViewerTest, name) {                                      \
    CefRefPtr<PdfViewerTestHandler> handler =                      \
        new PdfViewerTestHandler(PdfViewerTestHandler::type, url); \
    handler->ExecuteTest();                                        \
    ReleaseAndWaitForDestructor(handler);                          \
  }

RUN_TEST(GlobalDefaultPdfDirect, GLOBAL_DEFAULT, kPdfDirectUrl)
RUN_TEST(GlobalDefaultPdfHtml, GLOBAL_DEFAULT, kPdfHtmlUrl)

RUN_TEST(GlobalNoHandlerPdfDirect, GLOBAL_NO_HANDLER, kPdfDirectUrl)
RUN_TEST(GlobalNoHandlerPdfHtml, GLOBAL_NO_HANDLER, kPdfHtmlUrl)

RUN_TEST(CustomNoHandlerPdfDirect, CUSTOM_NO_HANDLER, kPdfDirectUrl)
RUN_TEST(CustomNoHandlerPdfHtml, CUSTOM_NO_HANDLER, kPdfHtmlUrl)
