Commit 4ebb4ef1 authored by Dmitry Gozman's avatar Dmitry Gozman Committed by Commit Bot

DevTools Protocol: expose frame detached reason

When Page.frameDetached arrives before Target.attachedToTarget
during local->remote frame swap, it is essential to know that
detach will actually lead to a swap, to not lose the frame
during transition period.

Bug: 1148088
Change-Id: I16ccfc10e268b7017eafc3ea2da4a4e4ea5c4f50
Reviewed-on: https://chromium-review.googlesource.com/c/chromium/src/+/2532770
Commit-Queue: Dmitry Gozman <dgozman@chromium.org>
Reviewed-by: default avatarAndrey Kosyakov <caseq@chromium.org>
Cr-Commit-Position: refs/heads/master@{#826630}
parent 61b7f11d
......@@ -6768,6 +6768,12 @@ domain Page
parameters
# Id of the frame that has been detached.
FrameId frameId
experimental enum reason
# The frame is removed from the DOM.
remove
# The frame is being swapped out in favor of an out-of-process iframe.
# A new frame target will be created (see Target.attachedToTarget).
swap
# Fired once navigation of the frame has completed. Frame is now associated with the new loader.
event frameNavigated
......
......@@ -662,7 +662,7 @@ void LocalFrame::DetachImpl(FrameDetachType type) {
GetEventHandlerRegistry().DidRemoveAllEventHandlers(*DomWindow());
probe::FrameDetachedFromParent(this);
probe::FrameDetachedFromParent(this, type);
supplements_.clear();
frame_scheduler_.reset();
......
......@@ -138,6 +138,16 @@ String NavigationPolicyToProtocol(NavigationPolicy policy) {
return DispositionEnum::CurrentTab;
}
String FrameDetachTypeToProtocol(FrameDetachType type) {
namespace ReasonEnum = protocol::Page::FrameDetached::ReasonEnum;
switch (type) {
case FrameDetachType::kRemove:
return ReasonEnum::Remove;
case FrameDetachType::kSwap:
return ReasonEnum::Swap;
}
}
Resource* CachedResource(LocalFrame* frame,
const KURL& url,
InspectorResourceContentLoader* loader) {
......@@ -951,8 +961,10 @@ void InspectorPageAgent::FrameAttachedToParent(LocalFrame* frame) {
GetFrontend()->flush();
}
void InspectorPageAgent::FrameDetachedFromParent(LocalFrame* frame) {
GetFrontend()->frameDetached(IdentifiersFactory::FrameId(frame));
void InspectorPageAgent::FrameDetachedFromParent(LocalFrame* frame,
FrameDetachType type) {
GetFrontend()->frameDetached(IdentifiersFactory::FrameId(frame),
FrameDetachTypeToProtocol(type));
}
bool InspectorPageAgent::ScreencastEnabled() {
......
......@@ -176,7 +176,7 @@ class CORE_EXPORT InspectorPageAgent final
void LoadEventFired(LocalFrame*);
void WillCommitLoad(LocalFrame*, DocumentLoader*);
void FrameAttachedToParent(LocalFrame*);
void FrameDetachedFromParent(LocalFrame*);
void FrameDetachedFromParent(LocalFrame*, FrameDetachType);
void FrameStartedLoading(LocalFrame*);
void FrameStoppedLoading(LocalFrame*);
void FrameRequestedNavigation(Frame* target_frame,
......
......@@ -112,7 +112,7 @@ interface CoreProbes {
void DomContentLoadedEventFired([Keep] LocalFrame*);
void LoadEventFired([Keep] LocalFrame*);
void FrameAttachedToParent([Keep] LocalFrame*);
void FrameDetachedFromParent([Keep] LocalFrame*);
void FrameDetachedFromParent([Keep] LocalFrame*, FrameDetachType);
void DidStartProvisionalLoad([Keep] LocalFrame*);
void DidFailProvisionalLoad([Keep] LocalFrame*);
void WillCommitLoad([Keep] LocalFrame*, DocumentLoader*);
......
Tests frame lifetime events.
Attached
Started loading
Creating iframe "blank.html"
{
method : Page.frameAttached
params : <object>
sessionId : <string>
}
{
method : Page.frameStartedLoading
params : {
frameId : <string>
}
sessionId : <string>
}
RequestWillBeSent .../inspector-protocol/resources/blank.html
Navigated
Started loading
Navigated
Detached
{
method : Page.frameNavigated
params : <object>
sessionId : <string>
}
{
method : Page.frameStoppedLoading
params : {
frameId : <string>
}
sessionId : <string>
}
Navigating iframe to "about:blank"
{
method : Page.frameStartedLoading
params : {
frameId : <string>
}
sessionId : <string>
}
{
method : Page.frameNavigated
params : <object>
sessionId : <string>
}
Removing iframe
{
method : Page.frameDetached
params : {
frameId : <string>
reason : remove
}
sessionId : <string>
}
......@@ -6,25 +6,22 @@
dp.Network.onRequestWillBeSent(e => {
testRunner.log(`RequestWillBeSent ${testRunner.trimURL(e.params.request.url)}`);
});
testRunner.log('Creating iframe "blank.html"');
session.evaluate(`
window.frame = document.createElement('iframe');
frame.src = '${testRunner.url('../resources/blank.html')}';
document.body.appendChild(frame);
`);
await dp.Page.onceFrameAttached();
testRunner.log('Attached');
await dp.Page.onceFrameStartedLoading();
testRunner.log('Started loading');
await dp.Page.onceFrameNavigated();
testRunner.log('Navigated');
await dp.Page.onceFrameStoppedLoading();
testRunner.log(await dp.Page.onceFrameAttached(), '', ['params', 'sessionId']);
testRunner.log(await dp.Page.onceFrameStartedLoading());
testRunner.log(await dp.Page.onceFrameNavigated(), '', ['params', 'sessionId']);
testRunner.log(await dp.Page.onceFrameStoppedLoading());
testRunner.log('Navigating iframe to "about:blank"');
session.evaluate('frame.src = "about:blank"');
await dp.Page.onceFrameStartedLoading();
testRunner.log('Started loading');
await dp.Page.onceFrameNavigated();
testRunner.log('Navigated');
testRunner.log(await dp.Page.onceFrameStartedLoading());
testRunner.log(await dp.Page.onceFrameNavigated(), '', ['params', 'sessionId']);
testRunner.log('Removing iframe');
session.evaluate('document.body.removeChild(frame);');
await dp.Page.onceFrameDetached();
testRunner.log('Detached');
testRunner.log(await dp.Page.onceFrameDetached());
testRunner.completeTest();
})
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment