browser_browsingContext-embedder.js (4958B)
1 "use strict"; 2 3 function observeOnce(topic) { 4 return new Promise(resolve => { 5 Services.obs.addObserver(function observer(aSubject, aTopic) { 6 if (topic == aTopic) { 7 Services.obs.removeObserver(observer, topic); 8 setTimeout(() => resolve(aSubject), 0); 9 } 10 }, topic); 11 }); 12 } 13 14 add_task(async function runTest() { 15 let fissionWindow = await BrowserTestUtils.openNewBrowserWindow({ 16 fission: true, 17 remote: true, 18 }); 19 20 info(`chrome, parent`); 21 let chromeBC = fissionWindow.docShell.browsingContext; 22 ok(chromeBC.currentWindowGlobal, "Should have a current WindowGlobal"); 23 is(chromeBC.embedderWindowGlobal, null, "chrome has no embedder global"); 24 is(chromeBC.embedderElement, null, "chrome has no embedder element"); 25 is(chromeBC.parent, null, "chrome has no parent"); 26 27 // Open a new tab, and check that basic frames work out. 28 let tab = await BrowserTestUtils.openNewForegroundTab({ 29 gBrowser: fissionWindow.gBrowser, 30 }); 31 32 info(`root, parent`); 33 let rootBC = tab.linkedBrowser.browsingContext; 34 ok(rootBC.currentWindowGlobal, "[parent] root has a window global"); 35 is( 36 rootBC.embedderWindowGlobal, 37 chromeBC.currentWindowGlobal, 38 "[parent] root has chrome as embedder global" 39 ); 40 is( 41 rootBC.embedderElement, 42 tab.linkedBrowser, 43 "[parent] root has browser as embedder element" 44 ); 45 is(rootBC.parent, null, "[parent] root has no parent"); 46 47 // Test with an in-process frame 48 let frameId = await SpecialPowers.spawn(tab.linkedBrowser, [], async () => { 49 info(`root, child`); 50 let rootBC = content.docShell.browsingContext; 51 is(rootBC.embedderElement, null, "[child] root has no embedder"); 52 is(rootBC.parent, null, "[child] root has no parent"); 53 54 info(`frame, child`); 55 let iframe = content.document.createElement("iframe"); 56 content.document.body.appendChild(iframe); 57 58 let frameBC = iframe.contentWindow.docShell.browsingContext; 59 is(frameBC.embedderElement, iframe, "[child] frame embedded within iframe"); 60 is(frameBC.parent, rootBC, "[child] frame has root as parent"); 61 62 return frameBC.id; 63 }); 64 65 info(`frame, parent`); 66 let frameBC = BrowsingContext.get(frameId); 67 ok(frameBC.currentWindowGlobal, "[parent] frame has a window global"); 68 is( 69 frameBC.embedderWindowGlobal, 70 rootBC.currentWindowGlobal, 71 "[parent] frame has root as embedder global" 72 ); 73 is(frameBC.embedderElement, null, "[parent] frame has no embedder element"); 74 is(frameBC.parent, rootBC, "[parent] frame has root as parent"); 75 76 // Test with an out-of-process iframe. 77 78 let oopID = await SpecialPowers.spawn(tab.linkedBrowser, [], async () => { 79 info(`creating oop iframe`); 80 let oop = content.document.createElement("iframe"); 81 oop.setAttribute("src", "https://example.com"); 82 content.document.body.appendChild(oop); 83 84 await new Promise(resolve => { 85 oop.addEventListener("load", resolve, { once: true }); 86 }); 87 88 info(`oop frame, child`); 89 let oopBC = oop.frameLoader.browsingContext; 90 is(oopBC.embedderElement, oop, "[child] oop frame embedded within iframe"); 91 is( 92 oopBC.parent, 93 content.docShell.browsingContext, 94 "[child] frame has root as parent" 95 ); 96 97 return oopBC.id; 98 }); 99 100 info(`oop frame, parent`); 101 let oopBC = BrowsingContext.get(oopID); 102 is( 103 oopBC.embedderWindowGlobal, 104 rootBC.currentWindowGlobal, 105 "[parent] oop frame has root as embedder global" 106 ); 107 is(oopBC.embedderElement, null, "[parent] oop frame has no embedder element"); 108 is(oopBC.parent, rootBC, "[parent] oop frame has root as parent"); 109 110 info(`waiting for oop window global`); 111 ok(oopBC.currentWindowGlobal, "[parent] oop frame has a window global"); 112 113 // Open a new window, and adopt |tab| into it. 114 115 let newWindow = await BrowserTestUtils.openNewBrowserWindow({ 116 fission: true, 117 remote: true, 118 }); 119 120 info(`new chrome, parent`); 121 let newChromeBC = newWindow.docShell.browsingContext; 122 ok(newChromeBC.currentWindowGlobal, "Should have a current WindowGlobal"); 123 is( 124 newChromeBC.embedderWindowGlobal, 125 null, 126 "new chrome has no embedder global" 127 ); 128 is(newChromeBC.embedderElement, null, "new chrome has no embedder element"); 129 is(newChromeBC.parent, null, "new chrome has no parent"); 130 131 isnot(newChromeBC, chromeBC, "different chrome browsing context"); 132 133 info(`adopting tab`); 134 let newTab = newWindow.gBrowser.adoptTab(tab); 135 136 is( 137 newTab.linkedBrowser.browsingContext, 138 rootBC, 139 "[parent] root browsing context survived" 140 ); 141 is( 142 rootBC.embedderWindowGlobal, 143 newChromeBC.currentWindowGlobal, 144 "[parent] embedder window global updated" 145 ); 146 is( 147 rootBC.embedderElement, 148 newTab.linkedBrowser, 149 "[parent] embedder element updated" 150 ); 151 is(rootBC.parent, null, "[parent] root has no parent"); 152 153 info(`closing window`); 154 await BrowserTestUtils.closeWindow(newWindow); 155 await BrowserTestUtils.closeWindow(fissionWindow); 156 });