Index: content/browser/in_process_webkit/dom_storage_context.cc |
diff --git a/content/browser/in_process_webkit/dom_storage_context.cc b/content/browser/in_process_webkit/dom_storage_context.cc |
index c276d7614c1530f88d6472ee1f27bbde1f650d5f..3cc0e9de6012c430301cfe7e6a0929b449ba558a 100644 |
--- a/content/browser/in_process_webkit/dom_storage_context.cc |
+++ b/content/browser/in_process_webkit/dom_storage_context.cc |
@@ -11,6 +11,7 @@ |
#include "base/file_util.h" |
#include "base/string_util.h" |
#include "content/browser/in_process_webkit/dom_storage_area.h" |
+#include "content/browser/in_process_webkit/dom_storage_message_filter.h" |
#include "content/browser/in_process_webkit/dom_storage_namespace.h" |
#include "content/browser/in_process_webkit/webkit_context.h" |
#include "content/common/dom_storage_common.h" |
@@ -52,6 +53,9 @@ void ClearLocalState(const FilePath& domstorage_path, |
const FilePath::CharType DOMStorageContext::kLocalStorageDirectory[] = |
FILE_PATH_LITERAL("Local Storage"); |
+const FilePath::CharType DOMStorageContext::kSessionStorageDirectory[] = |
+ FILE_PATH_LITERAL("Session Storage"); |
+ |
const FilePath::CharType DOMStorageContext::kLocalStorageExtension[] = |
FILE_PATH_LITERAL(".localstorage"); |
@@ -114,7 +118,7 @@ int64 DOMStorageContext::CloneSessionStorage(int64 original_id) { |
BrowserThread::PostTask( |
BrowserThread::WEBKIT_DEPRECATED, FROM_HERE, |
base::Bind(&DOMStorageContext::CompleteCloningSessionStorage, this, |
- original_id, clone_id)); |
+ original_id, clone_id, data_path_)); |
return clone_id; |
} |
@@ -147,8 +151,17 @@ void DOMStorageContext::DeleteSessionStorageNamespace(int64 namespace_id) { |
if (iter == storage_namespace_map_.end()) |
return; |
DCHECK(iter->second->dom_storage_type() == DOM_STORAGE_SESSION); |
+ FilePath session_storage_directory = |
+ iter->second->session_storage_directory(); |
delete iter->second; |
storage_namespace_map_.erase(iter); |
+ |
+ if (!save_session_state_ && |
+ !session_storage_directory.empty() && |
+ !data_path_.empty()) { |
+ FilePath to_delete = data_path_.Append(kSessionStorageDirectory) |
+ .Append(session_storage_directory); |
+ } |
} |
DOMStorageNamespace* DOMStorageContext::GetStorageNamespace( |
@@ -164,6 +177,20 @@ DOMStorageNamespace* DOMStorageContext::GetStorageNamespace( |
return CreateSessionStorage(id); |
} |
+DOMStorageNamespace* DOMStorageContext::RecreateSessionStorageNamespace( |
+ int64 id, |
+ const FilePath& session_storage_directory) { |
+ FilePath dir_path; |
+ if (!data_path_.empty()) { |
+ dir_path = data_path_.Append(kSessionStorageDirectory) |
+ .Append(session_storage_directory); |
+ } |
+ DOMStorageNamespace* new_namespace = |
+ DOMStorageNamespace::CreateSessionStorageNamespace(this, dir_path, id); |
+ RegisterStorageNamespace(new_namespace); |
+ return new_namespace; |
+} |
+ |
void DOMStorageContext::RegisterMessageFilter( |
DOMStorageMessageFilter* message_filter) { |
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); |
@@ -195,6 +222,13 @@ void DOMStorageContext::PurgeMemory() { |
GetStorageNamespace(kLocalStorageNamespaceId, false); |
if (local_storage) |
local_storage->PurgeMemory(); |
+ // In non-incognito profiles, the sessionStorage is backed up on the disk, and |
+ // can be purged. |
+ if (!data_path_.empty()) { |
+ for (StorageNamespaceMap::iterator it = storage_namespace_map_.begin(); |
+ it != storage_namespace_map_.end(); ++it) { |
+ } |
+ } |
} |
void DOMStorageContext::DeleteDataModifiedSince(const base::Time& cutoff) { |
@@ -265,8 +299,18 @@ DOMStorageNamespace* DOMStorageContext::CreateLocalStorage() { |
DOMStorageNamespace* DOMStorageContext::CreateSessionStorage( |
int64 namespace_id) { |
+ FilePath dir_path; |
+ if (!data_path_.empty()) { |
+ // We cannot derive the directory name for the sessionStorage databases |
+ // directly from |namespace_id|. There is no guarantee that the same |
+ // namespace ID won't be reused before we restore the session. |
+ file_util::CreateDirectory(data_path_.Append(kSessionStorageDirectory)); |
+ file_util::CreateTemporaryDirInDir( |
+ data_path_.Append(kSessionStorageDirectory), "", &dir_path); |
+ } |
DOMStorageNamespace* new_namespace = |
- DOMStorageNamespace::CreateSessionStorageNamespace(this, namespace_id); |
+ DOMStorageNamespace::CreateSessionStorageNamespace(this, dir_path, |
+ namespace_id); |
RegisterStorageNamespace(new_namespace); |
return new_namespace; |
} |
@@ -281,13 +325,33 @@ void DOMStorageContext::RegisterStorageNamespace( |
/* static */ |
void DOMStorageContext::CompleteCloningSessionStorage( |
- DOMStorageContext* context, int64 existing_id, int64 clone_id) { |
+ DOMStorageContext* context, int64 existing_id, int64 clone_id, |
+ const FilePath& data_path) { |
DCHECK(BrowserThread::CurrentlyOn(BrowserThread::WEBKIT_DEPRECATED)); |
DOMStorageNamespace* existing_namespace = |
context->GetStorageNamespace(existing_id, false); |
// If nothing exists, then there's nothing to clone. |
- if (existing_namespace) |
- context->RegisterStorageNamespace(existing_namespace->Copy(clone_id)); |
+ if (existing_namespace) { |
+ if (data_path.empty()) { |
+ // Incognito session storage. |
+ context->RegisterStorageNamespace(existing_namespace->Copy(clone_id)); |
+ } else { |
+ DOMStorageNamespace* clone_namespace = |
+ context->CreateSessionStorage(clone_id); |
+ // Copy (in-memory) data from the existing namespace to the clone. Rely on |
+ // lazy writing to sync the data eventually on disk. |
+ DOMStorageNamespace* existing_namespace = |
+ context->GetStorageNamespace(existing_id, false); |
+ DCHECK(existing_namespace); |
+ |
+ // Ensure the copying won't cause storage events. |
+ DOMStorageMessageFilter::SetIgnoreStorageEvents(true); |
+ |
+ existing_namespace->CopyDataTo(clone_namespace); |
+ |
+ DOMStorageMessageFilter::SetIgnoreStorageEvents(false); |
+ } |
+ } |
} |
FilePath DOMStorageContext::GetLocalStorageFilePath( |
@@ -298,3 +362,16 @@ FilePath DOMStorageContext::GetLocalStorageFilePath( |
webkit_glue::WebStringToFilePathString(origin_id); |
return storageDir.Append(id.append(kLocalStorageExtension)); |
} |
+ |
+void DOMStorageContext::DeleteUnneededSessionStorages( |
+ const std::set<std::string>& needed_session_storages) { |
+ file_util::FileEnumerator file_enumerator( |
+ data_path_.Append(kSessionStorageDirectory), |
+ false, file_util::FileEnumerator::DIRECTORIES); |
+ for (FilePath file_path = file_enumerator.Next(); !file_path.empty(); |
+ file_path = file_enumerator.Next()) { |
+ if (needed_session_storages.find(file_path.BaseName().value()) == |
+ needed_session_storages.end()) |
+ file_util::Delete(file_path, true); |
+ } |
+} |