mirror of
https://bitbucket.org/chromiumembedded/cef
synced 2025-06-05 21:39:12 +02:00
chrome: Enforce matching context for new user and incognito profiles
Selecting a new user or incognito profile via Chrome UI may result in the creation of a new Profile object. If that occurs, we should find or create a matching CefBrowserContext and CefRequestContext instead of reusing an existing mismatched context (e.g. using the original context for an incognito window would be a mismatch). If a new CefRequestContext will be created the client can now implement CefBrowserProcessHandler::GetDefaultRequestContextHandler() to provide the handler for that context. To test with a new user profile: 1. Click "Profile" icon, select "Add". Now you have 2+ profiles. 2. Click "Profile" icon, select the other user name to create a new window using the other user profile. 3. The new window should launch successfully. To test with a new incognito profile: 1. Select "New Incognito window" from the 3-dot menu. 2. The new window should launch successfully. To test DevTools window creation for the new profile: 1. Right-click in the new window, select Inspect. 2. The DevTools window should launch successfully.
This commit is contained in:
@ -115,7 +115,7 @@ CefRefPtr<CefRequestContext> CefRequestContext::GetGlobalContext() {
|
||||
|
||||
CefRequestContextImpl::Config config;
|
||||
config.is_global = true;
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(config);
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(std::move(config));
|
||||
}
|
||||
|
||||
// static
|
||||
@ -132,7 +132,7 @@ CefRefPtr<CefRequestContext> CefRequestContext::CreateContext(
|
||||
config.settings = settings;
|
||||
config.handler = handler;
|
||||
config.unique_id = g_next_id.GetNext();
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(config);
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(std::move(config));
|
||||
}
|
||||
|
||||
// static
|
||||
@ -153,7 +153,7 @@ CefRefPtr<CefRequestContext> CefRequestContext::CreateContext(
|
||||
config.other = static_cast<CefRequestContextImpl*>(other.get());
|
||||
config.handler = handler;
|
||||
config.unique_id = g_next_id.GetNext();
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(config);
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(std::move(config));
|
||||
}
|
||||
|
||||
// CefRequestContextImpl
|
||||
@ -176,7 +176,8 @@ CefRequestContextImpl::CreateGlobalRequestContext(
|
||||
Config config;
|
||||
config.is_global = true;
|
||||
config.settings = settings;
|
||||
CefRefPtr<CefRequestContextImpl> impl = new CefRequestContextImpl(config);
|
||||
CefRefPtr<CefRequestContextImpl> impl =
|
||||
new CefRequestContextImpl(std::move(config));
|
||||
impl->Initialize();
|
||||
return impl;
|
||||
}
|
||||
@ -193,7 +194,21 @@ CefRequestContextImpl::GetOrCreateForRequestContext(
|
||||
// Use the global context.
|
||||
Config config;
|
||||
config.is_global = true;
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(config);
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(std::move(config));
|
||||
}
|
||||
|
||||
// static
|
||||
CefRefPtr<CefRequestContextImpl>
|
||||
CefRequestContextImpl::GetOrCreateForBrowserContext(
|
||||
CefBrowserContext* browser_context,
|
||||
CefRefPtr<CefRequestContextHandler> handler) {
|
||||
DCHECK(browser_context);
|
||||
|
||||
Config config;
|
||||
config.browser_context = browser_context;
|
||||
config.handler = handler;
|
||||
config.unique_id = g_next_id.GetNext();
|
||||
return CefRequestContextImpl::GetOrCreateRequestContext(std::move(config));
|
||||
}
|
||||
|
||||
content::BrowserContext* CefRequestContextImpl::GetBrowserContext(
|
||||
@ -241,7 +256,6 @@ void CefRequestContextImpl::ExecuteWhenBrowserContextInitialized(
|
||||
return;
|
||||
}
|
||||
|
||||
EnsureBrowserContext();
|
||||
browser_context()->StoreOrTriggerInitCallback(std::move(callback));
|
||||
}
|
||||
|
||||
@ -638,7 +652,32 @@ void CefRequestContextImpl::OnRenderFrameDeleted(
|
||||
|
||||
// static
|
||||
CefRefPtr<CefRequestContextImpl>
|
||||
CefRequestContextImpl::GetOrCreateRequestContext(const Config& config) {
|
||||
CefRequestContextImpl::GetOrCreateRequestContext(Config&& config) {
|
||||
if (config.browser_context) {
|
||||
// CefBrowserContext is only accessed on the UI thread.
|
||||
CEF_REQUIRE_UIT();
|
||||
DCHECK(!config.is_global);
|
||||
DCHECK(!config.other);
|
||||
|
||||
// Retrieve any request context that currently exists for the browser
|
||||
// context. If |config.handler| is nullptr, and the returned request context
|
||||
// does not have a handler, then we can just return that existing context.
|
||||
// Otherwise, we'll need to create a new request context with
|
||||
// |config.handler|.
|
||||
if (auto other = config.browser_context->GetAnyRequestContext(
|
||||
/*prefer_no_handler=*/!config.handler)) {
|
||||
if (!config.handler && !other->GetHandler()) {
|
||||
// Safe to return the existing context.
|
||||
return other;
|
||||
}
|
||||
|
||||
// Use the existing request context as a starting point. It may be the
|
||||
// global context. This is functionally equivalent to calling
|
||||
// `CefRequestContext::CreateContext(other, handler)`.
|
||||
config.other = other;
|
||||
}
|
||||
}
|
||||
|
||||
if (config.is_global ||
|
||||
(config.other && config.other->IsGlobal() && !config.handler)) {
|
||||
// Return the singleton global context.
|
||||
@ -646,8 +685,8 @@ CefRequestContextImpl::GetOrCreateRequestContext(const Config& config) {
|
||||
CefAppManager::Get()->GetGlobalRequestContext().get());
|
||||
}
|
||||
|
||||
// The new context will be initialized later by EnsureBrowserContext().
|
||||
CefRefPtr<CefRequestContextImpl> context = new CefRequestContextImpl(config);
|
||||
CefRefPtr<CefRequestContextImpl> context =
|
||||
new CefRequestContextImpl(std::move(config));
|
||||
|
||||
// Initialize ASAP so that any tasks blocked on initialization will execute.
|
||||
if (CEF_CURRENTLY_ON_UIT()) {
|
||||
@ -661,8 +700,8 @@ CefRequestContextImpl::GetOrCreateRequestContext(const Config& config) {
|
||||
}
|
||||
|
||||
CefRequestContextImpl::CefRequestContextImpl(
|
||||
const CefRequestContextImpl::Config& config)
|
||||
: config_(config) {}
|
||||
CefRequestContextImpl::Config&& config)
|
||||
: config_(std::move(config)) {}
|
||||
|
||||
void CefRequestContextImpl::Initialize() {
|
||||
CEF_REQUIRE_UIT();
|
||||
@ -673,6 +712,9 @@ void CefRequestContextImpl::Initialize() {
|
||||
// Share storage with |config_.other|.
|
||||
browser_context_ = config_.other->browser_context();
|
||||
CHECK(browser_context_);
|
||||
} else if (config_.browser_context) {
|
||||
browser_context_ = config_.browser_context;
|
||||
config_.browser_context = nullptr;
|
||||
}
|
||||
|
||||
if (!browser_context_) {
|
||||
@ -710,9 +752,10 @@ void CefRequestContextImpl::Initialize() {
|
||||
browser_context_->AddCefRequestContext(this);
|
||||
|
||||
if (config_.other) {
|
||||
// Clear the reference to |config_.other| after setting
|
||||
// |request_context_getter_|. This is the reverse order of checks in
|
||||
// IsSharedWith().
|
||||
// Clear the reference to |config_.other| after adding the new assocation
|
||||
// with |browser_context_| as this may result in |other| being released
|
||||
// and we don't want the browser context to be destroyed prematurely.
|
||||
// This is the also the reverse order of checks in IsSharingWith().
|
||||
config_.other = nullptr;
|
||||
}
|
||||
}
|
||||
@ -727,14 +770,6 @@ void CefRequestContextImpl::BrowserContextInitialized() {
|
||||
}
|
||||
}
|
||||
|
||||
void CefRequestContextImpl::EnsureBrowserContext() {
|
||||
CEF_REQUIRE_UIT();
|
||||
if (!browser_context()) {
|
||||
Initialize();
|
||||
}
|
||||
DCHECK(browser_context());
|
||||
}
|
||||
|
||||
void CefRequestContextImpl::ClearCertificateExceptionsInternal(
|
||||
CefRefPtr<CefCompletionCallback> callback,
|
||||
CefBrowserContext::Getter browser_context_getter) {
|
||||
|
Reference in New Issue
Block a user