Home | History | Annotate | Download | only in browser
      1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
      2 // Use of this source code is governed by a BSD-style license that can be
      3 // found in the LICENSE file.
      4 
      5 #ifndef CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_
      6 #define CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_
      7 
      8 #include "base/process/kill.h"
      9 #include "base/process/process_handle.h"
     10 #include "content/common/content_export.h"
     11 #include "content/public/browser/navigation_controller.h"
     12 #include "content/public/common/page_transition_types.h"
     13 #include "ipc/ipc_listener.h"
     14 #include "ipc/ipc_sender.h"
     15 #include "ui/base/window_open_disposition.h"
     16 
     17 namespace content {
     18 
     19 class NavigationEntry;
     20 class RenderFrameHost;
     21 class RenderViewHost;
     22 class WebContents;
     23 class WebContentsImpl;
     24 struct FaviconURL;
     25 struct FrameNavigateParams;
     26 struct LoadCommittedDetails;
     27 struct LoadFromMemoryCacheDetails;
     28 struct Referrer;
     29 struct ResourceRedirectDetails;
     30 struct ResourceRequestDetails;
     31 
     32 // An observer API implemented by classes which are interested in various page
     33 // load events from WebContents.  They also get a chance to filter IPC messages.
     34 //
     35 // Since a WebContents can be a delegate to almost arbitrarily many
     36 // RenderViewHosts, it is important to check in those WebContentsObserver
     37 // methods which take a RenderViewHost that the event came from the
     38 // RenderViewHost the observer cares about.
     39 //
     40 // Usually, observers should only care about the current RenderViewHost as
     41 // returned by GetRenderViewHost().
     42 //
     43 // TODO(creis, jochen): Hide the fact that there are several RenderViewHosts
     44 // from the WebContentsObserver API. http://crbug.com/173325
     45 class CONTENT_EXPORT WebContentsObserver : public IPC::Listener,
     46                                            public IPC::Sender {
     47  public:
     48   // Called when a RenderFrameHost associated with this WebContents is created.
     49   virtual void RenderFrameCreated(RenderFrameHost* render_frame_host) {}
     50 
     51   // Called whenever a RenderFrameHost associated with this WebContents is
     52   // deleted.
     53   virtual void RenderFrameDeleted(RenderFrameHost* render_frame_host) {}
     54 
     55   // Only one of the two methods below will be called when a RVH is created for
     56   // a WebContents, depending on whether it's for an interstitial or not.
     57   virtual void RenderViewCreated(RenderViewHost* render_view_host) {}
     58   virtual void RenderViewForInterstitialPageCreated(
     59       RenderViewHost* render_view_host) {}
     60 
     61   // This method is invoked when the RenderView of the current RenderViewHost
     62   // is ready, e.g. because we recreated it after a crash.
     63   virtual void RenderViewReady() {}
     64 
     65   // This method is invoked when a RenderViewHost of the WebContents is
     66   // deleted. Note that this does not always happen when the WebContents starts
     67   // to use a different RenderViewHost, as the old RenderViewHost might get
     68   // just swapped out.
     69   virtual void RenderViewDeleted(RenderViewHost* render_view_host) {}
     70 
     71   // This method is invoked when the process for the current RenderView crashes.
     72   // The WebContents continues to use the RenderViewHost, e.g. when the user
     73   // reloads the current page.
     74   // When the RenderViewHost is deleted, the RenderViewDeleted method will be
     75   // invoked.
     76   virtual void RenderProcessGone(base::TerminationStatus status) {}
     77 
     78   // This method is invoked when a WebContents swaps its render view host with
     79   // another one, possibly changing processes. The RenderViewHost that has
     80   // been replaced is in |old_render_view_host|, which is NULL if the old RVH
     81   // was shut down.
     82   virtual void RenderViewHostChanged(RenderViewHost* old_host,
     83                                      RenderViewHost* new_host) {}
     84 
     85   // This method is invoked after the WebContents decided which RenderViewHost
     86   // to use for the next navigation, but before the navigation starts.
     87   virtual void AboutToNavigateRenderView(
     88       RenderViewHost* render_view_host) {}
     89 
     90   // This method is invoked after the browser process starts a navigation to a
     91   // pending NavigationEntry. It is not called for renderer-initiated
     92   // navigations unless they are sent to the browser process via OpenURL. It may
     93   // be called multiple times for a given navigation, such as a typed URL
     94   // followed by a cross-process client or server redirect.
     95   virtual void DidStartNavigationToPendingEntry(
     96       const GURL& url,
     97       NavigationController::ReloadType reload_type) {}
     98 
     99   // |render_view_host| is the RenderViewHost for which the provisional load is
    100   // happening. |frame_id| is a positive, non-zero integer identifying the
    101   // navigating frame in the given |render_view_host|. |parent_frame_id| is the
    102   // frame identifier of the frame containing the navigating frame, or -1 if the
    103   // frame is not contained in another frame.
    104   //
    105   // Since the URL validation will strip error URLs, or srcdoc URLs, the boolean
    106   // flags |is_error_page| and |is_iframe_srcdoc| will indicate that the not
    107   // validated URL was either an error page or an iframe srcdoc.
    108   //
    109   // Note that during a cross-process navigation, several provisional loads
    110   // can be on-going in parallel.
    111   virtual void DidStartProvisionalLoadForFrame(
    112       int64 frame_id,
    113       int64 parent_frame_id,
    114       bool is_main_frame,
    115       const GURL& validated_url,
    116       bool is_error_page,
    117       bool is_iframe_srcdoc,
    118       RenderViewHost* render_view_host) {}
    119 
    120   // This method is invoked right after the DidStartProvisionalLoadForFrame if
    121   // the provisional load affects the main frame, or if the provisional load
    122   // was redirected. The latter use case is DEPRECATED. You should listen to
    123   // WebContentsObserver::DidGetRedirectForResourceRequest instead.
    124   virtual void ProvisionalChangeToMainFrameUrl(
    125       const GURL& url,
    126       RenderViewHost* render_view_host) {}
    127 
    128   // This method is invoked when the provisional load was successfully
    129   // committed. The |render_view_host| is now the current RenderViewHost of the
    130   // WebContents.
    131   //
    132   // If the navigation only changed the reference fragment, or was triggered
    133   // using the history API (e.g. window.history.replaceState), we will receive
    134   // this signal without a prior DidStartProvisionalLoadForFrame signal.
    135   virtual void DidCommitProvisionalLoadForFrame(
    136       int64 frame_id,
    137       const base::string16& frame_unique_name,
    138       bool is_main_frame,
    139       const GURL& url,
    140       PageTransition transition_type,
    141       RenderViewHost* render_view_host) {}
    142 
    143   // This method is invoked when the provisional load failed.
    144   virtual void DidFailProvisionalLoad(int64 frame_id,
    145                                       const base::string16& frame_unique_name,
    146                                       bool is_main_frame,
    147                                       const GURL& validated_url,
    148                                       int error_code,
    149                                       const base::string16& error_description,
    150                                       RenderViewHost* render_view_host) {}
    151 
    152   // If the provisional load corresponded to the main frame, this method is
    153   // invoked in addition to DidCommitProvisionalLoadForFrame.
    154   virtual void DidNavigateMainFrame(
    155       const LoadCommittedDetails& details,
    156       const FrameNavigateParams& params) {}
    157 
    158   // And regardless of what frame navigated, this method is invoked after
    159   // DidCommitProvisionalLoadForFrame was invoked.
    160   virtual void DidNavigateAnyFrame(
    161       const LoadCommittedDetails& details,
    162       const FrameNavigateParams& params) {}
    163 
    164   // This method is invoked once the window.document object of the main frame
    165   // was created.
    166   virtual void DocumentAvailableInMainFrame() {}
    167 
    168   // This method is invoked once the onload handler of the main frame has
    169   // completed.
    170   virtual void DocumentOnLoadCompletedInMainFrame(int32 page_id) {}
    171 
    172   // This method is invoked when the document in the given frame finished
    173   // loading. At this point, scripts marked as defer were executed, and
    174   // content scripts marked "document_end" get injected into the frame.
    175   virtual void DocumentLoadedInFrame(int64 frame_id,
    176                                      RenderViewHost* render_view_host) {}
    177 
    178   // This method is invoked when the navigation is done, i.e. the spinner of
    179   // the tab will stop spinning, and the onload event was dispatched.
    180   //
    181   // If the WebContents is displaying replacement content, e.g. network error
    182   // pages, DidFinishLoad is invoked for frames that were not sending
    183   // navigational events before. It is safe to ignore these events.
    184   virtual void DidFinishLoad(int64 frame_id,
    185                              const GURL& validated_url,
    186                              bool is_main_frame,
    187                              RenderViewHost* render_view_host) {}
    188 
    189   // This method is like DidFinishLoad, but when the load failed or was
    190   // cancelled, e.g. window.stop() is invoked.
    191   virtual void DidFailLoad(int64 frame_id,
    192                            const GURL& validated_url,
    193                            bool is_main_frame,
    194                            int error_code,
    195                            const base::string16& error_description,
    196                            RenderViewHost* render_view_host) {}
    197 
    198   // This method is invoked when content was loaded from an in-memory cache.
    199   virtual void DidLoadResourceFromMemoryCache(
    200       const LoadFromMemoryCacheDetails& details) {}
    201 
    202   // This method is invoked when a response has been received for a resource
    203   // request.
    204   virtual void DidGetResourceResponseStart(
    205       const ResourceRequestDetails& details) {}
    206 
    207   // This method is invoked when a redirect was received while requesting a
    208   // resource.
    209   virtual void DidGetRedirectForResourceRequest(
    210       const ResourceRedirectDetails& details) {}
    211 
    212   // This method is invoked when a new non-pending navigation entry is created.
    213   // This corresponds to one NavigationController entry being created
    214   // (in the case of new navigations) or renavigated to (for back/forward
    215   // navigations).
    216   virtual void NavigationEntryCommitted(
    217       const LoadCommittedDetails& load_details) {}
    218 
    219   // This method is invoked when a new WebContents was created in response to
    220   // an action in the observed WebContents, e.g. a link with target=_blank was
    221   // clicked. The |source_frame_id| indicates in which frame the action took
    222   // place.
    223   virtual void DidOpenRequestedURL(WebContents* new_contents,
    224                                    const GURL& url,
    225                                    const Referrer& referrer,
    226                                    WindowOpenDisposition disposition,
    227                                    PageTransition transition,
    228                                    int64 source_frame_id) {}
    229 
    230   virtual void FrameDetached(RenderViewHost* render_view_host,
    231                              int64 frame_id) {}
    232 
    233   // This method is invoked when the renderer has completed its first paint
    234   // after a non-empty layout.
    235   virtual void DidFirstVisuallyNonEmptyPaint(int32 page_id) {}
    236 
    237   // These two methods correspond to the points in time when the spinner of the
    238   // tab starts and stops spinning.
    239   virtual void DidStartLoading(RenderViewHost* render_view_host) {}
    240   virtual void DidStopLoading(RenderViewHost* render_view_host) {}
    241 
    242   // When WebContents::Stop() is called, the WebContents stops loading and then
    243   // invokes this method. If there are ongoing navigations, their respective
    244   // failure methods will also be invoked.
    245   virtual void NavigationStopped() {}
    246 
    247   // This indicates that the next navigation was triggered by a user gesture.
    248   virtual void DidGetUserGesture() {}
    249 
    250   // This method is invoked when a RenderViewHost of this WebContents was
    251   // configured to ignore UI events, and an UI event took place.
    252   virtual void DidGetIgnoredUIEvent() {}
    253 
    254   // These methods are invoked every time the WebContents changes visibility.
    255   virtual void WasShown() {}
    256   virtual void WasHidden() {}
    257 
    258   // This methods is invoked when the title of the WebContents is set. If the
    259   // title was explicitly set, |explicit_set| is true, otherwise the title was
    260   // synthesized and |explicit_set| is false.
    261   virtual void TitleWasSet(NavigationEntry* entry, bool explicit_set) {}
    262 
    263   virtual void AppCacheAccessed(const GURL& manifest_url,
    264                                 bool blocked_by_policy) {}
    265 
    266   // Notification that a plugin has crashed.
    267   // |plugin_pid| is the process ID identifying the plugin process. Note that
    268   // this ID is supplied by the renderer, so should not be trusted. Besides, the
    269   // corresponding process has probably died at this point. The ID may even have
    270   // been reused by a new process.
    271   virtual void PluginCrashed(const base::FilePath& plugin_path,
    272                              base::ProcessId plugin_pid) {}
    273 
    274   // Notification that the given plugin has hung or become unhung. This
    275   // notification is only for Pepper plugins.
    276   //
    277   // The plugin_child_id is the unique child process ID from the plugin. Note
    278   // that this ID is supplied by the renderer, so should be validated before
    279   // it's used for anything in case there's an exploited renderer.
    280   virtual void PluginHungStatusChanged(int plugin_child_id,
    281                                        const base::FilePath& plugin_path,
    282                                        bool is_hung) {}
    283 
    284   // Invoked when WebContents::Clone() was used to clone a WebContents.
    285   virtual void DidCloneToNewWebContents(WebContents* old_web_contents,
    286                                         WebContents* new_web_contents) {}
    287 
    288   // Invoked when the WebContents is being destroyed. Gives subclasses a chance
    289   // to cleanup. At the time this is invoked |web_contents()| returns NULL.
    290   // It is safe to delete 'this' from here.
    291   virtual void WebContentsDestroyed(WebContents* web_contents) {}
    292 
    293   // Called when the user agent override for a WebContents has been changed.
    294   virtual void UserAgentOverrideSet(const std::string& user_agent) {}
    295 
    296   // Invoked when new FaviconURL candidates are received from the renderer.
    297   virtual void DidUpdateFaviconURL(int32 page_id,
    298                                    const std::vector<FaviconURL>& candidates) {}
    299 
    300   // Invoked when a pepper plugin creates and shows or destroys a fullscreen
    301   // render widget.
    302   virtual void DidShowFullscreenWidget(int routing_id) {}
    303   virtual void DidDestroyFullscreenWidget(int routing_id) {}
    304 
    305   // Invoked when visible SSL state (as defined by SSLStatus) changes.
    306   virtual void DidChangeVisibleSSLState() {}
    307 
    308   // Invoked when an interstitial page is attached or detached.
    309   virtual void DidAttachInterstitialPage() {}
    310   virtual void DidDetachInterstitialPage() {}
    311 
    312   // Invoked before a form repost warning is shown.
    313   virtual void BeforeFormRepostWarningShow() {}
    314 
    315   // Invoked when the beforeunload handler fires. The time is from the renderer.
    316   virtual void BeforeUnloadFired(const base::TimeTicks& proceed_time) {}
    317 
    318   // Invoked when a user cancels a before unload dialog.
    319   virtual void BeforeUnloadDialogCancelled() {}
    320 
    321   // IPC::Listener implementation.
    322   virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE;
    323 
    324   // IPC::Sender implementation.
    325   virtual bool Send(IPC::Message* message) OVERRIDE;
    326   int routing_id() const;
    327 
    328  protected:
    329   // Use this constructor when the object is tied to a single WebContents for
    330   // its entire lifetime.
    331   explicit WebContentsObserver(WebContents* web_contents);
    332 
    333   // Use this constructor when the object wants to observe a WebContents for
    334   // part of its lifetime.  It can then call Observe() to start and stop
    335   // observing.
    336   WebContentsObserver();
    337 
    338   virtual ~WebContentsObserver();
    339 
    340   // Start observing a different WebContents; used with the default constructor.
    341   void Observe(WebContents* web_contents);
    342 
    343   WebContents* web_contents() const;
    344 
    345  private:
    346   friend class WebContentsImpl;
    347 
    348   // Invoked from WebContentsImpl. Invokes WebContentsDestroyed and NULL out
    349   // |web_contents_|.
    350   void WebContentsImplDestroyed();
    351 
    352   WebContentsImpl* web_contents_;
    353 
    354   DISALLOW_COPY_AND_ASSIGN(WebContentsObserver);
    355 };
    356 
    357 }  // namespace content
    358 
    359 #endif  // CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_OBSERVER_H_
    360