• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 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 CHROME_BROWSER_UI_OMNIBOX_OMNIBOX_NAVIGATION_OBSERVER_H_
6 #define CHROME_BROWSER_UI_OMNIBOX_OMNIBOX_NAVIGATION_OBSERVER_H_
7 
8 #include <string>
9 
10 #include "base/memory/ref_counted.h"
11 #include "base/memory/scoped_ptr.h"
12 #include "chrome/browser/autocomplete/autocomplete_match.h"
13 #include "content/public/browser/notification_observer.h"
14 #include "content/public/browser/notification_registrar.h"
15 #include "content/public/browser/web_contents_observer.h"
16 #include "net/url_request/url_fetcher_delegate.h"
17 
18 namespace history {
19 class ShortcutsBackend;
20 }
21 
22 namespace net {
23 class URLFetcher;
24 class URLRequestStatus;
25 }
26 
27 // Monitors omnibox navigations in order to trigger behaviors that depend on
28 // successful navigations.
29 //
30 // Currently two such behaviors exist:
31 // (1) For single-word queries where we can't tell if the entry was a search or
32 //     an intranet hostname, the omnibox opens as a search by default, but this
33 //     class attempts to open as a URL via an HTTP HEAD request.  If successful,
34 //     displays an infobar once the search result has also loaded.  See
35 //     AlternateNavInfoBarDelegate.
36 // (2) Omnibox navigations that complete successfully are added to the
37 //     Shortcuts backend.
38 //
39 // TODO(pkasting): Probably NOTIFICATION_OMNIBOX_OPENED_URL should disappear and
40 // everyone who listened to it should be triggered from this class instead.
41 //
42 // The memory management of this object is a bit tricky. The OmniboxEditModel
43 // will create us and be responsible for us until we attach as an observer
44 // after a pending load starts (it will delete us if this doesn't happen).
45 // Once this pending load starts, we're responsible for deleting ourselves.
46 class OmniboxNavigationObserver : public content::NotificationObserver,
47                                   public content::WebContentsObserver,
48                                   public net::URLFetcherDelegate {
49  public:
50   enum LoadState {
51     LOAD_NOT_SEEN,
52     LOAD_PENDING,
53     LOAD_COMMITTED,
54   };
55 
56   OmniboxNavigationObserver(Profile* profile,
57                             const base::string16& text,
58                             const AutocompleteMatch& match,
59                             const AutocompleteMatch& alternate_nav_match);
60   virtual ~OmniboxNavigationObserver();
61 
load_state()62   LoadState load_state() const { return load_state_; }
63 
64   // Called directly by OmniboxEditModel when an extension-related navigation
65   // occurs.  Such navigations don't trigger an immediate NAV_ENTRY_PENDING and
66   // must be handled separately.
67   void OnSuccessfulNavigation();
68 
69  private:
70   enum FetchState {
71     FETCH_NOT_COMPLETE,
72     FETCH_SUCCEEDED,
73     FETCH_FAILED,
74   };
75 
76   // content::NotificationObserver:
77   virtual void Observe(int type,
78                        const content::NotificationSource& source,
79                        const content::NotificationDetails& details) OVERRIDE;
80 
81   // content::WebContentsObserver:
82   virtual void DidStartNavigationToPendingEntry(
83       const GURL& url,
84       content::NavigationController::ReloadType reload_type) OVERRIDE;
85   virtual void NavigationEntryCommitted(
86       const content::LoadCommittedDetails& load_details) OVERRIDE;
87   virtual void WebContentsDestroyed(
88       content::WebContents* web_contents) OVERRIDE;
89 
90   // net::URLFetcherDelegate:
91   virtual void OnURLFetchComplete(const net::URLFetcher* source) OVERRIDE;
92 
93   // Once the load has committed and any URL fetch has completed, this displays
94   // the alternate nav infobar if necessary, and deletes |this|.
95   void OnAllLoadingFinished();
96 
97   const base::string16 text_;
98   const AutocompleteMatch match_;
99   const AutocompleteMatch alternate_nav_match_;
100   scoped_refptr<history::ShortcutsBackend> shortcuts_backend_;  // May be NULL
101                                                                 // in incognito.
102   scoped_ptr<net::URLFetcher> fetcher_;
103   LoadState load_state_;
104   FetchState fetch_state_;
105 
106   content::NotificationRegistrar registrar_;
107 
108   DISALLOW_COPY_AND_ASSIGN(OmniboxNavigationObserver);
109 };
110 
111 #endif  // CHROME_BROWSER_UI_OMNIBOX_OMNIBOX_NAVIGATION_OBSERVER_H_
112