Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "base/file_util.h" | 5 #include "base/file_util.h" |
| 6 #include "base/json/json_reader.h" | |
| 6 #include "base/memory/ref_counted.h" | 7 #include "base/memory/ref_counted.h" |
| 7 #include "base/path_service.h" | 8 #include "base/path_service.h" |
| 8 #include "base/utf_string_conversions.h" | 9 #include "base/utf_string_conversions.h" |
| 10 #include "content/common/renderer_constants.h" | |
| 9 #include "content/browser/renderer_host/render_view_host_impl.h" | 11 #include "content/browser/renderer_host/render_view_host_impl.h" |
| 10 #include "content/browser/site_instance_impl.h" | 12 #include "content/browser/site_instance_impl.h" |
| 11 #include "content/browser/web_contents/web_contents_impl.h" | 13 #include "content/browser/web_contents/web_contents_impl.h" |
| 12 #include "content/public/browser/navigation_controller.h" | 14 #include "content/public/browser/navigation_controller.h" |
| 13 #include "content/public/browser/navigation_entry.h" | 15 #include "content/public/browser/navigation_entry.h" |
| 14 #include "content/public/browser/notification_details.h" | 16 #include "content/public/browser/notification_details.h" |
| 15 #include "content/public/browser/notification_observer.h" | 17 #include "content/public/browser/notification_observer.h" |
| 16 #include "content/public/browser/notification_registrar.h" | 18 #include "content/public/browser/notification_registrar.h" |
| 17 #include "content/public/browser/notification_types.h" | 19 #include "content/public/browser/notification_types.h" |
| 18 #include "content/public/browser/render_process_host.h" | 20 #include "content/public/browser/render_process_host.h" |
| 19 #include "content/public/browser/render_view_host_observer.h" | 21 #include "content/public/browser/render_view_host_observer.h" |
| 20 #include "content/public/browser/web_contents.h" | 22 #include "content/public/browser/web_contents.h" |
| 21 #include "content/public/common/url_constants.h" | 23 #include "content/public/common/url_constants.h" |
| 22 #include "content/public/test/browser_test_utils.h" | 24 #include "content/public/test/browser_test_utils.h" |
| 23 #include "content/public/test/test_utils.h" | 25 #include "content/public/test/test_utils.h" |
| 24 #include "content/shell/shell.h" | 26 #include "content/shell/shell.h" |
| 25 #include "content/test/content_browser_test.h" | 27 #include "content/test/content_browser_test.h" |
| 26 #include "content/test/content_browser_test_utils.h" | 28 #include "content/test/content_browser_test_utils.h" |
| 27 #include "net/base/net_util.h" | 29 #include "net/base/net_util.h" |
| 28 #include "net/test/test_server.h" | 30 #include "net/test/test_server.h" |
| 29 | 31 |
| 32 namespace { | |
| 33 | |
| 34 bool CompareTrees(base::DictionaryValue* first, base::DictionaryValue* second) { | |
| 35 string16 name1; | |
| 36 string16 name2; | |
| 37 if (!first->GetString(content::kFrameTreeNodeNameKey, &name1) || | |
| 38 !second->GetString(content::kFrameTreeNodeNameKey, &name2)) | |
| 39 return false; | |
|
Charlie Reis
2012/08/22 22:08:34
Should this be return false, or a failed EXPECT?
nasko
2012/08/23 21:55:53
No. The semantics of this function is just to retu
Charlie Reis
2012/08/24 23:26:07
I just meant that we always expect the GetString (
| |
| 40 if (name1 != name2) | |
| 41 return false; | |
| 42 | |
| 43 int id1 = 0; | |
| 44 int id2 = 0; | |
| 45 if (!first->GetInteger(content::kFrameTreeNodeIdKey, &id1) || | |
| 46 !second->GetInteger(content::kFrameTreeNodeIdKey, &id2)) | |
| 47 return false; | |
| 48 if (id1 != id2) | |
| 49 return false; | |
| 50 | |
| 51 ListValue* subtree1 = NULL; | |
| 52 ListValue* subtree2 = NULL; | |
| 53 bool result1 = first->GetList(content::kFrameTreeNodeSubtreeKey, &subtree1); | |
| 54 bool result2 = second->GetList(content::kFrameTreeNodeSubtreeKey, &subtree2); | |
| 55 if (!result1 && !result2) | |
| 56 return true; | |
| 57 if (!result1 || !result2) | |
| 58 return false; | |
| 59 | |
| 60 if (subtree1->GetSize() != subtree2->GetSize()) | |
| 61 return false; | |
| 62 | |
| 63 base::DictionaryValue* child1 = NULL; | |
| 64 base::DictionaryValue* child2 = NULL; | |
| 65 for (size_t i = 0; i < subtree1->GetSize(); ++i) { | |
| 66 if (!subtree1->GetDictionary(i, &child1) || | |
| 67 !subtree2->GetDictionary(i, &child2)) | |
|
Charlie Reis
2012/08/22 22:08:34
nit: Needs braces, since condition doesn't fit on
nasko
2012/08/23 21:55:53
Done.
| |
| 68 return false; | |
| 69 if (!CompareTrees(child1, child2)) | |
| 70 return false; | |
| 71 } | |
| 72 | |
| 73 return true; | |
| 74 } | |
| 75 | |
| 76 base::DictionaryValue* GetTree(content::RenderViewHostImpl* rvh) { | |
| 77 std::string frame_tree = rvh->frame_tree(); | |
| 78 EXPECT_FALSE(frame_tree.empty()); | |
| 79 base::Value* v = base::JSONReader::Read(frame_tree); | |
| 80 base::DictionaryValue* tree = NULL; | |
| 81 EXPECT_TRUE(v->IsType(base::Value::TYPE_DICTIONARY)); | |
| 82 EXPECT_TRUE(v->GetAsDictionary(&tree)); | |
| 83 return tree; | |
| 84 } | |
| 85 | |
| 86 } // namespace | |
| 87 | |
| 30 namespace content { | 88 namespace content { |
| 31 | 89 |
| 32 class RenderViewHostManagerTest : public ContentBrowserTest { | 90 class RenderViewHostManagerTest : public ContentBrowserTest { |
| 33 public: | 91 public: |
| 34 RenderViewHostManagerTest() {} | 92 RenderViewHostManagerTest() {} |
| 35 | 93 |
| 36 static bool GetFilePathWithHostAndPortReplacement( | 94 static bool GetFilePathWithHostAndPortReplacement( |
| 37 const std::string& original_file_path, | 95 const std::string& original_file_path, |
| 38 const net::HostPortPair& host_port_pair, | 96 const net::HostPortPair& host_port_pair, |
| 39 std::string* replacement_path) { | 97 std::string* replacement_path) { |
| (...skipping 354 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 394 EXPECT_TRUE(success); | 452 EXPECT_TRUE(success); |
| 395 close_observer.Wait(); | 453 close_observer.Wait(); |
| 396 } | 454 } |
| 397 | 455 |
| 398 // Test for crbug.com/99202. PostMessage calls should still work after | 456 // Test for crbug.com/99202. PostMessage calls should still work after |
| 399 // navigating the source and target windows to different sites. | 457 // navigating the source and target windows to different sites. |
| 400 // Specifically: | 458 // Specifically: |
| 401 // 1) Create 3 windows (opener, "foo", and _blank) and send "foo" cross-process. | 459 // 1) Create 3 windows (opener, "foo", and _blank) and send "foo" cross-process. |
| 402 // 2) Fail to post a message from "foo" to opener with the wrong target origin. | 460 // 2) Fail to post a message from "foo" to opener with the wrong target origin. |
| 403 // 3) Post a message from "foo" to opener, which replies back to "foo". | 461 // 3) Post a message from "foo" to opener, which replies back to "foo". |
| 404 // 4) Post a message from _blank to "foo". | 462 // 4) Post a message from _blank to "foo". |
|
Charlie Reis
2012/08/22 22:08:34
Please briefly describe steps 5 and 6 as well.
nasko
2012/08/23 21:55:53
Done.
| |
| 405 IN_PROC_BROWSER_TEST_F(RenderViewHostManagerTest, | 463 IN_PROC_BROWSER_TEST_F(RenderViewHostManagerTest, |
| 406 SupportCrossProcessPostMessage) { | 464 SupportCrossProcessPostMessage) { |
| 407 // Start two servers with different sites. | 465 // Start two servers with different sites. |
| 408 ASSERT_TRUE(test_server()->Start()); | 466 ASSERT_TRUE(test_server()->Start()); |
| 409 net::TestServer https_server( | 467 net::TestServer https_server( |
| 410 net::TestServer::TYPE_HTTPS, | 468 net::TestServer::TYPE_HTTPS, |
| 411 net::TestServer::kLocalhost, | 469 net::TestServer::kLocalhost, |
| 412 FilePath(FILE_PATH_LITERAL("content/test/data"))); | 470 FilePath(FILE_PATH_LITERAL("content/test/data"))); |
| 413 ASSERT_TRUE(https_server.Start()); | 471 ASSERT_TRUE(https_server.Start()); |
| 414 | 472 |
| (...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 479 | 537 |
| 480 // 2) Fail to post a message from the foo window to the opener if the target | 538 // 2) Fail to post a message from the foo window to the opener if the target |
| 481 // origin is wrong. We won't see an error, but we can check for the right | 539 // origin is wrong. We won't see an error, but we can check for the right |
| 482 // number of received messages below. | 540 // number of received messages below. |
| 483 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | 541 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( |
| 484 foo_contents->GetRenderViewHost(), L"", | 542 foo_contents->GetRenderViewHost(), L"", |
| 485 L"window.domAutomationController.send(postToOpener('msg'," | 543 L"window.domAutomationController.send(postToOpener('msg'," |
| 486 L"'http://google.com'));", | 544 L"'http://google.com'));", |
| 487 &success)); | 545 &success)); |
| 488 EXPECT_TRUE(success); | 546 EXPECT_TRUE(success); |
| 547 ASSERT_FALSE(opener_manager->GetSwappedOutRenderViewHost(orig_site_instance)); | |
| 489 | 548 |
| 490 // 3) Post a message from the foo window to the opener. The opener will | 549 // 3) Post a message from the foo window to the opener. The opener will |
| 491 // reply, causing the foo window to update its own title. | 550 // reply, causing the foo window to update its own title. |
| 492 WindowedNotificationObserver title_observer( | 551 WindowedNotificationObserver title_observer( |
| 493 NOTIFICATION_WEB_CONTENTS_TITLE_UPDATED, | 552 NOTIFICATION_WEB_CONTENTS_TITLE_UPDATED, |
| 494 Source<WebContents>(foo_contents)); | 553 Source<WebContents>(foo_contents)); |
| 495 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | 554 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( |
| 496 foo_contents->GetRenderViewHost(), L"", | 555 foo_contents->GetRenderViewHost(), L"", |
| 497 L"window.domAutomationController.send(postToOpener('msg','*'));", | 556 L"window.domAutomationController.send(postToOpener('msg','*'));", |
| 498 &success)); | 557 &success)); |
| 499 EXPECT_TRUE(success); | 558 EXPECT_TRUE(success); |
| 559 ASSERT_FALSE(opener_manager->GetSwappedOutRenderViewHost(orig_site_instance)); | |
| 500 title_observer.Wait(); | 560 title_observer.Wait(); |
| 501 | 561 |
| 502 // We should have received only 1 message in the opener and "foo" tabs, | 562 // We should have received only 1 message in the opener and "foo" tabs, |
| 503 // and updated the title. | 563 // and updated the title. |
| 504 int opener_received_messages = 0; | 564 int opener_received_messages = 0; |
| 505 EXPECT_TRUE(ExecuteJavaScriptAndExtractInt( | 565 EXPECT_TRUE(ExecuteJavaScriptAndExtractInt( |
| 506 opener_contents->GetRenderViewHost(), L"", | 566 opener_contents->GetRenderViewHost(), L"", |
| 507 L"window.domAutomationController.send(window.receivedMessages);", | 567 L"window.domAutomationController.send(window.receivedMessages);", |
| 508 &opener_received_messages)); | 568 &opener_received_messages)); |
| 509 int foo_received_messages = 0; | 569 int foo_received_messages = 0; |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 524 new_contents->GetRenderViewHost(), L"", | 584 new_contents->GetRenderViewHost(), L"", |
| 525 L"window.domAutomationController.send(postToFoo('msg2'));", | 585 L"window.domAutomationController.send(postToFoo('msg2'));", |
| 526 &success)); | 586 &success)); |
| 527 EXPECT_TRUE(success); | 587 EXPECT_TRUE(success); |
| 528 title_observer2.Wait(); | 588 title_observer2.Wait(); |
| 529 EXPECT_EQ(ASCIIToUTF16("msg2"), foo_contents->GetTitle()); | 589 EXPECT_EQ(ASCIIToUTF16("msg2"), foo_contents->GetTitle()); |
| 530 | 590 |
| 531 // This postMessage should have created a swapped out RVH for the new | 591 // This postMessage should have created a swapped out RVH for the new |
| 532 // SiteInstance in the target=_blank window. | 592 // SiteInstance in the target=_blank window. |
| 533 EXPECT_TRUE(new_manager->GetSwappedOutRenderViewHost(foo_site_instance)); | 593 EXPECT_TRUE(new_manager->GetSwappedOutRenderViewHost(foo_site_instance)); |
| 594 | |
| 595 NavigateToURL(new_shell, https_server.GetURL("files/post_message2.html")); | |
| 596 | |
| 597 // 5) Now verify that posting a message from the foo window to a subframe of | |
| 598 // the opener window works fine. The opener subframe will reply, causing the | |
| 599 // foo window to update its own title. | |
| 600 WindowedNotificationObserver title_observer3( | |
| 601 NOTIFICATION_WEB_CONTENTS_TITLE_UPDATED, | |
| 602 Source<WebContents>(new_shell->web_contents())); | |
| 603 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 604 foo_contents->GetRenderViewHost(), L"", | |
| 605 L"window.domAutomationController.send(postToOpenerFrame('msg3','*'));", | |
| 606 &success)); | |
| 607 EXPECT_TRUE(success); | |
| 608 title_observer3.Wait(); | |
| 609 EXPECT_EQ(ASCIIToUTF16("msg3"), new_shell->web_contents()->GetTitle()); | |
| 610 | |
| 611 // 5) Lastly, verify that the _blank window can post a message to subframe | |
|
Charlie Reis
2012/08/22 22:08:34
nit: This should be 6. Also, "to a subframe"
nasko
2012/08/23 21:55:53
Done.
| |
| 612 // of the foo window. The subframe of foo will set the foo window title and | |
| 613 // will reply, setting the _blank window title. | |
| 614 WindowedNotificationObserver title_observer4( | |
| 615 NOTIFICATION_WEB_CONTENTS_TITLE_UPDATED, | |
| 616 Source<WebContents>(new_shell2->web_contents())); | |
| 617 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 618 new_contents->GetRenderViewHost(), L"", | |
| 619 L"window.domAutomationController.send(postToFooFrame('msg4'));", | |
| 620 &success)); | |
| 621 EXPECT_TRUE(success); | |
| 622 title_observer4.Wait(); | |
| 623 EXPECT_EQ(ASCIIToUTF16("msg4"), new_shell2->web_contents()->GetTitle()); | |
| 534 } | 624 } |
| 535 | 625 |
| 536 // Test for crbug.com/116192. Navigations to a window's opener should | 626 // Test for crbug.com/116192. Navigations to a window's opener should |
| 537 // still work after a process swap. | 627 // still work after a process swap. |
| 538 IN_PROC_BROWSER_TEST_F(RenderViewHostManagerTest, | 628 IN_PROC_BROWSER_TEST_F(RenderViewHostManagerTest, |
| 539 AllowTargetedNavigationsInOpenerAfterSwap) { | 629 AllowTargetedNavigationsInOpenerAfterSwap) { |
| 540 // Start two servers with different sites. | 630 // Start two servers with different sites. |
| 541 ASSERT_TRUE(test_server()->Start()); | 631 ASSERT_TRUE(test_server()->Start()); |
| 542 net::TestServer https_server( | 632 net::TestServer https_server( |
| 543 net::TestServer::TYPE_HTTPS, | 633 net::TestServer::TYPE_HTTPS, |
| (...skipping 488 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1032 rvh_observers.AddObserverToRVH(shell()->web_contents()->GetRenderViewHost()); | 1122 rvh_observers.AddObserverToRVH(shell()->web_contents()->GetRenderViewHost()); |
| 1033 | 1123 |
| 1034 // This used to leak a render view host. | 1124 // This used to leak a render view host. |
| 1035 shell()->Close(); | 1125 shell()->Close(); |
| 1036 | 1126 |
| 1037 RunAllPendingInMessageLoop(); // Needed on ChromeOS. | 1127 RunAllPendingInMessageLoop(); // Needed on ChromeOS. |
| 1038 | 1128 |
| 1039 EXPECT_EQ(0U, rvh_observers.GetNumObservers()); | 1129 EXPECT_EQ(0U, rvh_observers.GetNumObservers()); |
| 1040 } | 1130 } |
| 1041 | 1131 |
| 1132 // Test for correct propagation of frames hierarchy across processes in the | |
|
Charlie Reis
2012/08/22 22:08:34
nit: frames -> the frame
nasko
2012/08/23 21:55:53
Done.
| |
| 1133 // same browsing context. The test starts by navigating to a page that has | |
|
Charlie Reis
2012/08/22 22:08:34
nit: browsing context -> BrowsingInstance
nasko
2012/08/23 21:55:53
Done.
| |
| 1134 // multiple nested frames. It then opens two windows and navigates each one | |
| 1135 // to a separate site, so at the end we have 3 site instances. It checks | |
|
Charlie Reis
2012/08/22 22:08:34
nit: site instances -> SiteInstances.
nasko
2012/08/23 21:55:53
Done.
| |
| 1136 // that frame trees are kept in sync through navigations, reloading, and | |
| 1137 // JavaScript manipulation of the frame tree. | |
| 1138 IN_PROC_BROWSER_TEST_F(RenderViewHostManagerTest, FrameTreeUpdates) { | |
| 1139 // Start two servers to allow using different sites. | |
| 1140 EXPECT_TRUE(test_server()->Start()); | |
| 1141 net::TestServer https_server( | |
| 1142 net::TestServer::TYPE_HTTPS, | |
| 1143 net::TestServer::kLocalhost, | |
| 1144 FilePath(FILE_PATH_LITERAL("content/test/data"))); | |
| 1145 EXPECT_TRUE(https_server.Start()); | |
| 1146 | |
| 1147 GURL frame_tree_url(test_server()->GetURL("files/frame_tree/top.html")); | |
| 1148 | |
| 1149 // Replace the 127.0.0.1 with localhost, which will give us a different | |
| 1150 // site instance. | |
| 1151 GURL::Replacements replacements; | |
| 1152 std::string new_host("localhost"); | |
| 1153 replacements.SetHostStr(new_host); | |
| 1154 GURL remote_frame = test_server()->GetURL( | |
| 1155 "files/frame_tree/1-1.html").ReplaceComponents(replacements); | |
| 1156 | |
| 1157 bool success = false; | |
| 1158 base::DictionaryValue* frames = NULL; | |
| 1159 base::ListValue* subtree = NULL; | |
| 1160 | |
| 1161 NavigateToURL(shell(), test_server()->GetURL("files/simple_page.html")); | |
| 1162 WebContents* opener_contents = shell()->web_contents(); | |
| 1163 RenderViewHostManager* opener_rvhm = static_cast<WebContentsImpl*>( | |
| 1164 opener_contents)->GetRenderManagerForTesting(); | |
| 1165 frames = GetTree(opener_rvhm->current_host()); | |
| 1166 EXPECT_FALSE(frames->GetList(content::kFrameTreeNodeSubtreeKey, &subtree)); | |
| 1167 | |
| 1168 NavigateToURL(shell(), frame_tree_url); | |
| 1169 frames = GetTree(opener_rvhm->current_host()); | |
| 1170 EXPECT_TRUE(frames->GetList(content::kFrameTreeNodeSubtreeKey, &subtree)); | |
| 1171 EXPECT_TRUE(subtree->GetSize() == 3); | |
| 1172 | |
| 1173 scoped_refptr<SiteInstance> orig_site_instance( | |
| 1174 opener_contents->GetSiteInstance()); | |
| 1175 EXPECT_TRUE(orig_site_instance != NULL); | |
| 1176 | |
| 1177 ShellAddedObserver shell_observer1; | |
| 1178 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 1179 opener_contents->GetRenderViewHost(), L"", | |
| 1180 L"window.domAutomationController.send(openWindow('1-3.html'));", | |
| 1181 &success)); | |
| 1182 EXPECT_TRUE(success); | |
| 1183 | |
| 1184 Shell* shell1 = shell_observer1.GetShell(); | |
| 1185 WebContents* contents1 = shell1->web_contents(); | |
| 1186 WaitForLoadStop(contents1); | |
| 1187 RenderViewHostManager* rvhm1 = static_cast<WebContentsImpl*>( | |
| 1188 contents1)->GetRenderManagerForTesting(); | |
| 1189 EXPECT_EQ("/files/frame_tree/1-3.html", contents1->GetURL().path()); | |
| 1190 | |
| 1191 NavigateToURL(shell1, https_server.GetURL("files/title1.html")); | |
| 1192 EXPECT_EQ("/files/title1.html", contents1->GetURL().path()); | |
| 1193 scoped_refptr<SiteInstance> site_instance1( | |
| 1194 contents1->GetSiteInstance()); | |
| 1195 EXPECT_NE(orig_site_instance, site_instance1); | |
| 1196 | |
| 1197 ShellAddedObserver shell_observer2; | |
| 1198 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 1199 opener_contents->GetRenderViewHost(), L"", | |
| 1200 L"window.domAutomationController.send(openWindow('../title2.html'));", | |
| 1201 &success)); | |
| 1202 EXPECT_TRUE(success); | |
| 1203 | |
| 1204 Shell* shell2 = shell_observer2.GetShell(); | |
| 1205 WebContents* contents2 = shell2->web_contents(); | |
| 1206 WaitForLoadStop(contents2); | |
| 1207 EXPECT_EQ("/files/title2.html", contents2->GetURL().path()); | |
| 1208 | |
| 1209 NavigateToURL(shell2, remote_frame); | |
| 1210 EXPECT_EQ("/files/frame_tree/1-1.html", contents2->GetURL().path()); | |
| 1211 scoped_refptr<SiteInstance> site_instance2( | |
| 1212 contents2->GetSiteInstance()); | |
| 1213 EXPECT_NE(orig_site_instance, site_instance2); | |
| 1214 EXPECT_NE(site_instance1, site_instance2); | |
| 1215 | |
| 1216 RenderViewHostManager* rvhm2 = static_cast<WebContentsImpl*>( | |
| 1217 contents2)->GetRenderManagerForTesting(); | |
| 1218 | |
| 1219 EXPECT_TRUE(CompareTrees( | |
| 1220 GetTree(opener_rvhm->current_host()), | |
| 1221 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1222 rvhm1->current_host()->GetSiteInstance())))); | |
|
Charlie Reis
2012/08/22 22:08:34
Maybe grab a reference to this SiteInstance to mak
nasko
2012/08/23 21:55:53
Done.
| |
| 1223 EXPECT_TRUE(CompareTrees( | |
| 1224 GetTree(opener_rvhm->current_host()), | |
| 1225 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1226 rvhm2->current_host()->GetSiteInstance())))); | |
| 1227 | |
| 1228 EXPECT_TRUE(CompareTrees( | |
| 1229 GetTree(rvhm1->current_host()), | |
| 1230 GetTree(rvhm1->GetSwappedOutRenderViewHost( | |
| 1231 opener_rvhm->current_host()->GetSiteInstance())))); | |
| 1232 EXPECT_TRUE(CompareTrees( | |
| 1233 GetTree(rvhm2->current_host()), | |
| 1234 GetTree(rvhm2->GetSwappedOutRenderViewHost( | |
| 1235 opener_rvhm->current_host()->GetSiteInstance())))); | |
| 1236 | |
| 1237 EXPECT_FALSE(CompareTrees( | |
| 1238 GetTree(opener_rvhm->current_host()), GetTree(rvhm1->current_host()))); | |
| 1239 EXPECT_FALSE(CompareTrees( | |
| 1240 GetTree(opener_rvhm->current_host()), GetTree(rvhm2->current_host()))); | |
| 1241 | |
| 1242 // Reload the original page, which will cause subframe ids to change. This | |
| 1243 // will ensure that the ids are properly replicated across reload. | |
| 1244 NavigateToURL(shell(), frame_tree_url); | |
| 1245 | |
| 1246 EXPECT_TRUE(CompareTrees( | |
| 1247 GetTree(opener_rvhm->current_host()), | |
| 1248 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1249 rvhm1->current_host()->GetSiteInstance())))); | |
| 1250 EXPECT_TRUE(CompareTrees( | |
| 1251 GetTree(opener_rvhm->current_host()), | |
| 1252 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1253 rvhm2->current_host()->GetSiteInstance())))); | |
| 1254 | |
| 1255 EXPECT_FALSE(CompareTrees( | |
| 1256 GetTree(opener_rvhm->current_host()), GetTree(rvhm1->current_host()))); | |
| 1257 EXPECT_FALSE(CompareTrees( | |
| 1258 GetTree(opener_rvhm->current_host()), GetTree(rvhm2->current_host()))); | |
| 1259 | |
| 1260 // Now let's ensure that using JS to add/remove frames results in proper | |
| 1261 // updates. | |
| 1262 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 1263 opener_contents->GetRenderViewHost(), L"", | |
| 1264 L"window.domAutomationController.send(removeFrame());", | |
| 1265 &success)); | |
| 1266 EXPECT_TRUE(success); | |
| 1267 frames = GetTree(opener_rvhm->current_host()); | |
| 1268 EXPECT_TRUE(frames->GetList(content::kFrameTreeNodeSubtreeKey, &subtree)); | |
| 1269 EXPECT_TRUE(subtree->GetSize() == 2); | |
| 1270 | |
| 1271 WindowedNotificationObserver title_observer( | |
| 1272 NOTIFICATION_WEB_CONTENTS_TITLE_UPDATED, | |
| 1273 Source<WebContents>(opener_contents)); | |
| 1274 EXPECT_TRUE(ExecuteJavaScriptAndExtractBool( | |
| 1275 opener_contents->GetRenderViewHost(), L"", | |
| 1276 L"window.domAutomationController.send(addFrame());", | |
| 1277 &success)); | |
| 1278 EXPECT_TRUE(success); | |
| 1279 title_observer.Wait(); | |
| 1280 | |
| 1281 frames = GetTree(opener_rvhm->current_host()); | |
| 1282 EXPECT_TRUE(frames->GetList(content::kFrameTreeNodeSubtreeKey, &subtree)); | |
| 1283 EXPECT_TRUE(subtree->GetSize() == 3); | |
| 1284 | |
| 1285 EXPECT_TRUE(CompareTrees( | |
| 1286 GetTree(opener_rvhm->current_host()), | |
| 1287 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1288 rvhm1->current_host()->GetSiteInstance())))); | |
| 1289 EXPECT_TRUE(CompareTrees( | |
| 1290 GetTree(opener_rvhm->current_host()), | |
| 1291 GetTree(opener_rvhm->GetSwappedOutRenderViewHost( | |
| 1292 rvhm2->current_host()->GetSiteInstance())))); | |
| 1293 } | |
| 1294 | |
| 1042 } // namespace content | 1295 } // namespace content |
| OLD | NEW |