OLD | NEW |
---|---|
1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 "content/browser/frame_host/navigation_controller_impl.h" | 5 #include "content/browser/frame_host/navigation_controller_impl.h" |
6 | 6 |
7 #include <stdint.h> | 7 #include <stdint.h> |
8 #include <utility> | 8 #include <utility> |
9 | 9 |
10 #include "base/bind.h" | 10 #include "base/bind.h" |
(...skipping 3187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3198 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); | 3198 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); |
3199 | 3199 |
3200 // 3. Go back, recreating the iframe. | 3200 // 3. Go back, recreating the iframe. |
3201 { | 3201 { |
3202 TestNavigationObserver back_load_observer(shell()->web_contents()); | 3202 TestNavigationObserver back_load_observer(shell()->web_contents()); |
3203 controller.GoBack(); | 3203 controller.GoBack(); |
3204 back_load_observer.Wait(); | 3204 back_load_observer.Wait(); |
3205 } | 3205 } |
3206 ASSERT_EQ(1U, root->child_count()); | 3206 ASSERT_EQ(1U, root->child_count()); |
3207 EXPECT_EQ(main_url, root->current_url()); | 3207 EXPECT_EQ(main_url, root->current_url()); |
3208 | 3208 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); |
3209 // TODO(creis): The child's current_url should be about:blank, but we're not | |
3210 // currently getting a commit in this case. For now, we'll lack a commit for | |
3211 // this frame, similar to the slow URL case. See https://crbug.com/626416. | |
3212 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) | |
3213 EXPECT_TRUE(root->child_at(0)->current_url().is_empty()); | |
3214 else | |
3215 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); | |
3216 | 3209 |
3217 // Verify that the parent was able to script the iframe. | 3210 // Verify that the parent was able to script the iframe. |
3218 { | 3211 { |
3219 std::string value; | 3212 std::string value; |
3220 EXPECT_TRUE(ExecuteScriptAndExtractString( | 3213 EXPECT_TRUE(ExecuteScriptAndExtractString( |
3221 root->child_at(0), | 3214 root->child_at(0), |
3222 "domAutomationController.send(document.body.innerHTML)", &value)); | 3215 "domAutomationController.send(document.body.innerHTML)", &value)); |
3223 EXPECT_EQ(expected_text, value); | 3216 EXPECT_EQ(expected_text, value); |
3224 } | 3217 } |
3225 | 3218 |
3226 EXPECT_EQ(2, controller.GetEntryCount()); | 3219 EXPECT_EQ(2, controller.GetEntryCount()); |
3227 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); | 3220 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); |
3228 EXPECT_EQ(entry, controller.GetLastCommittedEntry()); | 3221 EXPECT_EQ(entry, controller.GetLastCommittedEntry()); |
3229 | 3222 |
3230 // The entry should have a FrameNavigationEntry for the blank subframe. | 3223 // The entry should have a FrameNavigationEntry for the blank subframe. |
3231 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | 3224 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { |
3232 ASSERT_EQ(1U, entry->root_node()->children.size()); | 3225 ASSERT_EQ(1U, entry->root_node()->children.size()); |
3233 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); | 3226 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); |
3234 } | 3227 } |
3235 } | 3228 } |
3236 | 3229 |
3230 // Verify that we correctly load nested iframes injected into a page if we go | |
3231 // back and recreate them. Also confirm that form values are not restored for | |
3232 // forms injected into about:blank pages. See https://crbug.com/657896. | |
3233 IN_PROC_BROWSER_TEST_F(NavigationControllerBrowserTest, | |
3234 FrameNavigationEntry_RecreatedInjectedBlankSubframe) { | |
3235 // 1. Start on a page that injects a nested iframe into an injected | |
3236 // about:blank iframe. | |
3237 GURL main_url(embedded_test_server()->GetURL( | |
3238 "/navigation_controller/inject_subframe_into_blank_iframe.html")); | |
3239 GURL blank_url(url::kAboutBlankURL); | |
3240 GURL inner_url( | |
3241 embedded_test_server()->GetURL("/navigation_controller/form.html")); | |
3242 EXPECT_TRUE(NavigateToURL(shell(), main_url)); | |
3243 NavigationControllerImpl& controller = static_cast<NavigationControllerImpl&>( | |
3244 shell()->web_contents()->GetController()); | |
3245 FrameTreeNode* root = static_cast<WebContentsImpl*>(shell()->web_contents()) | |
3246 ->GetFrameTree() | |
3247 ->root(); | |
3248 | |
3249 // Verify that the inner iframe was able to load. | |
3250 ASSERT_EQ(1U, root->child_count()); | |
3251 ASSERT_EQ(1U, root->child_at(0)->child_count()); | |
3252 ASSERT_EQ(0U, root->child_at(0)->child_at(0)->child_count()); | |
3253 EXPECT_EQ(main_url, root->current_url()); | |
3254 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); | |
3255 EXPECT_EQ(inner_url, root->child_at(0)->child_at(0)->current_url()); | |
3256 | |
3257 EXPECT_EQ(1, controller.GetEntryCount()); | |
3258 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); | |
3259 NavigationEntryImpl* entry = controller.GetLastCommittedEntry(); | |
3260 | |
3261 // The entry should have FrameNavigationEntries for the subframes. | |
3262 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | |
3263 ASSERT_EQ(1U, entry->root_node()->children.size()); | |
3264 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); | |
3265 EXPECT_EQ(inner_url, | |
3266 entry->root_node()->children[0]->children[0]->frame_entry->url()); | |
3267 } | |
3268 | |
3269 // Set a value in the form which will be stored in the PageState. | |
3270 EXPECT_TRUE( | |
3271 ExecuteScript(root->child_at(0)->child_at(0), | |
3272 "document.getElementById('itext').value = 'modified';")); | |
3273 | |
3274 // 2. Navigate the main frame same-site, destroying the subframes. | |
3275 GURL main_url_2(embedded_test_server()->GetURL( | |
3276 "/navigation_controller/simple_page_1.html")); | |
3277 EXPECT_TRUE(NavigateToURL(shell(), main_url_2)); | |
3278 ASSERT_EQ(0U, root->child_count()); | |
3279 EXPECT_EQ(main_url_2, root->current_url()); | |
3280 | |
3281 EXPECT_EQ(2, controller.GetEntryCount()); | |
3282 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); | |
3283 | |
3284 // 3. Go back, recreating the subframes. | |
3285 { | |
3286 TestNavigationObserver back_load_observer(shell()->web_contents()); | |
3287 controller.GoBack(); | |
3288 back_load_observer.Wait(); | |
3289 } | |
3290 ASSERT_EQ(1U, root->child_count()); | |
3291 EXPECT_EQ(main_url, root->current_url()); | |
3292 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); | |
3293 | |
3294 // Verify that the inner iframe went to the correct URL. | |
3295 EXPECT_EQ(inner_url, root->child_at(0)->child_at(0)->current_url()); | |
3296 | |
3297 EXPECT_EQ(2, controller.GetEntryCount()); | |
3298 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); | |
3299 EXPECT_EQ(entry, controller.GetLastCommittedEntry()); | |
3300 | |
3301 // The entry should have FrameNavigationEntries for the subframes. | |
3302 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | |
3303 ASSERT_EQ(1U, entry->root_node()->children.size()); | |
3304 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); | |
3305 EXPECT_EQ(inner_url, | |
3306 entry->root_node()->children[0]->children[0]->frame_entry->url()); | |
3307 } | |
3308 | |
3309 // With injected about:blank iframes, we never restore form values from | |
3310 // PageState. | |
3311 std::string form_value; | |
alexmos
2016/10/21 06:34:16
nit: maybe initialize to something other than ""?
Charlie Reis
2016/10/21 07:34:30
Done.
| |
3312 EXPECT_TRUE( | |
3313 ExecuteScriptAndExtractString(root->child_at(0)->child_at(0), | |
3314 "window.domAutomationController.send(" | |
3315 "document.getElementById('itext').value);", | |
3316 &form_value)); | |
3317 EXPECT_EQ("", form_value); | |
3318 } | |
3319 | |
3320 // Verify that we correctly load a nested iframe created by an injected iframe | |
3321 // srcdoc if we go back and recreate the frames. Also verify that form values | |
3322 // are correctly restored for forms within srcdoc frames, unlike forms injected | |
3323 // into about:blank pages (as tested in | |
3324 // FrameNavigationEntry_RecreatedInjectedBlankSubframe). | |
3325 // | |
3326 // This test worked before and after the fix for https://crbug.com/657896, but | |
3327 // it failed with a preliminary version of the fix. | |
3328 IN_PROC_BROWSER_TEST_F(NavigationControllerBrowserTest, | |
3329 FrameNavigationEntry_RecreatedInjectedSrcdocSubframe) { | |
3330 // 1. Start on a page that injects a nested iframe srcdoc which contains a | |
3331 // nested iframe. | |
3332 GURL main_url(embedded_test_server()->GetURL( | |
3333 "/navigation_controller/inject_iframe_srcdoc_with_nested_frame.html")); | |
3334 GURL blank_url(url::kAboutBlankURL); | |
3335 GURL inner_url( | |
3336 embedded_test_server()->GetURL("/navigation_controller/form.html")); | |
3337 EXPECT_TRUE(NavigateToURL(shell(), main_url)); | |
3338 NavigationControllerImpl& controller = static_cast<NavigationControllerImpl&>( | |
3339 shell()->web_contents()->GetController()); | |
3340 FrameTreeNode* root = static_cast<WebContentsImpl*>(shell()->web_contents()) | |
3341 ->GetFrameTree() | |
3342 ->root(); | |
3343 | |
3344 // Verify that the inner iframe was able to load. | |
3345 ASSERT_EQ(1U, root->child_count()); | |
3346 ASSERT_EQ(1U, root->child_at(0)->child_count()); | |
3347 ASSERT_EQ(0U, root->child_at(0)->child_at(0)->child_count()); | |
3348 EXPECT_EQ(main_url, root->current_url()); | |
3349 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); | |
3350 EXPECT_EQ(inner_url, root->child_at(0)->child_at(0)->current_url()); | |
3351 | |
3352 EXPECT_EQ(1, controller.GetEntryCount()); | |
3353 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); | |
3354 NavigationEntryImpl* entry = controller.GetLastCommittedEntry(); | |
3355 | |
3356 // The entry should have FrameNavigationEntries for the subframes. | |
3357 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | |
3358 ASSERT_EQ(1U, entry->root_node()->children.size()); | |
3359 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); | |
3360 EXPECT_EQ(inner_url, | |
3361 entry->root_node()->children[0]->children[0]->frame_entry->url()); | |
3362 } | |
3363 | |
3364 // Set a value in the form which will be stored in the PageState. | |
3365 EXPECT_TRUE( | |
3366 ExecuteScript(root->child_at(0)->child_at(0), | |
3367 "document.getElementById('itext').value = 'modified';")); | |
3368 | |
3369 // 2. Navigate the main frame same-site, destroying the subframes. | |
3370 GURL main_url_2(embedded_test_server()->GetURL( | |
3371 "/navigation_controller/simple_page_1.html")); | |
3372 EXPECT_TRUE(NavigateToURL(shell(), main_url_2)); | |
3373 ASSERT_EQ(0U, root->child_count()); | |
3374 EXPECT_EQ(main_url_2, root->current_url()); | |
3375 | |
3376 EXPECT_EQ(2, controller.GetEntryCount()); | |
3377 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); | |
3378 | |
3379 // 3. Go back, recreating the subframes. | |
3380 { | |
3381 TestNavigationObserver back_load_observer(shell()->web_contents()); | |
3382 controller.GoBack(); | |
3383 back_load_observer.Wait(); | |
3384 } | |
3385 ASSERT_EQ(1U, root->child_count()); | |
3386 // TODO(creis): This line is unexpectedly failing in PlzNavigate, so the test | |
3387 // is disabled there for now. | |
3388 ASSERT_EQ(1U, root->child_at(0)->child_count()); | |
Charlie Reis
2016/10/21 04:39:25
Not sure why this isn't working in PlzNavigate (ev
alexmos
2016/10/21 06:34:16
Acknowledged. I tried it out locally, and it seem
| |
3389 ASSERT_EQ(0U, root->child_at(0)->child_at(0)->child_count()); | |
3390 EXPECT_EQ(main_url, root->current_url()); | |
3391 EXPECT_EQ(blank_url, root->child_at(0)->current_url()); | |
3392 | |
3393 // Verify that the inner iframe went to the correct URL. | |
3394 EXPECT_EQ(inner_url, root->child_at(0)->child_at(0)->current_url()); | |
3395 | |
3396 EXPECT_EQ(2, controller.GetEntryCount()); | |
3397 EXPECT_EQ(0, controller.GetLastCommittedEntryIndex()); | |
3398 EXPECT_EQ(entry, controller.GetLastCommittedEntry()); | |
3399 | |
3400 // The entry should have FrameNavigationEntries for the subframes. | |
3401 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) { | |
3402 ASSERT_EQ(1U, entry->root_node()->children.size()); | |
3403 EXPECT_EQ(blank_url, entry->root_node()->children[0]->frame_entry->url()); | |
3404 EXPECT_EQ(inner_url, | |
3405 entry->root_node()->children[0]->children[0]->frame_entry->url()); | |
3406 } | |
3407 | |
3408 // With injected iframe srcdoc pages, we do restore form values from | |
3409 // PageState. | |
3410 std::string form_value; | |
3411 EXPECT_TRUE( | |
3412 ExecuteScriptAndExtractString(root->child_at(0)->child_at(0), | |
3413 "window.domAutomationController.send(" | |
3414 "document.getElementById('itext').value);", | |
3415 &form_value)); | |
3416 EXPECT_EQ("modified", form_value); | |
3417 } | |
3418 | |
3237 // Ensure we don't crash if an onload handler removes an about:blank frame after | 3419 // Ensure we don't crash if an onload handler removes an about:blank frame after |
3238 // recreating it on a back/forward. See https://crbug.com/638166. | 3420 // recreating it on a back/forward. See https://crbug.com/638166. |
3239 IN_PROC_BROWSER_TEST_F(NavigationControllerBrowserTest, | 3421 IN_PROC_BROWSER_TEST_F(NavigationControllerBrowserTest, |
3240 FrameNavigationEntry_RemoveRecreatedBlankSubframe) { | 3422 FrameNavigationEntry_RemoveRecreatedBlankSubframe) { |
3241 // 1. Start on a page that removes its about:blank iframe during onload. | 3423 // 1. Start on a page that removes its about:blank iframe during onload. |
3242 GURL main_url(embedded_test_server()->GetURL( | 3424 GURL main_url(embedded_test_server()->GetURL( |
3243 "/navigation_controller/remove_blank_iframe_on_load.html")); | 3425 "/navigation_controller/remove_blank_iframe_on_load.html")); |
3244 GURL blank_url(url::kAboutBlankURL); | 3426 GURL blank_url(url::kAboutBlankURL); |
3245 EXPECT_TRUE(NavigateToURL(shell(), main_url)); | 3427 EXPECT_TRUE(NavigateToURL(shell(), main_url)); |
3246 NavigationControllerImpl& controller = static_cast<NavigationControllerImpl&>( | 3428 NavigationControllerImpl& controller = static_cast<NavigationControllerImpl&>( |
(...skipping 2253 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5500 subframe_delayer.WaitForNavigationFinished(); | 5682 subframe_delayer.WaitForNavigationFinished(); |
5501 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); | 5683 EXPECT_EQ(1, controller.GetLastCommittedEntryIndex()); |
5502 EXPECT_EQ(url_a, root->current_url()); | 5684 EXPECT_EQ(url_a, root->current_url()); |
5503 EXPECT_EQ(frame_url_a2, root->child_at(0)->current_url()); | 5685 EXPECT_EQ(frame_url_a2, root->child_at(0)->current_url()); |
5504 | 5686 |
5505 // Let the main frame commit. | 5687 // Let the main frame commit. |
5506 mainframe_delayer.WaitForNavigationFinished(); | 5688 mainframe_delayer.WaitForNavigationFinished(); |
5507 EXPECT_TRUE(WaitForLoadStop(shell()->web_contents())); | 5689 EXPECT_TRUE(WaitForLoadStop(shell()->web_contents())); |
5508 EXPECT_EQ(2, controller.GetLastCommittedEntryIndex()); | 5690 EXPECT_EQ(2, controller.GetLastCommittedEntryIndex()); |
5509 EXPECT_EQ(url_b, root->current_url()); | 5691 EXPECT_EQ(url_b, root->current_url()); |
5510 | 5692 EXPECT_EQ(frame_url_b1, root->child_at(0)->current_url()); |
5511 // TODO(creis): The child's current_url should be about:blank, but we're not | |
5512 // currently getting a commit in this case. For now, we'll lack a commit for | |
5513 // this frame, similar to the slow URL case. See https://crbug.com/626416. | |
5514 if (SiteIsolationPolicy::UseSubframeNavigationEntries()) | |
5515 EXPECT_TRUE(root->child_at(0)->current_url().is_empty()); | |
5516 else | |
5517 EXPECT_EQ(frame_url_b1, root->child_at(0)->current_url()); | |
5518 | 5693 |
5519 // Check the PageState of the previous entry to ensure it isn't corrupted. | 5694 // Check the PageState of the previous entry to ensure it isn't corrupted. |
5520 NavigationEntry* entry = controller.GetEntryAtIndex(1); | 5695 NavigationEntry* entry = controller.GetEntryAtIndex(1); |
5521 EXPECT_EQ(url_a, entry->GetURL()); | 5696 EXPECT_EQ(url_a, entry->GetURL()); |
5522 ExplodedPageState exploded_state; | 5697 ExplodedPageState exploded_state; |
5523 EXPECT_TRUE( | 5698 EXPECT_TRUE( |
5524 DecodePageState(entry->GetPageState().ToEncodedData(), &exploded_state)); | 5699 DecodePageState(entry->GetPageState().ToEncodedData(), &exploded_state)); |
5525 EXPECT_EQ(url_a, GURL(exploded_state.top.url_string.string())); | 5700 EXPECT_EQ(url_a, GURL(exploded_state.top.url_string.string())); |
5526 EXPECT_EQ(frame_url_a2, | 5701 EXPECT_EQ(frame_url_a2, |
5527 GURL(exploded_state.top.children.at(0).url_string.string())); | 5702 GURL(exploded_state.top.children.at(0).url_string.string())); |
(...skipping 1022 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
6550 histogram.ExpectTotalCount(kReloadToReloadMetricName, 4); | 6725 histogram.ExpectTotalCount(kReloadToReloadMetricName, 4); |
6551 histogram.ExpectTotalCount(kReloadMainResourceToReloadMetricName, 3); | 6726 histogram.ExpectTotalCount(kReloadMainResourceToReloadMetricName, 3); |
6552 | 6727 |
6553 controller.ReloadToRefreshContent(false); | 6728 controller.ReloadToRefreshContent(false); |
6554 EXPECT_TRUE(WaitForLoadStop(shell()->web_contents())); | 6729 EXPECT_TRUE(WaitForLoadStop(shell()->web_contents())); |
6555 histogram.ExpectTotalCount(kReloadToReloadMetricName, 4); | 6730 histogram.ExpectTotalCount(kReloadToReloadMetricName, 4); |
6556 histogram.ExpectTotalCount(kReloadMainResourceToReloadMetricName, 3); | 6731 histogram.ExpectTotalCount(kReloadMainResourceToReloadMetricName, 3); |
6557 } | 6732 } |
6558 | 6733 |
6559 } // namespace content | 6734 } // namespace content |
OLD | NEW |