| OLD | NEW |
| 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2011 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/sessions/base_session_service.h" | 5 #include "chrome/browser/sessions/base_session_service.h" |
| 6 | 6 |
| 7 #include "base/bind.h" | 7 #include "base/bind.h" |
| 8 #include "base/pickle.h" | 8 #include "base/pickle.h" |
| 9 #include "base/stl_util.h" | 9 #include "base/stl_util.h" |
| 10 #include "base/threading/thread.h" | 10 #include "base/threading/thread.h" |
| 11 #include "chrome/browser/browser_process.h" | 11 #include "chrome/browser/browser_process.h" |
| 12 #include "chrome/browser/profiles/profile.h" | 12 #include "chrome/browser/profiles/profile.h" |
| 13 #include "chrome/browser/sessions/session_backend.h" | 13 #include "chrome/browser/sessions/session_backend.h" |
| 14 #include "chrome/browser/sessions/session_types.h" | 14 #include "chrome/browser/sessions/session_types.h" |
| 15 #include "chrome/common/url_constants.h" | 15 #include "chrome/common/url_constants.h" |
| 16 #include "content/browser/tab_contents/navigation_entry.h" | 16 #include "content/browser/tab_contents/navigation_entry.h" |
| 17 #include "content/public/browser/browser_thread.h" |
| 17 #include "content/public/common/referrer.h" | 18 #include "content/public/common/referrer.h" |
| 18 #include "webkit/glue/webkit_glue.h" | 19 #include "webkit/glue/webkit_glue.h" |
| 19 | 20 |
| 21 using content::BrowserThread; |
| 20 using WebKit::WebReferrerPolicy; | 22 using WebKit::WebReferrerPolicy; |
| 21 | 23 |
| 22 // InternalGetCommandsRequest ------------------------------------------------- | 24 // InternalGetCommandsRequest ------------------------------------------------- |
| 23 | 25 |
| 24 BaseSessionService::InternalGetCommandsRequest::~InternalGetCommandsRequest() { | 26 BaseSessionService::InternalGetCommandsRequest::~InternalGetCommandsRequest() { |
| 25 STLDeleteElements(&commands); | 27 STLDeleteElements(&commands); |
| 26 } | 28 } |
| 27 | 29 |
| 28 // BaseSessionService --------------------------------------------------------- | 30 // BaseSessionService --------------------------------------------------------- |
| 29 | 31 |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 62 static const int kSaveDelayMS = 2500; | 64 static const int kSaveDelayMS = 2500; |
| 63 | 65 |
| 64 // static | 66 // static |
| 65 const int BaseSessionService::max_persist_navigation_count = 6; | 67 const int BaseSessionService::max_persist_navigation_count = 6; |
| 66 | 68 |
| 67 BaseSessionService::BaseSessionService(SessionType type, | 69 BaseSessionService::BaseSessionService(SessionType type, |
| 68 Profile* profile, | 70 Profile* profile, |
| 69 const FilePath& path) | 71 const FilePath& path) |
| 70 : profile_(profile), | 72 : profile_(profile), |
| 71 path_(path), | 73 path_(path), |
| 72 backend_thread_(NULL), | |
| 73 ALLOW_THIS_IN_INITIALIZER_LIST(weak_factory_(this)), | 74 ALLOW_THIS_IN_INITIALIZER_LIST(weak_factory_(this)), |
| 74 pending_reset_(false), | 75 pending_reset_(false), |
| 75 commands_since_reset_(0) { | 76 commands_since_reset_(0) { |
| 76 if (profile) { | 77 if (profile) { |
| 77 // We should never be created when incognito. | 78 // We should never be created when incognito. |
| 78 DCHECK(!profile->IsOffTheRecord()); | 79 DCHECK(!profile->IsOffTheRecord()); |
| 79 } | 80 } |
| 80 backend_ = new SessionBackend(type, | 81 backend_ = new SessionBackend(type, |
| 81 profile_ ? profile_->GetPath() : path_); | 82 profile_ ? profile_->GetPath() : path_); |
| 82 DCHECK(backend_.get()); | 83 DCHECK(backend_.get()); |
| 83 backend_thread_ = g_browser_process->file_thread(); | 84 |
| 84 if (!backend_thread_) | 85 RunTaskOnBackendThread(FROM_HERE, |
| 85 backend_->Init(); | 86 base::Bind(&SessionBackend::Init, backend_)); |
| 86 // If backend_thread is non-null, backend will init itself as appropriate. | |
| 87 } | 87 } |
| 88 | 88 |
| 89 BaseSessionService::~BaseSessionService() { | 89 BaseSessionService::~BaseSessionService() { |
| 90 } | 90 } |
| 91 | 91 |
| 92 void BaseSessionService::DeleteLastSession() { | 92 void BaseSessionService::DeleteLastSession() { |
| 93 if (!backend_thread()) { | 93 RunTaskOnBackendThread( |
| 94 backend()->DeleteLastSession(); | 94 FROM_HERE, |
| 95 } else { | 95 base::Bind(&SessionBackend::DeleteLastSession, backend())); |
| 96 backend_thread()->message_loop()->PostTask( | |
| 97 FROM_HERE, base::Bind(&SessionBackend::DeleteLastSession, backend())); | |
| 98 } | |
| 99 } | 96 } |
| 100 | 97 |
| 101 void BaseSessionService::ScheduleCommand(SessionCommand* command) { | 98 void BaseSessionService::ScheduleCommand(SessionCommand* command) { |
| 102 DCHECK(command); | 99 DCHECK(command); |
| 103 commands_since_reset_++; | 100 commands_since_reset_++; |
| 104 pending_commands_.push_back(command); | 101 pending_commands_.push_back(command); |
| 105 StartSaveTimer(); | 102 StartSaveTimer(); |
| 106 } | 103 } |
| 107 | 104 |
| 108 void BaseSessionService::StartSaveTimer() { | 105 void BaseSessionService::StartSaveTimer() { |
| 109 // Don't start a timer when testing (profile == NULL or | 106 // Don't start a timer when testing (profile == NULL or |
| 110 // MessageLoop::current() is NULL). | 107 // MessageLoop::current() is NULL). |
| 111 if (MessageLoop::current() && profile() && !weak_factory_.HasWeakPtrs()) { | 108 if (MessageLoop::current() && profile() && !weak_factory_.HasWeakPtrs()) { |
| 112 MessageLoop::current()->PostDelayedTask( | 109 MessageLoop::current()->PostDelayedTask( |
| 113 FROM_HERE, | 110 FROM_HERE, |
| 114 base::Bind(&BaseSessionService::Save, weak_factory_.GetWeakPtr()), | 111 base::Bind(&BaseSessionService::Save, weak_factory_.GetWeakPtr()), |
| 115 kSaveDelayMS); | 112 kSaveDelayMS); |
| 116 } | 113 } |
| 117 } | 114 } |
| 118 | 115 |
| 119 void BaseSessionService::Save() { | 116 void BaseSessionService::Save() { |
| 120 DCHECK(backend()); | 117 DCHECK(backend()); |
| 121 | 118 |
| 122 if (pending_commands_.empty()) | 119 if (pending_commands_.empty()) |
| 123 return; | 120 return; |
| 124 | 121 |
| 125 if (!backend_thread()) { | 122 RunTaskOnBackendThread( |
| 126 backend()->AppendCommands( | 123 FROM_HERE, |
| 127 new std::vector<SessionCommand*>(pending_commands_), pending_reset_); | 124 base::Bind(&SessionBackend::AppendCommands, backend(), |
| 128 } else { | 125 new std::vector<SessionCommand*>(pending_commands_), |
| 129 backend_thread()->message_loop()->PostTask( | 126 pending_reset_)); |
| 130 FROM_HERE, | 127 |
| 131 base::Bind(&SessionBackend::AppendCommands, backend(), | |
| 132 new std::vector<SessionCommand*>(pending_commands_), | |
| 133 pending_reset_)); | |
| 134 } | |
| 135 // Backend took ownership of commands. | 128 // Backend took ownership of commands. |
| 136 pending_commands_.clear(); | 129 pending_commands_.clear(); |
| 137 | 130 |
| 138 if (pending_reset_) { | 131 if (pending_reset_) { |
| 139 commands_since_reset_ = 0; | 132 commands_since_reset_ = 0; |
| 140 pending_reset_ = false; | 133 pending_reset_ = false; |
| 141 } | 134 } |
| 142 } | 135 } |
| 143 | 136 |
| 144 SessionCommand* BaseSessionService::CreateUpdateTabNavigationCommand( | 137 SessionCommand* BaseSessionService::CreateUpdateTabNavigationCommand( |
| (...skipping 123 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 268 // NOTE: Do not track print preview tab because re-opening that page will | 261 // NOTE: Do not track print preview tab because re-opening that page will |
| 269 // just display a non-functional print preview page. | 262 // just display a non-functional print preview page. |
| 270 return url.is_valid() && url != GURL(chrome::kChromeUIPrintURL); | 263 return url.is_valid() && url != GURL(chrome::kChromeUIPrintURL); |
| 271 } | 264 } |
| 272 | 265 |
| 273 BaseSessionService::Handle BaseSessionService::ScheduleGetLastSessionCommands( | 266 BaseSessionService::Handle BaseSessionService::ScheduleGetLastSessionCommands( |
| 274 InternalGetCommandsRequest* request, | 267 InternalGetCommandsRequest* request, |
| 275 CancelableRequestConsumerBase* consumer) { | 268 CancelableRequestConsumerBase* consumer) { |
| 276 scoped_refptr<InternalGetCommandsRequest> request_wrapper(request); | 269 scoped_refptr<InternalGetCommandsRequest> request_wrapper(request); |
| 277 AddRequest(request, consumer); | 270 AddRequest(request, consumer); |
| 278 if (backend_thread()) { | 271 RunTaskOnBackendThread( |
| 279 backend_thread()->message_loop()->PostTask( | 272 FROM_HERE, |
| 280 FROM_HERE, | 273 base::Bind(&SessionBackend::ReadLastSessionCommands, backend(), |
| 281 base::Bind(&SessionBackend::ReadLastSessionCommands, backend(), | 274 request_wrapper)); |
| 282 request_wrapper)); | |
| 283 } else { | |
| 284 backend()->ReadLastSessionCommands(request); | |
| 285 } | |
| 286 return request->handle(); | 275 return request->handle(); |
| 287 } | 276 } |
| 288 | 277 |
| 289 BaseSessionService::Handle | 278 BaseSessionService::Handle |
| 290 BaseSessionService::ScheduleGetCurrentSessionCommands( | 279 BaseSessionService::ScheduleGetCurrentSessionCommands( |
| 291 InternalGetCommandsRequest* request, | 280 InternalGetCommandsRequest* request, |
| 292 CancelableRequestConsumerBase* consumer) { | 281 CancelableRequestConsumerBase* consumer) { |
| 293 scoped_refptr<InternalGetCommandsRequest> request_wrapper(request); | 282 scoped_refptr<InternalGetCommandsRequest> request_wrapper(request); |
| 294 AddRequest(request, consumer); | 283 AddRequest(request, consumer); |
| 295 if (backend_thread()) { | 284 RunTaskOnBackendThread( |
| 296 backend_thread()->message_loop()->PostTask( | 285 FROM_HERE, |
| 297 FROM_HERE, | 286 base::Bind(&SessionBackend::ReadCurrentSessionCommands, backend(), |
| 298 base::Bind(&SessionBackend::ReadCurrentSessionCommands, backend(), | 287 request_wrapper)); |
| 299 request_wrapper)); | |
| 300 } else { | |
| 301 backend()->ReadCurrentSessionCommands(request); | |
| 302 } | |
| 303 return request->handle(); | 288 return request->handle(); |
| 304 } | 289 } |
| 290 |
| 291 bool BaseSessionService::RunTaskOnBackendThread( |
| 292 const tracked_objects::Location& from_here, |
| 293 const base::Closure& task) { |
| 294 if (profile_ && BrowserThread::IsMessageLoopValid(BrowserThread::FILE)) { |
| 295 return BrowserThread::PostTask(BrowserThread::FILE, from_here, task); |
| 296 } else { |
| 297 // Fall back to executing on the main thread if the file thread |
| 298 // has gone away (around shutdown time) or if we're running as |
| 299 // part of a unit test that does not set profile_. |
| 300 task.Run(); |
| 301 return true; |
| 302 } |
| 303 } |
| OLD | NEW |