- add sources.
[platform/framework/web/crosswalk.git] / src / chrome / browser / history / shortcuts_backend.h
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 CHROME_BROWSER_HISTORY_SHORTCUTS_BACKEND_H_
6 #define CHROME_BROWSER_HISTORY_SHORTCUTS_BACKEND_H_
7
8 #include <map>
9 #include <string>
10 #include <vector>
11
12 #include "base/files/file_path.h"
13 #include "base/gtest_prod_util.h"
14 #include "base/memory/ref_counted.h"
15 #include "base/memory/scoped_ptr.h"
16 #include "base/observer_list.h"
17 #include "base/strings/string16.h"
18 #include "base/synchronization/lock.h"
19 #include "base/time/time.h"
20 #include "chrome/browser/autocomplete/autocomplete_match.h"
21 #include "components/browser_context_keyed_service/refcounted_browser_context_keyed_service.h"
22 #include "content/public/browser/notification_observer.h"
23 #include "content/public/browser/notification_registrar.h"
24 #include "url/gurl.h"
25
26 class Profile;
27
28 namespace history {
29
30 class ShortcutsDatabase;
31
32 // This class manages the shortcut provider backend - access to database on the
33 // db thread, etc.
34 class ShortcutsBackend : public RefcountedBrowserContextKeyedService,
35                          public content::NotificationObserver {
36  public:
37   // The following struct encapsulates one previously selected omnibox shortcut.
38   struct Shortcut {
39     // The pieces of an AutocompleteMatch that we preserve in a shortcut.
40     struct MatchCore {
41       explicit MatchCore(const AutocompleteMatch& match);
42       MatchCore(const string16& fill_into_edit,
43                 const GURL& destination_url,
44                 const string16& contents,
45                 const ACMatchClassifications& contents_class,
46                 const string16& description,
47                 const ACMatchClassifications& description_class,
48                 content::PageTransition transition,
49                 AutocompleteMatch::Type type,
50                 const string16& keyword);
51       ~MatchCore();
52
53       AutocompleteMatch ToMatch() const;
54
55       string16 fill_into_edit;
56       GURL destination_url;
57       string16 contents;
58       // For both contents_class and description_class, we strip MATCH
59       // classifications; the ShortcutsProvider will re-mark MATCH regions based
60       // on the user's current typing.
61       ACMatchClassifications contents_class;
62       string16 description;
63       ACMatchClassifications description_class;
64       content::PageTransition transition;
65       AutocompleteMatch::Type type;
66       string16 keyword;
67     };
68
69     Shortcut(const std::string& id,
70              const string16& text,
71              const MatchCore& match_core,
72              const base::Time& last_access_time,
73              int number_of_hits);
74     // Required for STL, we don't use this directly.
75     Shortcut();
76     ~Shortcut();
77
78     std::string id;  // Unique guid for the shortcut.
79     string16 text;   // The user's original input string.
80     MatchCore match_core;
81     base::Time last_access_time;  // Last time shortcut was selected.
82     int number_of_hits;           // How many times shortcut was selected.
83   };
84
85   typedef std::multimap<string16, const Shortcut> ShortcutMap;
86
87   // |profile| is necessary for profile notifications only and can be NULL in
88   // unit-tests. For unit testing, set |suppress_db| to true to prevent creation
89   // of the database, in which case all operations are performed in memory only.
90   ShortcutsBackend(Profile* profile, bool suppress_db);
91
92   // The interface is guaranteed to be called on the thread AddObserver()
93   // was called.
94   class ShortcutsBackendObserver {
95    public:
96     // Called after the database is loaded and Init() completed.
97     virtual void OnShortcutsLoaded() = 0;
98     // Called when shortcuts changed (added/updated/removed) in the database.
99     virtual void OnShortcutsChanged() {}
100
101    protected:
102     virtual ~ShortcutsBackendObserver() {}
103   };
104
105   // Asynchronously initializes the ShortcutsBackend, it is safe to call
106   // multiple times - only the first call will be processed.
107   bool Init();
108
109   // All of the public functions *must* be called on UI thread only!
110
111   bool initialized() const { return current_state_ == INITIALIZED; }
112   const ShortcutMap& shortcuts_map() const { return shortcuts_map_; }
113
114   // Deletes the Shortcuts with the url.
115   bool DeleteShortcutsWithUrl(const GURL& shortcut_url);
116
117   void AddObserver(ShortcutsBackendObserver* obs);
118   void RemoveObserver(ShortcutsBackendObserver* obs);
119
120   // Called when a successful omnibox navigation occurs.  Adds a corresponding
121   // shortcut.
122   void OnOmniboxNavigation(const string16& text,
123                            const AutocompleteMatch& match);
124
125  private:
126   friend class base::RefCountedThreadSafe<ShortcutsBackend>;
127   friend class ShortcutsProviderTest;
128   FRIEND_TEST_ALL_PREFIXES(ShortcutsBackendTest, AddAndUpdateShortcut);
129   FRIEND_TEST_ALL_PREFIXES(ShortcutsBackendTest, DeleteShortcuts);
130
131   enum CurrentState {
132     NOT_INITIALIZED,  // Backend created but not initialized.
133     INITIALIZING,     // Init() called, but not completed yet.
134     INITIALIZED,      // Initialization completed, all accessors can be safely
135                       // called.
136   };
137
138   typedef std::map<std::string, ShortcutMap::iterator> GuidMap;
139
140   virtual ~ShortcutsBackend();
141
142   // RefcountedBrowserContextKeyedService:
143   virtual void ShutdownOnUIThread() OVERRIDE;
144
145   // content::NotificationObserver:
146   virtual void Observe(int type,
147                        const content::NotificationSource& source,
148                        const content::NotificationDetails& details) OVERRIDE;
149
150   // Internal initialization of the back-end. Posted by Init() to the DB thread.
151   // On completion posts InitCompleted() back to UI thread.
152   void InitInternal();
153
154   // Finishes initialization on UI thread, notifies all observers.
155   void InitCompleted();
156
157   // Adds the Shortcut to the database.
158   bool AddShortcut(const Shortcut& shortcut);
159
160   // Updates timing and selection count for the Shortcut.
161   bool UpdateShortcut(const Shortcut& shortcut);
162
163   // Deletes the Shortcuts with the id.
164   bool DeleteShortcutsWithIds(const std::vector<std::string>& shortcut_ids);
165
166   // Deletes all shortcuts whose URLs begin with |url|.  If |exact_match| is
167   // true, only shortcuts from exactly |url| are deleted.
168   bool DeleteShortcutsWithUrl(const GURL& url, bool exact_match);
169
170   // Deletes all of the shortcuts.
171   bool DeleteAllShortcuts();
172
173   CurrentState current_state_;
174   ObserverList<ShortcutsBackendObserver> observer_list_;
175   scoped_refptr<ShortcutsDatabase> db_;
176
177   // The |temp_shortcuts_map_| and |temp_guid_map_| used for temporary storage
178   // between InitInternal() and InitComplete() to avoid doing a potentially huge
179   // copy.
180   scoped_ptr<ShortcutMap> temp_shortcuts_map_;
181   scoped_ptr<GuidMap> temp_guid_map_;
182
183   ShortcutMap shortcuts_map_;
184   // This is a helper map for quick access to a shortcut by guid.
185   GuidMap guid_map_;
186
187   content::NotificationRegistrar notification_registrar_;
188
189   // For some unit-test only.
190   bool no_db_access_;
191
192   DISALLOW_COPY_AND_ASSIGN(ShortcutsBackend);
193 };
194
195 }  // namespace history
196
197 #endif  // CHROME_BROWSER_HISTORY_SHORTCUTS_BACKEND_H_