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

#ifndef CONTENT_BROWSER_RENDERER_HOST_PAGE_IMPL_H_
#define CONTENT_BROWSER_RENDERER_HOST_PAGE_IMPL_H_

#include <memory>
#include <optional>
#include <set>
#include <vector>

#include "base/memory/raw_ref.h"
#include "base/memory/weak_ptr.h"
#include "base/time/time.h"
#include "cc/input/browser_controls_state.h"
#include "content/browser/fenced_frame/fenced_frame_url_mapping.h"
#include "content/browser/renderer_host/stored_page.h"
#include "content/browser/shared_storage/shared_storage_saved_query_data.h"
#include "content/common/content_export.h"
#include "content/common/navigation_client.mojom.h"
#include "content/public/browser/page.h"
#include "net/base/schemeful_site.h"
#include "services/metrics/public/cpp/ukm_source.h"
#include "services/metrics/public/cpp/ukm_source_id.h"
#include "third_party/blink/public/common/features.h"
#include "third_party/blink/public/common/shared_storage/shared_storage_utils.h"
#include "third_party/blink/public/mojom/css/preferred_color_scheme.mojom.h"
#include "third_party/blink/public/mojom/favicon/favicon_url.mojom.h"
#include "third_party/blink/public/mojom/frame/text_autosizer_page_info.mojom.h"
#include "third_party/skia/include/core/SkColor.h"
#include "ui/base/ime/mojom/virtual_keyboard_types.mojom.h"
#include "url/gurl.h"

#if BUILDFLAG(IS_ANDROID)
#include "content/browser/android/page_proxy.h"
#endif

namespace cc {
struct BrowserControlsOffsetTagModifications;
}  // namespace cc

namespace viz {
class PeakGpuMemoryTracker;
}  // namespace viz

namespace content {

class NavigationRequest;
class PageDelegate;
class RenderFrameHostImpl;

// This implements the Page interface that is exposed to embedders of content,
// and adds things only visible to content.

// Please refer to content/public/browser/page.h for more details.
class CONTENT_EXPORT PageImpl : public Page {
 public:
  enum class ActivationType {
    kPrerendering,
    kPreview,
  };
  PageImpl(RenderFrameHostImpl& rfh, PageDelegate& delegate);

  ~PageImpl() override;

  using base::SupportsUserData::ClearAllUserData;

  // Page implementation.
  const std::optional<GURL>& GetManifestUrl() const override;
  void GetManifest(GetManifestCallback callback) override;
  bool IsPrimary() const override;
  void WriteIntoTrace(perfetto::TracedValue context) override;
  base::WeakPtr<Page> GetWeakPtr() override;
  bool IsPageScaleFactorOne() override;
  const std::string& GetContentsMimeType() const override;
  void SetResizableForTesting(std::optional<bool> resizable) override;
  std::optional<bool> GetResizable() override;
#if BUILDFLAG(IS_ANDROID)
  const base::android::JavaRef<jobject>& GetJavaPage() override;
#endif

  // Setter for the `window.setResizable(bool)` API's value defining whether the
  // window can be resized or not. `std::nullopt` means the value is not set.
  void SetResizable(std::optional<bool> resizable);

  std::optional<uint64_t> canvas_noise_token() const {
    return canvas_noise_token_;
  }
  void set_canvas_noise_token(std::optional<uint64_t> token) {
    canvas_noise_token_ = token;
  }

  base::WeakPtr<PageImpl> GetWeakPtrImpl();

  virtual void UpdateManifestUrl(const GURL& manifest_url);

  RenderFrameHostImpl& GetMainDocument() const;

  bool is_on_load_completed_in_main_document() const {
    return is_on_load_completed_in_main_document_;
  }
  void set_is_on_load_completed_in_main_document(bool completed) {
    is_on_load_completed_in_main_document_ = completed;
  }

  bool did_first_contentful_paint_in_main_document() const {
    return did_first_contentful_paint_in_main_document_;
  }
  void set_did_first_contentful_paint_in_main_document() {
    did_first_contentful_paint_in_main_document_ = true;
  }

  bool is_main_document_element_available() const {
    return is_main_document_element_available_;
  }
  void set_is_main_document_element_available(bool completed) {
    is_main_document_element_available_ = completed;
  }

  bool uses_temporary_zoom_level() const { return uses_temporary_zoom_level_; }
  void set_uses_temporary_zoom_level(bool level) {
    uses_temporary_zoom_level_ = level;
  }

  void OnFirstVisuallyNonEmptyPaint();
  bool did_first_visually_non_empty_paint() const {
    return did_first_visually_non_empty_paint_;
  }

  const std::vector<blink::mojom::FaviconURLPtr>& favicon_urls() const {
    return favicon_urls_;
  }
  void set_favicon_urls(std::vector<blink::mojom::FaviconURLPtr> favicon_urls) {
    favicon_urls_ = std::move(favicon_urls);
  }

  void OnThemeColorChanged(const std::optional<SkColor>& theme_color);

  void DidChangeBackgroundColor(SkColor4f background_color, bool color_adjust);

  // Notifies the page's color scheme was inferred.
  void DidInferColorScheme(blink::mojom::PreferredColorScheme color_scheme);

  void NotifyPageBecameCurrent();

  std::optional<SkColor> theme_color() const {
    return main_document_theme_color_;
  }

  std::optional<SkColor> background_color() const {
    return main_document_background_color_;
  }

  std::optional<blink::mojom::PreferredColorScheme> inferred_color_scheme()
      const {
    return main_document_inferred_color_scheme_;
  }

  void SetContentsMimeType(std::string mime_type);

  void OnTextAutosizerPageInfoChanged(
      blink::mojom::TextAutosizerPageInfoPtr page_info);

  blink::mojom::TextAutosizerPageInfo text_autosizer_page_info() const {
    return text_autosizer_page_info_;
  }

  FencedFrameURLMapping& fenced_frame_urls_map() {
    return fenced_frame_urls_map_;
  }

  void set_last_main_document_source_id(ukm::SourceId id) {
    last_main_document_source_id_ = id;
  }
  ukm::SourceId last_main_document_source_id() const {
    return last_main_document_source_id_;
  }

  // Sets the start time of the prerender activation navigation for this page.
  // TODO(falken): Plumb NavigationRequest to
  // RenderFrameHostManager::CommitPending and remove this.
  void SetActivationStartTime(base::TimeTicks activation_start);

  // Called during the activation navigation. Sends an IPC to the RenderViews in
  // the renderers, instructing them to transition their documents from
  // prerendered to activated. Tells the corresponding RenderFrameHostImpls that
  // the renderer will be activating their documents.
  void Activate(
      ActivationType type,
      StoredPage::RenderViewHostImplSafeRefSet& render_view_hosts_to_activate,
      std::optional<blink::ViewTransitionState> view_transition_state,
      base::OnceCallback<void(base::TimeTicks)> completion_callback);

  // Prerender2:
  // Dispatches load events that were deferred to be dispatched after
  // activation. Please note that this should only be called on prerender
  // activation.
  void MaybeDispatchLoadEventsOnPrerenderActivation();

  // Hide or show the browser controls for the given Page, based on allowed
  // states, desired state and whether the transition should be animated or
  // not.
  void UpdateBrowserControlsState(
      cc::BrowserControlsState constraints,
      cc::BrowserControlsState current,
      bool animate,
      const std::optional<cc::BrowserControlsOffsetTagModifications>&
          offset_tag_modifications);

  float GetPageScaleFactor() const;

  void set_load_progress(double load_progress) {
    load_progress_ = load_progress;
  }
  double load_progress() const { return load_progress_; }

  // The env() variables for virtual keyboard overlay and context menu insets
  // are page-level, and don't get propagated into iframes, because a) that
  // would be a cross-site info leak, and b) it's hard to know exactly how they
  // would be used in that context.
  // See https://github.com/w3c/csswg-drafts/issues/4670.
  void NotifyVirtualKeyboardOverlayRect(const gfx::Rect& keyboard_rect);

  // This call will "show interest" in the Element with the provided DOMNodeID,
  // which is presumed to have an `interestfor` attribute.
  void ShowInterestInElement(int);

  void SetVirtualKeyboardMode(ui::mojom::VirtualKeyboardMode mode);
  ui::mojom::VirtualKeyboardMode virtual_keyboard_mode() const {
    return virtual_keyboard_mode_;
  }

  const std::string& GetEncoding() { return canonical_encoding_; }
  void UpdateEncoding(const std::string& encoding_name);

  // Returns the keyboard layout mapping.
  base::flat_map<std::string, std::string> GetKeyboardLayoutMap();

  // Retrieves the index from `select_url_saved_query_index_results_` for the
  // given key, or a special value indicating the status of the query. The key
  // is a tuple of (`origin`, `script_url`, `operation_name`, `query_name`).
  //
  // - New Query: If no entry exists for the key, initializes a new entry with
  //   an index of -1 (indicating pending) and returns -2.
  // - Pending Query: If an entry exists but the index is -1, adds the provided
  //   `callback` to the list of callbacks for this query and returns -1.
  // - Completed Query: If an entry exists and the index is nonnegative, returns
  //   the index.
  int32_t GetSavedQueryResultIndexOrStoreCallback(
      const url::Origin& origin,
      const GURL& script_url,
      const std::string& operation_name,
      const std::u16string& query_name,
      base::OnceCallback<void(uint32_t)> callback);

  // Updates `select_url_saved_query_index_results_` for the given key as
  // follows. The key is a tuple of (`origin`, `script_url`, `operation_name`,
  // `query_name`).
  //  - The index is of the entry is set to `index`.
  //  - If the entry has any callbacks, runs them in order.
  //
  // Precondition: The entry exists and its index has value -1.
  void SetSavedQueryResultIndexAndRunCallbacks(
      const url::Origin& origin,
      const GURL& script_url,
      const std::string& operation_name,
      const std::u16string& query_name,
      uint32_t index);

  // Returns whether a pending call to `sharedStorage.selectURL()` has
  // sufficient budget for `site`, debiting `select_url_overall_budget_` and
  // `select_url_per_site_budget_[site]` if so and if
  // `blink::features::kSharedStorageSelectURLLimit` is enabled. If
  // `blink::features::kSharedStorageSelectURLLimit` is disabled, always returns
  // `blink::SharedStorageSelectUrlBudgetStatus::kSufficientBudget`. If there is
  // insufficient budget, the returned enum value specifies which budget was
  // insufficient.
  blink::SharedStorageSelectUrlBudgetStatus CheckAndMaybeDebitSelectURLBudgets(
      const net::SchemefulSite& site,
      double bits_to_charge);

  // See documentation for |credentialless_iframes_nonce_|.
  const base::UnguessableToken& credentialless_iframes_nonce() const {
    return credentialless_iframes_nonce_;
  }

  // Take ownership of the loading memory tracker from the NavigationRequest
  // that navigated to this page.
  void TakeLoadingMemoryTracker(NavigationRequest* request);
  // If we have a loading memory tracker, close it as loading has stopped. It
  // will asynchronously receive the statistics from the GPU process, and update
  // UMA stats.
  void ResetLoadingMemoryTracker();
  // If we have a loading memory tracker, cancel it as loading hasn't stopped
  // and the page is being navigated away from. UMA stats will not be recorded.
  void CancelLoadingMemoryTracker();

  bool is_overriding_user_agent() { return is_overriding_user_agent_; }
  void set_is_overriding_user_agent(bool is_overriding_user_agent) {
    is_overriding_user_agent_ = is_overriding_user_agent;
  }

  // Use to set and release |last_commit_params_|, see documentation of the
  // member for more details. This is only called for outermost pages.
  void SetLastCommitParams(
      mojom::DidCommitProvisionalLoadParamsPtr commit_params);
  mojom::DidCommitProvisionalLoadParamsPtr TakeLastCommitParams();

 private:
  void DidActivateAllRenderViewsForPrerenderingOrPreview(
      base::OnceCallback<void(base::TimeTicks)> completion_callback);

  // This method is needed to ensure that PageImpl can both implement a Page's
  // method and define a new GetMainDocument(). Please refer to page.h for more
  // details.
  RenderFrameHost& GetMainDocumentHelper() override;

  // True if we've received a notification that the onload() handler has
  // run for the main document.
  bool is_on_load_completed_in_main_document_ = false;

  // True if the main document had done a first contentful paint.
  bool did_first_contentful_paint_in_main_document_ = false;

  // True if we've received a notification that the window.document element
  // became available for the main document.
  bool is_main_document_element_available_ = false;

  // True if plugin zoom level is set for the main document.
  bool uses_temporary_zoom_level_ = false;

  // Overall load progress of this Page. Initial load progress value is 0.0
  // before the load has begun.
  double load_progress_ = 0.0;

  // Web application manifest URL for this page.
  // See https://w3c.github.io/manifest/#web-application-manifest.
  //
  // This is non-nullopt when the page gets an update of the manifest URL. It
  // can be the empty URL when the manifest url is removed and a non-empty
  // URL when it has a valid URL for the manifest. If this is non-nullopt,
  // WebContentsObserver::DidUpdateWebManifestURL() will be called
  // (either immediately on document load, or on activation in the case
  // of a prerendered page).
  //
  // nullopt indicates that the page did not get an update of the
  // manifest URL, and DidUpdateWebManifestURL() will not be called.
  std::optional<GURL> manifest_url_;

  // Candidate favicon URLs. Each page may have a collection and will be
  // displayed when active (i.e., upon activation for prerendering).
  std::vector<blink::mojom::FaviconURLPtr> favicon_urls_;

  // Whether the first visually non-empty paint has occurred.
  bool did_first_visually_non_empty_paint_ = false;

  // Stores the value set by `window.setResizable(bool)` API for whether the
  // window can be resized or not. `std::nullopt` means the value is not set.
  std::optional<bool> resizable_ = std::nullopt;

  // A 64 bit token used as the initial hash value for canvas noising per page,
  // where nullopt indicates canvas noising should not be enabled for the page.
  // The initial hash value will be a combination of the main frame's origin and
  // the browser context (see
  // content/browser/fingerprinting_protection/canvas_noise_token_data.h for
  // more details). Modifying the token value must happen prior to the commit of
  // the page's main frame navigation and will be communicated to the renderer
  // process during commit via CommitNavigationParams.
  // TODO(https://crbug.com/377325952): Make a more specific type than uint64_t.
  std::optional<uint64_t> canvas_noise_token_ = std::nullopt;

  // The theme color for the underlying document as specified
  // by theme-color meta tag.
  std::optional<SkColor> main_document_theme_color_;

  // The background color for the underlying document as computed by CSS.
  std::optional<SkColor> main_document_background_color_;

  // The inferred color scheme of the document.
  std::optional<blink::mojom::PreferredColorScheme>
      main_document_inferred_color_scheme_;

  // Contents MIME type for the main document. It can be used to check whether
  // we can do something for special contents.
  std::string contents_mime_type_;

  // Fenced frames:
  // Any fenced frames created within this page will access this map.
  FencedFrameURLMapping fenced_frame_urls_map_;

  // If `blink::features::kSharedStorageSelectURLLimit` is enabled, the number
  // of bits of entropy remaining in this pageload's overall budget for calls to
  // `sharedStorage.selectURL()`. Calls from all sites on this page are
  // charged to this budget. `select_url_overall_budget_` is not renewed until
  // `this` is destroyed, and it does not rely on any assumptions about when
  // specifically `this` is destroyed (e.g. during navigation or not).
  std::optional<double> select_url_overall_budget_;

  // If `blink::features::kSharedStorageSelectURLLimit` is enabled, the maximum
  // number of bits of entropy in a single site's budget.
  std::optional<double> select_url_max_bits_per_site_;

  // A map of sites to the number bits of entropy remaining in the site's
  // budget for calls to `sharedStorage.selectURL()` during this pageload.
  // `select_url_per_site_budget_` is not cleared until `this` is destroyed,
  // and it does not rely on any assumptions about when specifically `this` is
  // destroyed (e.g. during navigation or not). Used only if
  // `blink::features::kSharedStorageSelectURLLimit` is enabled.
  base::flat_map<net::SchemefulSite, double> select_url_per_site_budget_;

  // A map of tuples (origin, worklet script URL, operation name, query name) to
  // the index returned for the corresponding `sharedStorage.selectURL()` query.
  base::flat_map<std::tuple<url::Origin, GURL, std::string, std::u16string>,
                 SharedStorageSavedQueryData>
      select_url_saved_query_index_results_;

  // This class is owned by the main RenderFrameHostImpl and it's safe to keep a
  // reference to it.
  const raw_ref<RenderFrameHostImpl> main_document_;

  // SourceId of the navigation in this page's main frame. Note that a same
  // document navigation is the only case where this source id can change, since
  // all other navigations create a new PageImpl instance.
  ukm::SourceId last_main_document_source_id_ = ukm::kInvalidSourceId;

  // This page is owned by the RenderFrameHostImpl, which in turn does not
  // outlive the delegate (the contents).
  const raw_ref<PageDelegate> delegate_;

  // Stores information from the main frame's renderer that needs to be shared
  // with OOPIF renderers.
  blink::mojom::TextAutosizerPageInfo text_autosizer_page_info_;

  // Prerender2: The start time of the activation navigation for prerendering,
  // which is passed to the renderer process, and will be accessible in the
  // prerendered page as PerformanceNavigationTiming.activationStart. Set after
  // navigation commit.
  // TODO(b:291867362): Plumb NavigationRequest to
  // RenderFrameHostManager::CommitPending and remove this.
  std::optional<base::TimeTicks> activation_start_time_;

  // The resizing mode requested by Blink for the virtual keyboard.
  ui::mojom::VirtualKeyboardMode virtual_keyboard_mode_ =
      ui::mojom::VirtualKeyboardMode::kUnset;

  // The last reported character encoding, not canonicalized.
  std::string last_reported_encoding_;
  // The canonicalized character encoding.
  std::string canonical_encoding_;

  // Nonce to be used for initializing the storage key and the network isolation
  // key of credentialless iframes which are children of this page's main
  // document.
  const base::UnguessableToken credentialless_iframes_nonce_ =
      base::UnguessableToken::Create();

  // This is only set for primary pages.
  // Created by NavigationRequest; ownership is maintained until the frame has
  // stopped loading, or we navigate away from the page before it finishes
  // loading.
  std::unique_ptr<viz::PeakGpuMemoryTracker> loading_memory_tracker_;

  // Whether the page is overriding the user agent or not.
  bool is_overriding_user_agent_ = false;

  // This is used to re-commit when restoring a page from the BackForwardCache
  // or when activating a prerendered page, with the same params as the original
  // navigation.
  mojom::DidCommitProvisionalLoadParamsPtr last_commit_params_;

#if BUILDFLAG(IS_ANDROID)
  // For each C++ Page, there is a Java counterpart. It is the JNI bridge in
  // between the two.
  std::unique_ptr<PageProxy> page_proxy_;
#endif

  base::WeakPtrFactory<PageImpl> weak_factory_{this};
};

}  // namespace content

#endif  // CONTENT_BROWSER_RENDERER_HOST_PAGE_IMPL_H_
