OLD | NEW |
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "chrome/browser/bookmarks/bookmark_storage.h" | 5 #include "chrome/browser/bookmarks/bookmark_storage.h" |
6 | 6 |
7 #include "base/compiler_specific.h" | 7 #include "base/compiler_specific.h" |
8 #include "base/file_util.h" | 8 #include "base/file_util.h" |
9 #include "base/histogram.h" | 9 #include "base/histogram.h" |
10 #include "base/message_loop.h" | |
11 #include "base/thread.h" | |
12 #include "base/time.h" | 10 #include "base/time.h" |
13 #include "chrome/browser/bookmarks/bookmark_codec.h" | 11 #include "chrome/browser/bookmarks/bookmark_codec.h" |
14 #include "chrome/browser/bookmarks/bookmark_model.h" | 12 #include "chrome/browser/bookmarks/bookmark_model.h" |
15 #include "chrome/browser/browser_process.h" | 13 #include "chrome/browser/chrome_thread.h" |
16 #include "chrome/browser/profile.h" | 14 #include "chrome/browser/profile.h" |
17 #include "chrome/common/chrome_constants.h" | 15 #include "chrome/common/chrome_constants.h" |
18 #include "chrome/common/json_value_serializer.h" | 16 #include "chrome/common/json_value_serializer.h" |
19 #include "chrome/common/notification_source.h" | 17 #include "chrome/common/notification_source.h" |
20 #include "chrome/common/notification_type.h" | 18 #include "chrome/common/notification_type.h" |
21 | 19 |
22 using base::TimeTicks; | 20 using base::TimeTicks; |
23 | 21 |
24 namespace { | 22 namespace { |
25 | 23 |
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
58 const FilePath path_; | 56 const FilePath path_; |
59 | 57 |
60 DISALLOW_COPY_AND_ASSIGN(FileDeleteTask); | 58 DISALLOW_COPY_AND_ASSIGN(FileDeleteTask); |
61 }; | 59 }; |
62 | 60 |
63 } // namespace | 61 } // namespace |
64 | 62 |
65 class BookmarkStorage::LoadTask : public Task { | 63 class BookmarkStorage::LoadTask : public Task { |
66 public: | 64 public: |
67 LoadTask(const FilePath& path, | 65 LoadTask(const FilePath& path, |
68 MessageLoop* loop, | |
69 BookmarkStorage* storage, | 66 BookmarkStorage* storage, |
70 LoadDetails* details) | 67 LoadDetails* details) |
71 : path_(path), | 68 : path_(path), |
72 loop_(loop), | |
73 storage_(storage), | 69 storage_(storage), |
74 details_(details) { | 70 details_(details) { |
75 } | 71 } |
76 | 72 |
77 virtual void Run() { | 73 virtual void Run() { |
78 bool bookmark_file_exists = file_util::PathExists(path_); | 74 bool bookmark_file_exists = file_util::PathExists(path_); |
79 if (bookmark_file_exists) { | 75 if (bookmark_file_exists) { |
80 JSONFileValueSerializer serializer(path_); | 76 JSONFileValueSerializer serializer(path_); |
81 scoped_ptr<Value> root(serializer.Deserialize(NULL)); | 77 scoped_ptr<Value> root(serializer.Deserialize(NULL)); |
82 | 78 |
(...skipping 13 matching lines...) Expand all Loading... |
96 TimeTicks::Now() - start_time); | 92 TimeTicks::Now() - start_time); |
97 | 93 |
98 start_time = TimeTicks::Now(); | 94 start_time = TimeTicks::Now(); |
99 AddBookmarksToIndex(details_->bb_node()); | 95 AddBookmarksToIndex(details_->bb_node()); |
100 AddBookmarksToIndex(details_->other_folder_node()); | 96 AddBookmarksToIndex(details_->other_folder_node()); |
101 UMA_HISTOGRAM_TIMES("Bookmarks.CreateBookmarkIndexTime", | 97 UMA_HISTOGRAM_TIMES("Bookmarks.CreateBookmarkIndexTime", |
102 TimeTicks::Now() - start_time); | 98 TimeTicks::Now() - start_time); |
103 } | 99 } |
104 } | 100 } |
105 | 101 |
106 if (loop_) { | 102 ChromeThread::PostTask( |
107 loop_->PostTask(FROM_HERE, NewRunnableMethod( | 103 ChromeThread::UI, FROM_HERE, |
108 storage_.get(), &BookmarkStorage::OnLoadFinished, | 104 NewRunnableMethod( |
109 bookmark_file_exists, path_)); | 105 storage_.get(), &BookmarkStorage::OnLoadFinished, |
110 } else { | 106 bookmark_file_exists, path_)); |
111 storage_->OnLoadFinished(bookmark_file_exists, path_); | |
112 } | |
113 } | 107 } |
114 | 108 |
115 private: | 109 private: |
116 // Adds node to the model's index, recursing through all children as well. | 110 // Adds node to the model's index, recursing through all children as well. |
117 void AddBookmarksToIndex(BookmarkNode* node) { | 111 void AddBookmarksToIndex(BookmarkNode* node) { |
118 if (node->is_url()) { | 112 if (node->is_url()) { |
119 if (node->GetURL().is_valid()) | 113 if (node->GetURL().is_valid()) |
120 details_->index()->Add(node); | 114 details_->index()->Add(node); |
121 } else { | 115 } else { |
122 for (int i = 0; i < node->GetChildCount(); ++i) | 116 for (int i = 0; i < node->GetChildCount(); ++i) |
123 AddBookmarksToIndex(node->GetChild(i)); | 117 AddBookmarksToIndex(node->GetChild(i)); |
124 } | 118 } |
125 } | 119 } |
126 | 120 |
127 const FilePath path_; | 121 const FilePath path_; |
128 MessageLoop* loop_; | |
129 scoped_refptr<BookmarkStorage> storage_; | 122 scoped_refptr<BookmarkStorage> storage_; |
130 LoadDetails* details_; | 123 LoadDetails* details_; |
131 | 124 |
132 DISALLOW_COPY_AND_ASSIGN(LoadTask); | 125 DISALLOW_COPY_AND_ASSIGN(LoadTask); |
133 }; | 126 }; |
134 | 127 |
135 // BookmarkStorage ------------------------------------------------------------- | 128 // BookmarkStorage ------------------------------------------------------------- |
136 | 129 |
137 BookmarkStorage::BookmarkStorage(Profile* profile, BookmarkModel* model) | 130 BookmarkStorage::BookmarkStorage(Profile* profile, BookmarkModel* model) |
138 : profile_(profile), | 131 : profile_(profile), |
139 model_(model), | 132 model_(model), |
140 backend_thread_(g_browser_process->file_thread()), | 133 writer_(profile->GetPath().Append(chrome::kBookmarksFileName)), |
141 writer_(profile->GetPath().Append(chrome::kBookmarksFileName), | |
142 backend_thread_), | |
143 tmp_history_path_( | 134 tmp_history_path_( |
144 profile->GetPath().Append(chrome::kHistoryBookmarksFileName)) { | 135 profile->GetPath().Append(chrome::kHistoryBookmarksFileName)) { |
145 writer_.set_commit_interval(base::TimeDelta::FromMilliseconds(kSaveDelayMS)); | 136 writer_.set_commit_interval(base::TimeDelta::FromMilliseconds(kSaveDelayMS)); |
146 RunTaskOnBackendThread(new BackupTask(writer_.path())); | 137 ChromeThread::PostTask( |
| 138 ChromeThread::FILE, FROM_HERE, new BackupTask(writer_.path())); |
147 } | 139 } |
148 | 140 |
149 BookmarkStorage::~BookmarkStorage() { | 141 BookmarkStorage::~BookmarkStorage() { |
150 if (writer_.HasPendingWrite()) | 142 if (writer_.HasPendingWrite()) |
151 writer_.DoScheduledWrite(); | 143 writer_.DoScheduledWrite(); |
152 } | 144 } |
153 | 145 |
154 void BookmarkStorage::LoadBookmarks(LoadDetails* details) { | 146 void BookmarkStorage::LoadBookmarks(LoadDetails* details) { |
155 DCHECK(!details_.get()); | 147 DCHECK(!details_.get()); |
156 DCHECK(details); | 148 DCHECK(details); |
157 details_.reset(details); | 149 details_.reset(details); |
158 DoLoadBookmarks(writer_.path()); | 150 DoLoadBookmarks(writer_.path()); |
159 } | 151 } |
160 | 152 |
161 void BookmarkStorage::DoLoadBookmarks(const FilePath& path) { | 153 void BookmarkStorage::DoLoadBookmarks(const FilePath& path) { |
162 Task* task = new LoadTask(path, | 154 ChromeThread::PostTask( |
163 backend_thread() ? MessageLoop::current() : NULL, | 155 ChromeThread::FILE, FROM_HERE, new LoadTask(path, this, details_.get())); |
164 this, | |
165 details_.get()); | |
166 RunTaskOnBackendThread(task); | |
167 } | 156 } |
168 | 157 |
169 void BookmarkStorage::MigrateFromHistory() { | 158 void BookmarkStorage::MigrateFromHistory() { |
170 // We need to wait until history has finished loading before reading | 159 // We need to wait until history has finished loading before reading |
171 // from generated bookmarks file. | 160 // from generated bookmarks file. |
172 HistoryService* history = | 161 HistoryService* history = |
173 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); | 162 profile_->GetHistoryService(Profile::EXPLICIT_ACCESS); |
174 if (!history) { | 163 if (!history) { |
175 // This happens in unit tests. | 164 // This happens in unit tests. |
176 if (model_) | 165 if (model_) |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
231 return; | 220 return; |
232 | 221 |
233 model_->DoneLoading(details_.release()); | 222 model_->DoneLoading(details_.release()); |
234 | 223 |
235 if (path == tmp_history_path_) { | 224 if (path == tmp_history_path_) { |
236 // We just finished migration from history. Save now to new file, | 225 // We just finished migration from history. Save now to new file, |
237 // after the model is created and done loading. | 226 // after the model is created and done loading. |
238 SaveNow(); | 227 SaveNow(); |
239 | 228 |
240 // Clean up after migration from history. | 229 // Clean up after migration from history. |
241 RunTaskOnBackendThread(new FileDeleteTask(tmp_history_path_)); | 230 ChromeThread::PostTask( |
| 231 ChromeThread::FILE, FROM_HERE, new FileDeleteTask(tmp_history_path_)); |
242 } | 232 } |
243 } | 233 } |
244 | 234 |
245 void BookmarkStorage::Observe(NotificationType type, | 235 void BookmarkStorage::Observe(NotificationType type, |
246 const NotificationSource& source, | 236 const NotificationSource& source, |
247 const NotificationDetails& details) { | 237 const NotificationDetails& details) { |
248 switch (type.value) { | 238 switch (type.value) { |
249 case NotificationType::HISTORY_LOADED: | 239 case NotificationType::HISTORY_LOADED: |
250 OnHistoryFinishedWriting(); | 240 OnHistoryFinishedWriting(); |
251 break; | 241 break; |
(...skipping 11 matching lines...) Expand all Loading... |
263 NOTREACHED(); | 253 NOTREACHED(); |
264 return false; | 254 return false; |
265 } | 255 } |
266 | 256 |
267 std::string data; | 257 std::string data; |
268 if (!SerializeData(&data)) | 258 if (!SerializeData(&data)) |
269 return false; | 259 return false; |
270 writer_.WriteNow(data); | 260 writer_.WriteNow(data); |
271 return true; | 261 return true; |
272 } | 262 } |
273 | |
274 void BookmarkStorage::RunTaskOnBackendThread(Task* task) const { | |
275 if (backend_thread()) { | |
276 backend_thread()->message_loop()->PostTask(FROM_HERE, task); | |
277 } else { | |
278 task->Run(); | |
279 delete task; | |
280 } | |
281 } | |
OLD | NEW |