mirror of
https://bitbucket.org/chromiumembedded/cef
synced 2025-06-05 21:39:12 +02:00
Move message routing from CefBrowser to CefFrame (see issue #2498).
This change moves the SendProcessMessage method from CefBrowser to CefFrame and adds CefBrowser parameters to OnProcessMessageReceived and OnDraggableRegionsChanged. The internal implementation has changed as follows: - Frame IDs are now a 64-bit combination of the 32-bit render_process_id and render_routing_id values that uniquely identify a RenderFrameHost (RFH). - CefFrameHostImpl objects are now managed by CefBrowserInfo with life span tied to RFH expectations. Specifically, a CefFrameHostImpl object representing a sub-frame will be created when a RenderFrame is created in the renderer process and detached when the associated RenderFrame is deleted or the renderer process in which it runs has died. - The CefFrameHostImpl object representing the main frame will always be valid but the underlying RFH (and associated frame ID) may change over time as a result of cross-origin navigations. Despite these changes calling LoadURL on the main frame object in the browser process will always navigate as expected. - Speculative RFHs, which may be created as a result of a cross-origin navigation and discarded if that navigation is not committed, are now handled correctly (e.g. ignored in most cases until they're committed). - It is less likely, but still possible, to receive a CefFrame object with an invalid frame ID (ID < 0). This can happen in cases where a RFH has not yet been created for a sub-frame. For example, when OnBeforeBrowse is called before initiating navigation in a previously nonexisting sub-frame. To test: All tests pass with NetworkService enabled and disabled.
This commit is contained in:
@@ -125,6 +125,64 @@ bool IsInternalRequest(const net::URLRequest* request) {
|
||||
return false;
|
||||
}
|
||||
|
||||
CefRefPtr<CefBrowserHostImpl> GetBrowserForRequest(
|
||||
const net::URLRequest* request) {
|
||||
DCHECK(request);
|
||||
CEF_REQUIRE_IOT();
|
||||
|
||||
// When navigating the main frame a new (pre-commit) URLRequest will be
|
||||
// created before the RenderFrameHost. Consequently we can't rely on
|
||||
// ResourceRequestInfo::GetRenderFrameForRequest returning a valid frame
|
||||
// ID. See https://crbug.com/776884 for background.
|
||||
int render_process_id = -1;
|
||||
int render_frame_id = MSG_ROUTING_NONE;
|
||||
if (content::ResourceRequestInfo::GetRenderFrameForRequest(
|
||||
request, &render_process_id, &render_frame_id) &&
|
||||
render_process_id >= 0 && render_frame_id >= 0) {
|
||||
return CefBrowserHostImpl::GetBrowserForFrameRoute(render_process_id,
|
||||
render_frame_id);
|
||||
}
|
||||
|
||||
content::ResourceRequestInfo* request_info =
|
||||
content::ResourceRequestInfo::ForRequest(request);
|
||||
if (request_info) {
|
||||
return CefBrowserHostImpl::GetBrowserForFrameTreeNode(
|
||||
request_info->GetFrameTreeNodeId());
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
CefRefPtr<CefFrame> GetFrameForRequest(
|
||||
scoped_refptr<CefBrowserInfo> browser_info,
|
||||
const net::URLRequest* request) {
|
||||
CEF_REQUIRE_IOT();
|
||||
content::ResourceRequestInfo* info =
|
||||
content::ResourceRequestInfo::ForRequest(request);
|
||||
if (!info)
|
||||
return nullptr;
|
||||
|
||||
// Try to locate the most reasonable match by ID.
|
||||
auto frame =
|
||||
browser_info->GetFrameForFrameTreeNode(info->GetFrameTreeNodeId());
|
||||
if (!frame) {
|
||||
frame = browser_info->GetFrameForRoute(info->GetRouteID(),
|
||||
info->GetRenderFrameID());
|
||||
}
|
||||
if (frame)
|
||||
return frame;
|
||||
|
||||
// The IsMainFrame() flag isn't completely reliable, so do this after
|
||||
// searching by ID.
|
||||
if (info->IsMainFrame())
|
||||
return browser_info->GetMainFrame();
|
||||
|
||||
// Create a temporary frame object for requests referencing sub-frames that
|
||||
// don't yet exist. Use the main frame as the parent because we don't know
|
||||
// the real parent.
|
||||
return browser_info->CreateTempSubFrame(CefFrameHostImpl::kInvalidFrameId);
|
||||
}
|
||||
|
||||
CefRefPtr<CefResourceRequestHandler> GetResourceRequestHandler(
|
||||
const net::URLRequest* request,
|
||||
CefRefPtr<CefRequestImpl>& cef_request,
|
||||
@@ -153,15 +211,14 @@ CefRefPtr<CefResourceRequestHandler> GetResourceRequestHandler(
|
||||
|
||||
CefRefPtr<CefResourceRequestHandler> resource_request_handler;
|
||||
|
||||
CefRefPtr<CefBrowserHostImpl> browser =
|
||||
CefBrowserHostImpl::GetBrowserForRequest(request);
|
||||
CefRefPtr<CefBrowserHostImpl> browser = GetBrowserForRequest(request);
|
||||
CefRefPtr<CefFrame> frame;
|
||||
CefRefPtr<CefRequestImpl> requestPtr;
|
||||
|
||||
// Give the browser handler a chance first.
|
||||
if (browser) {
|
||||
// A frame should always exist, or be created.
|
||||
frame = browser->GetFrameForRequest(request);
|
||||
frame = GetFrameForRequest(browser->browser_info(), request);
|
||||
DCHECK(frame);
|
||||
|
||||
CefRefPtr<CefClient> client = browser->GetClient();
|
||||
|
Reference in New Issue
Block a user