Index: content/browser/storage_partition_impl_map.cc |
diff --git a/content/browser/storage_partition_impl_map.cc b/content/browser/storage_partition_impl_map.cc |
index c5721aee667f653d391592867196ff8950e51c99..0bd097747502c31cde3c960b35156b36294c0367 100644 |
--- a/content/browser/storage_partition_impl_map.cc |
+++ b/content/browser/storage_partition_impl_map.cc |
@@ -18,6 +18,7 @@ |
#include "content/browser/fileapi/browser_file_system_helper.h" |
#include "content/browser/fileapi/chrome_blob_storage_context.h" |
#include "content/browser/loader/resource_request_info_impl.h" |
+#include "content/browser/net/cookie_store_map_impl.h" |
#include "content/browser/resource_context_impl.h" |
#include "content/browser/storage_partition_impl.h" |
#include "content/browser/streams/stream.h" |
@@ -28,10 +29,12 @@ |
#include "content/public/browser/browser_context.h" |
#include "content/public/browser/browser_thread.h" |
#include "content/public/browser/content_browser_client.h" |
+#include "content/public/browser/cookie_store_factory.h" |
#include "content/public/browser/storage_partition.h" |
#include "content/public/common/content_constants.h" |
#include "content/public/common/url_constants.h" |
#include "crypto/sha2.h" |
+#include "net/cookies/cookie_monster.h" |
#include "net/url_request/url_request_context.h" |
#include "net/url_request/url_request_context_getter.h" |
#include "webkit/browser/blob/blob_url_request_job_factory.h" |
@@ -346,6 +349,45 @@ void BlockingGarbageCollect( |
base::Bind(base::IgnoreResult(&base::DeleteFile), trash_directory, true)); |
} |
+void AttachCookieStoreOnIOThread( |
+ const scoped_refptr<net::URLRequestContextGetter>& url_request_context, |
+ const scoped_refptr<net::CookieStore> cookie_store) { |
+ DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); |
+ url_request_context->GetURLRequestContext()->set_cookie_store( |
+ cookie_store.get()); |
+} |
+ |
+net::CookieStore* CreateInMemoryCookieStore( |
+ const CookieStoreConfig& default_config, |
+ bool is_default) { |
+ // See CreatePersistentCookieStore for note about delegates and |is_default|. |
+ if (is_default) { |
+ return CreateCookieStore( |
+ CookieStoreConfig::InMemoryWithOptions( |
+ default_config.storage_policy, default_config.cookie_delegate)); |
+ } else { |
+ return CreateCookieStore(CookieStoreConfig::InMemoryWithOptions( |
+ default_config.storage_policy, NULL)); |
+ } |
+} |
+ |
+net::CookieStore* CreatePersistentCookieStore( |
+ const CookieStoreConfig& default_config, |
+ const base::FilePath& partition_path, |
+ bool is_default) { |
+ // Cookie delegates are not used in the non-default partition. If support |
+ // is to be added for other partitions, then the delegate must be modified |
+ // so it knows which partition cookie changes are sourcing from. |
+ if (is_default) { |
+ return CreateCookieStore(default_config); |
+ } else { |
+ return CreateCookieStore( |
+ CookieStoreConfig::Persistent( |
+ partition_path.Append(kCookieFilename), |
+ default_config.session_cookie_mode)); |
+ } |
+} |
+ |
} // namespace |
// static |
@@ -403,9 +445,52 @@ StoragePartitionImpl* StoragePartitionImplMap::Get( |
base::FilePath partition_path = |
browser_context_->GetPath().Append( |
GetStoragePartitionPath(partition_domain, partition_name)); |
+ |
+ // Create the cookie stores. |
+ scoped_ptr<CookieStoreMapImpl> cookie_store_map(new CookieStoreMapImpl()); |
+ CookieStoreConfig default_config = browser_context_->GetCookieStoreConfig(); |
+ bool in_memory_cookies = in_memory || default_config.in_memory; |
+ browser_context_->OverrideCookieStoreMap(in_memory_cookies, partition_path, |
+ partition_domain.empty(), |
+ cookie_store_map.get()); |
+ |
+ // Add in cookie jars for Http, Https and file (if enabled). |
+ scoped_refptr<net::CookieStore> http_cookie_store = |
+ cookie_store_map->GetForScheme(chrome::kHttpScheme); |
+ if (!http_cookie_store.get()) { |
+ DCHECK(!cookie_store_map->GetForScheme(chrome::kHttpsScheme)); |
+ |
+ if (in_memory_cookies) { |
+ http_cookie_store = CreateInMemoryCookieStore(default_config, |
+ partition_domain.empty()); |
+ } else { |
+ http_cookie_store = CreatePersistentCookieStore(default_config, |
+ partition_path, |
+ partition_domain.empty()); |
+ } |
+ |
+ cookie_store_map->SetForScheme(chrome::kHttpScheme, http_cookie_store); |
+ cookie_store_map->SetForScheme(chrome::kHttpsScheme, http_cookie_store); |
+ } |
+ // There are places in code, such as data deletion, that assume both |
+ // http and https share the same cookie jar. |
+ DCHECK(cookie_store_map->GetForScheme(chrome::kHttpsScheme) == |
+ http_cookie_store); |
+ |
+ // If file scheme is enable, share the same cookie store as http. This is |
Matt Perry
2013/08/07 21:48:56
enabled*
awong
2013/08/16 00:54:54
Done.
|
+ // legacy behavior. A complete valid, alternate approach is to use a |
+ // different cookie database. See comments inside CookieMonster about |
+ // separating out file cookies into their own CookieMonster. |
+ if (!cookie_store_map->GetForScheme(chrome::kFileScheme)) { |
+ if (http_cookie_store->GetCookieMonster()->IsCookieableScheme( |
+ chrome::kFileScheme)) { |
+ cookie_store_map->SetForScheme(chrome::kFileScheme, http_cookie_store); |
+ } |
+ } |
+ |
StoragePartitionImpl* partition = |
StoragePartitionImpl::Create(browser_context_, in_memory, |
- partition_path); |
+ partition_path, cookie_store_map.Pass()); |
partitions_[partition_config] = partition; |
ChromeBlobStorageContext* blob_storage_context = |
@@ -568,8 +653,26 @@ void StoragePartitionImplMap::PostCreateInitialization( |
InitializeResourceContext(browser_context_); |
} |
- // Check first to avoid memory leak in unittests. |
- if (BrowserThread::IsMessageLoopValid(BrowserThread::IO)) { |
+ // In unittests, BrowserThread::IO may not be valid which would yield a |
+ // memory leak on a PostTask. Also, in content_unittests, the |
+ // URLRequestContext is NULL. |
+ // |
+ // TODO(ajwong): Should default ContentBrowserClient return a non-null |
+ // URLRequestContext? |
+ if (BrowserThread::IsMessageLoopValid(BrowserThread::IO) && |
+ partition->GetURLRequestContext()) { |
+ // The main URLRequestContextGetter was first created just before |
+ // PostCreateInitialization() is called thus attaching the CookieStore here |
+ // is guaranteed to occur before anyone else can see the main request |
+ // context including the media request context. |
+ BrowserThread::PostTask( |
+ BrowserThread::IO, FROM_HERE, |
+ base::Bind(&AttachCookieStoreOnIOThread, |
+ make_scoped_refptr(partition->GetURLRequestContext()), |
+ make_scoped_refptr( |
+ partition->GetCookieStoreMap().GetForScheme( |
+ chrome::kHttpScheme)))); |
+ |
BrowserThread::PostTask( |
BrowserThread::IO, FROM_HERE, |
base::Bind(&ChromeAppCacheService::InitializeOnIOThread, |
@@ -581,7 +684,7 @@ void StoragePartitionImplMap::PostCreateInitialization( |
make_scoped_refptr( |
browser_context_->GetSpecialStoragePolicy()))); |
- // We do not call InitializeURLRequestContext() for media contexts because, |
+ // We do not initialize the AppCacheService for media contexts because, |
// other than the HTTP cache, the media contexts share the same backing |
// objects as their associated "normal" request context. Thus, the previous |
// call serves to initialize the media request context for this storage |