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_NAVIGATION_CONTROLLER_H_
      6 #define CONTENT_PUBLIC_BROWSER_NAVIGATION_CONTROLLER_H_
      7 
      8 #include <map>
      9 #include <string>
     10 #include <vector>
     11 
     12 #include "base/memory/ref_counted.h"
     13 #include "base/strings/string16.h"
     14 #include "content/common/content_export.h"
     15 #include "content/public/browser/global_request_id.h"
     16 #include "content/public/common/page_transition_types.h"
     17 #include "content/public/common/referrer.h"
     18 #include "url/gurl.h"
     19 
     20 namespace base {
     21 
     22 class RefCountedMemory;
     23 
     24 }  // namespace base
     25 
     26 namespace content {
     27 
     28 class BrowserContext;
     29 class NavigationEntry;
     30 class SessionStorageNamespace;
     31 class WebContents;
     32 
     33 // Used to store the mapping of a StoragePartition id to
     34 // SessionStorageNamespace.
     35 typedef std::map<std::string, scoped_refptr<SessionStorageNamespace> >
     36     SessionStorageNamespaceMap;
     37 
     38 // A NavigationController maintains the back-forward list for a WebContents and
     39 // manages all navigation within that list.
     40 //
     41 // Each NavigationController belongs to one WebContents; each WebContents has
     42 // exactly one NavigationController.
     43 class NavigationController {
     44  public:
     45   enum ReloadType {
     46     NO_RELOAD,                   // Normal load.
     47     RELOAD,                      // Normal (cache-validating) reload.
     48     RELOAD_IGNORING_CACHE,       // Reload bypassing the cache (shift-reload).
     49     RELOAD_ORIGINAL_REQUEST_URL  // Reload using the original request URL.
     50   };
     51 
     52   // Load type used in LoadURLParams.
     53   enum LoadURLType {
     54     // For loads that do not fall into any types below.
     55     LOAD_TYPE_DEFAULT,
     56 
     57     // An http post load request initiated from browser side.
     58     // The post data is passed in |browser_initiated_post_data|.
     59     LOAD_TYPE_BROWSER_INITIATED_HTTP_POST,
     60 
     61     // Loads a 'data:' scheme URL with specified base URL and a history entry
     62     // URL. This is only safe to be used for browser-initiated data: URL
     63     // navigations, since it shows arbitrary content as if it comes from
     64     // |virtual_url_for_data_url|.
     65     LOAD_TYPE_DATA
     66 
     67     // Adding new LoadURLType? Also update LoadUrlParams.java static constants.
     68   };
     69 
     70   // User agent override type used in LoadURLParams.
     71   enum UserAgentOverrideOption {
     72     // Use the override value from the previous NavigationEntry in the
     73     // NavigationController.
     74     UA_OVERRIDE_INHERIT,
     75 
     76     // Use the default user agent.
     77     UA_OVERRIDE_FALSE,
     78 
     79     // Use the user agent override, if it's available.
     80     UA_OVERRIDE_TRUE
     81 
     82     // Adding new UserAgentOverrideOption? Also update LoadUrlParams.java
     83     // static constants.
     84   };
     85 
     86   enum RestoreType {
     87     // Indicates the restore is from the current session. For example, restoring
     88     // a closed tab.
     89     RESTORE_CURRENT_SESSION,
     90 
     91     // Restore from the previous session.
     92     RESTORE_LAST_SESSION_EXITED_CLEANLY,
     93     RESTORE_LAST_SESSION_CRASHED,
     94   };
     95 
     96   // Creates a navigation entry and translates the virtual url to a real one.
     97   // This is a general call; prefer LoadURL[FromRenderer]/TransferURL below.
     98   // Extra headers are separated by \n.
     99   CONTENT_EXPORT static NavigationEntry* CreateNavigationEntry(
    100       const GURL& url,
    101       const Referrer& referrer,
    102       PageTransition transition,
    103       bool is_renderer_initiated,
    104       const std::string& extra_headers,
    105       BrowserContext* browser_context);
    106 
    107   // Extra optional parameters for LoadURLWithParams.
    108   struct CONTENT_EXPORT LoadURLParams {
    109     // The url to load. This field is required.
    110     GURL url;
    111 
    112     // See LoadURLType comments above.
    113     LoadURLType load_type;
    114 
    115     // PageTransition for this load. See PageTransition for details.
    116     // Note the default value in constructor below.
    117     PageTransition transition_type;
    118 
    119     // The FrameTreeNode ID for the frame to navigate, or -1 for the main frame.
    120     int64 frame_tree_node_id;
    121 
    122     // Referrer for this load. Empty if none.
    123     Referrer referrer;
    124 
    125     // Any redirect URLs that occurred for this navigation before |url|.
    126     // Defaults to an empty vector.
    127     std::vector<GURL> redirect_chain;
    128 
    129     // Extra headers for this load, separated by \n.
    130     std::string extra_headers;
    131 
    132     // True for renderer-initiated navigations. This is
    133     // important for tracking whether to display pending URLs.
    134     bool is_renderer_initiated;
    135 
    136     // User agent override for this load. See comments in
    137     // UserAgentOverrideOption definition.
    138     UserAgentOverrideOption override_user_agent;
    139 
    140     // Marks the new navigation as being transferred from one RVH to another.
    141     // In this case the browser can recycle the old request once the new
    142     // renderer wants to navigate. Identifies the request ID of the old request.
    143     GlobalRequestID transferred_global_request_id;
    144 
    145     // Used in LOAD_TYPE_DATA loads only. Used for specifying a base URL
    146     // for pages loaded via data URLs.
    147     GURL base_url_for_data_url;
    148 
    149     // Used in LOAD_TYPE_DATA loads only. URL displayed to the user for
    150     // data loads.
    151     GURL virtual_url_for_data_url;
    152 
    153     // Used in LOAD_TYPE_BROWSER_INITIATED_HTTP_POST loads only. Carries the
    154     // post data of the load. Ownership is transferred to NavigationController
    155     // after LoadURLWithParams call.
    156     scoped_refptr<base::RefCountedMemory> browser_initiated_post_data;
    157 
    158     // True if this URL should be able to access local resources.
    159     bool can_load_local_resources;
    160 
    161     // Indicates whether this navigation should replace the current
    162     // navigation entry.
    163     bool should_replace_current_entry;
    164 
    165     // Used to specify which frame to navigate. If empty, the main frame is
    166     // navigated. This is currently only used in tests.
    167     std::string frame_name;
    168 
    169     // Indicates that during this navigation, the session history should be
    170     // cleared such that the resulting page is the first and only entry of the
    171     // session history.
    172     //
    173     // The clearing is done asynchronously, and completes when this navigation
    174     // commits.
    175     bool should_clear_history_list;
    176 
    177     explicit LoadURLParams(const GURL& url);
    178     ~LoadURLParams();
    179 
    180     // Allows copying of LoadURLParams struct.
    181     LoadURLParams(const LoadURLParams& other);
    182     LoadURLParams& operator=(const LoadURLParams& other);
    183   };
    184 
    185   // Disables checking for a repost and prompting the user. This is used during
    186   // testing.
    187   CONTENT_EXPORT static void DisablePromptOnRepost();
    188 
    189   virtual ~NavigationController() {}
    190 
    191   // Returns the web contents associated with this controller. It can never be
    192   // NULL.
    193   virtual WebContents* GetWebContents() const = 0;
    194 
    195   // Get/set the browser context for this controller. It can never be NULL.
    196   virtual BrowserContext* GetBrowserContext() const = 0;
    197   virtual void SetBrowserContext(BrowserContext* browser_context) = 0;
    198 
    199   // Initializes this NavigationController with the given saved navigations,
    200   // using |selected_navigation| as the currently loaded entry. Before this call
    201   // the controller should be unused (there should be no current entry). |type|
    202   // indicates where the restor comes from. This takes ownership of the
    203   // NavigationEntrys in |entries| and clears it out.  This is used for session
    204   // restore.
    205   virtual void Restore(int selected_navigation,
    206                        RestoreType type,
    207                        std::vector<NavigationEntry*>* entries) = 0;
    208 
    209   // Entries -------------------------------------------------------------------
    210 
    211   // There are two basic states for entries: pending and committed. When an
    212   // entry is navigated to, a request is sent to the server. While that request
    213   // has not been responded to, the NavigationEntry is pending. Once data is
    214   // received for that entry, that NavigationEntry is committed.
    215 
    216   // A transient entry is an entry that, when the user navigates away, is
    217   // removed and discarded rather than being added to the back-forward list.
    218   // Transient entries are useful for interstitial pages and the like.
    219 
    220   // Active entry --------------------------------------------------------------
    221 
    222   // THIS IS DEPRECATED. DO NOT USE. Use GetVisibleEntry instead.
    223   //
    224   // Returns the active entry, which is the transient entry if any, the pending
    225   // entry if a navigation is in progress or the last committed entry otherwise.
    226   // NOTE: This can be NULL!!
    227   //
    228   // If you are trying to get the current state of the NavigationController,
    229   // this is the method you will typically want to call.  If you want to display
    230   // the active entry to the user (e.g., in the location bar), use
    231   // GetVisibleEntry instead.
    232   virtual NavigationEntry* GetActiveEntry() const = 0;
    233 
    234   // Returns the same entry as GetActiveEntry, except that it ignores pending
    235   // history navigation entries.  This should be used when displaying info to
    236   // the user, so that the location bar and other indicators do not update for
    237   // a back/forward navigation until the pending entry commits.  This approach
    238   // guards against URL spoofs on slow history navigations.
    239   virtual NavigationEntry* GetVisibleEntry() const = 0;
    240 
    241   // Returns the index from which we would go back/forward or reload.  This is
    242   // the last_committed_entry_index_ if pending_entry_index_ is -1.  Otherwise,
    243   // it is the pending_entry_index_.
    244   virtual int GetCurrentEntryIndex() const = 0;
    245 
    246   // Returns the last committed entry, which may be null if there are no
    247   // committed entries.
    248   virtual NavigationEntry* GetLastCommittedEntry() const = 0;
    249 
    250   // Returns the index of the last committed entry.
    251   virtual int GetLastCommittedEntryIndex() const = 0;
    252 
    253   // Returns true if the source for the current entry can be viewed.
    254   virtual bool CanViewSource() const = 0;
    255 
    256   // Navigation list -----------------------------------------------------------
    257 
    258   // Returns the number of entries in the NavigationController, excluding
    259   // the pending entry if there is one, but including the transient entry if
    260   // any.
    261   virtual int GetEntryCount() const = 0;
    262 
    263   virtual NavigationEntry* GetEntryAtIndex(int index) const = 0;
    264 
    265   // Returns the entry at the specified offset from current.  Returns NULL
    266   // if out of bounds.
    267   virtual NavigationEntry* GetEntryAtOffset(int offset) const = 0;
    268 
    269   // Pending entry -------------------------------------------------------------
    270 
    271   // Discards the pending and transient entries if any.
    272   virtual void DiscardNonCommittedEntries() = 0;
    273 
    274   // Returns the pending entry corresponding to the navigation that is
    275   // currently in progress, or null if there is none.
    276   virtual NavigationEntry* GetPendingEntry() const = 0;
    277 
    278   // Returns the index of the pending entry or -1 if the pending entry
    279   // corresponds to a new navigation (created via LoadURL).
    280   virtual int GetPendingEntryIndex() const = 0;
    281 
    282   // Transient entry -----------------------------------------------------------
    283 
    284   // Returns the transient entry if any. This is an entry which is removed and
    285   // discarded if any navigation occurs. Note that the returned entry is owned
    286   // by the navigation controller and may be deleted at any time.
    287   virtual NavigationEntry* GetTransientEntry() const = 0;
    288 
    289   // Adds an entry that is returned by GetActiveEntry(). The entry is
    290   // transient: any navigation causes it to be removed and discarded.  The
    291   // NavigationController becomes the owner of |entry| and deletes it when
    292   // it discards it. This is useful with interstitial pages that need to be
    293   // represented as an entry, but should go away when the user navigates away
    294   // from them.
    295   // Note that adding a transient entry does not change the active contents.
    296   virtual void SetTransientEntry(NavigationEntry* entry) = 0;
    297 
    298   // New navigations -----------------------------------------------------------
    299 
    300   // Loads the specified URL, specifying extra http headers to add to the
    301   // request.  Extra headers are separated by \n.
    302   virtual void LoadURL(const GURL& url,
    303                        const Referrer& referrer,
    304                        PageTransition type,
    305                        const std::string& extra_headers) = 0;
    306 
    307   // More general version of LoadURL. See comments in LoadURLParams for
    308   // using |params|.
    309   virtual void LoadURLWithParams(const LoadURLParams& params) = 0;
    310 
    311   // Loads the current page if this NavigationController was restored from
    312   // history and the current page has not loaded yet or if the load was
    313   // explicitly requested using SetNeedsReload().
    314   virtual void LoadIfNecessary() = 0;
    315 
    316   // Renavigation --------------------------------------------------------------
    317 
    318   // Navigation relative to the "current entry"
    319   virtual bool CanGoBack() const = 0;
    320   virtual bool CanGoForward() const = 0;
    321   virtual bool CanGoToOffset(int offset) const = 0;
    322   virtual void GoBack() = 0;
    323   virtual void GoForward() = 0;
    324 
    325   // Navigates to the specified absolute index.
    326   virtual void GoToIndex(int index) = 0;
    327 
    328   // Navigates to the specified offset from the "current entry". Does nothing if
    329   // the offset is out of bounds.
    330   virtual void GoToOffset(int offset) = 0;
    331 
    332   // Reloads the current entry. If |check_for_repost| is true and the current
    333   // entry has POST data the user is prompted to see if they really want to
    334   // reload the page. In nearly all cases pass in true.  If a transient entry
    335   // is showing, initiates a new navigation to its URL.
    336   virtual void Reload(bool check_for_repost) = 0;
    337 
    338   // Like Reload(), but don't use caches (aka "shift-reload").
    339   virtual void ReloadIgnoringCache(bool check_for_repost) = 0;
    340 
    341   // Reloads the current entry using the original URL used to create it.  This
    342   // is used for cases where the user wants to refresh a page using a different
    343   // user agent after following a redirect.
    344   virtual void ReloadOriginalRequestURL(bool check_for_repost) = 0;
    345 
    346   // Removing of entries -------------------------------------------------------
    347 
    348   // Removes the entry at the specified |index|.  This call discards any
    349   // transient entries.  If the index is the last committed index or the pending
    350   // entry, this does nothing and returns false.
    351   virtual bool RemoveEntryAtIndex(int index) = 0;
    352 
    353   // Random --------------------------------------------------------------------
    354 
    355   // Session storage depends on dom_storage that depends on blink::WebString,
    356   // which cannot be used on iOS.
    357 #if !defined(OS_IOS)
    358   // Returns all the SessionStorageNamespace objects that this
    359   // NavigationController knows about.
    360   virtual const SessionStorageNamespaceMap&
    361       GetSessionStorageNamespaceMap() const = 0;
    362 
    363   // TODO(ajwong): Remove this once prerendering, instant, and session restore
    364   // are migrated.
    365   virtual SessionStorageNamespace* GetDefaultSessionStorageNamespace() = 0;
    366 #endif
    367 
    368   // Sets the max restored page ID this NavigationController has seen, if it
    369   // was restored from a previous session.
    370   virtual void SetMaxRestoredPageID(int32 max_id) = 0;
    371 
    372   // Returns the largest restored page ID seen in this navigation controller,
    373   // if it was restored from a previous session.  (-1 otherwise)
    374   virtual int32 GetMaxRestoredPageID() const = 0;
    375 
    376   // Returns true if a reload happens when activated (SetActive(true) is
    377   // invoked). This is true for session/tab restore, cloned tabs and tabs that
    378   // requested a reload (using SetNeedsReload()) after their renderer was
    379   // killed.
    380   virtual bool NeedsReload() const = 0;
    381 
    382   // Request a reload to happen when activated. This can be used when a renderer
    383   // backing a background tab is killed by the system on Android or ChromeOS.
    384   virtual void SetNeedsReload() = 0;
    385 
    386   // Cancels a repost that brought up a warning.
    387   virtual void CancelPendingReload() = 0;
    388   // Continues a repost that brought up a warning.
    389   virtual void ContinuePendingReload() = 0;
    390 
    391   // Returns true if we are navigating to the URL the tab is opened with.
    392   // Returns false after the initial navigation has committed.
    393   virtual bool IsInitialNavigation() const = 0;
    394 
    395   // Broadcasts the NOTIFICATION_NAV_ENTRY_CHANGED notification for the given
    396   // entry (which must be at the given index). This will keep things in sync
    397   // like the saved session.
    398   virtual void NotifyEntryChanged(const NavigationEntry* entry, int index) = 0;
    399 
    400   // Copies the navigation state from the given controller to this one. This
    401   // one should be empty (just created).
    402   virtual void CopyStateFrom(const NavigationController& source) = 0;
    403 
    404   // A variant of CopyStateFrom. Removes all entries from this except the last
    405   // committed entry, and inserts all entries from |source| before and including
    406   // its last committed entry. For example:
    407   // source: A B *C* D
    408   // this:   E F *G*
    409   // result: A B C *G*
    410   // If there is a pending entry after *G* in |this|, it is also preserved.
    411   // If |replace_entry| is true, the current entry in |source| is replaced. So
    412   // the result above would be A B *G*.
    413   // This ignores any pending or transient entries in |source|.  Callers must
    414   // ensure that |CanPruneAllButLastCommitted| returns true before calling this,
    415   // or it will crash.
    416   virtual void CopyStateFromAndPrune(NavigationController* source,
    417                                      bool replace_entry) = 0;
    418 
    419   // Returns whether it is safe to call PruneAllButLastCommitted or
    420   // CopyStateFromAndPrune.  There must be a last committed entry, no transient
    421   // entry, and if there is a pending entry, it must be new and not an existing
    422   // entry.
    423   //
    424   // If there were no last committed entry, the pending entry might not commit,
    425   // leaving us with a blank page.  This is unsafe when used with
    426   // |CopyStateFromAndPrune|, which would show an existing entry above the blank
    427   // page.
    428   // If there were a transient entry, we would not want to prune the other
    429   // entries, which the transient entry could be referring to.
    430   // If there were an existing pending entry, we could not prune the last
    431   // committed entry, in case it did not commit.  That would leave us with no
    432   // sensible place to put the pending entry when it did commit, after all other
    433   // entries are pruned.  For example, it could be going back several entries.
    434   // (New pending entries are safe, because they can always commit to the end.)
    435   virtual bool CanPruneAllButLastCommitted() = 0;
    436 
    437   // Removes all the entries except the last committed entry. If there is a new
    438   // pending navigation it is preserved.  Callers must ensure
    439   // |CanPruneAllButLastCommitted| returns true before calling this, or it will
    440   // crash.
    441   virtual void PruneAllButLastCommitted() = 0;
    442 
    443   // Clears all screenshots associated with navigation entries in this
    444   // controller. Useful to reduce memory consumption in low-memory situations.
    445   virtual void ClearAllScreenshots() = 0;
    446 
    447  private:
    448   // This interface should only be implemented inside content.
    449   friend class NavigationControllerImpl;
    450   NavigationController() {}
    451 };
    452 
    453 }  // namespace content
    454 
    455 #endif  // CONTENT_PUBLIC_BROWSER_NAVIGATION_CONTROLLER_H_
    456