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/basictypes.h" | 5 #include "base/basictypes.h" |
6 | |
7 #include "base/bind.h" | 6 #include "base/bind.h" |
8 #include "base/callback.h" | 7 #include "base/callback.h" |
9 #include "base/memory/shared_memory.h" | 8 #include "base/memory/shared_memory.h" |
10 #include "base/strings/string_util.h" | 9 #include "base/strings/string_util.h" |
11 #include "base/strings/utf_string_conversions.h" | 10 #include "base/strings/utf_string_conversions.h" |
12 #include "base/win/windows_version.h" | 11 #include "base/win/windows_version.h" |
13 #include "content/common/frame_messages.h" | 12 #include "content/common/frame_messages.h" |
14 #include "content/common/ssl_status_serialization.h" | 13 #include "content/common/ssl_status_serialization.h" |
15 #include "content/common/view_messages.h" | 14 #include "content/common/view_messages.h" |
16 #include "content/public/browser/browser_context.h" | 15 #include "content/public/browser/browser_context.h" |
17 #include "content/public/browser/browser_thread.h" | |
18 #include "content/public/browser/native_web_keyboard_event.h" | 16 #include "content/public/browser/native_web_keyboard_event.h" |
19 #include "content/public/browser/render_frame_host.h" | |
20 #include "content/public/browser/render_process_host.h" | |
21 #include "content/public/browser/web_contents.h" | |
22 #include "content/public/browser/web_ui_controller_factory.h" | 17 #include "content/public/browser/web_ui_controller_factory.h" |
23 #include "content/public/common/bindings_policy.h" | 18 #include "content/public/common/bindings_policy.h" |
24 #include "content/public/common/content_switches.h" | |
25 #include "content/public/common/page_zoom.h" | 19 #include "content/public/common/page_zoom.h" |
26 #include "content/public/common/url_constants.h" | 20 #include "content/public/common/url_constants.h" |
27 #include "content/public/common/url_utils.h" | 21 #include "content/public/common/url_utils.h" |
28 #include "content/public/renderer/document_state.h" | 22 #include "content/public/renderer/document_state.h" |
29 #include "content/public/renderer/history_item_serialization.h" | 23 #include "content/public/renderer/history_item_serialization.h" |
30 #include "content/public/renderer/navigation_state.h" | 24 #include "content/public/renderer/navigation_state.h" |
31 #include "content/public/test/browser_test_utils.h" | 25 #include "content/public/test/browser_test_utils.h" |
32 #include "content/public/test/render_view_test.h" | 26 #include "content/public/test/render_view_test.h" |
33 #include "content/public/test/test_utils.h" | 27 #include "content/public/test/test_utils.h" |
34 #include "content/renderer/render_view_impl.h" | 28 #include "content/renderer/render_view_impl.h" |
35 #include "content/shell/browser/shell.h" | 29 #include "content/shell/browser/shell.h" |
36 #include "content/shell/browser/shell_browser_context.h" | 30 #include "content/shell/browser/shell_browser_context.h" |
37 #include "content/shell/browser/shell_content_browser_client.h" | |
38 #include "content/shell/common/shell_content_client.h" | |
39 #include "content/shell/renderer/shell_content_renderer_client.h" | |
40 #include "content/test/content_browser_test.h" | |
41 #include "content/test/content_browser_test_utils.h" | |
42 #include "content/test/mock_keyboard.h" | 31 #include "content/test/mock_keyboard.h" |
43 #include "net/base/net_errors.h" | 32 #include "net/base/net_errors.h" |
44 #include "net/cert/cert_status_flags.h" | 33 #include "net/cert/cert_status_flags.h" |
45 #include "net/disk_cache/disk_cache.h" | |
46 #include "net/http/failing_http_transaction_factory.h" | |
47 #include "net/http/http_cache.h" | |
48 #include "net/url_request/url_request_context.h" | |
49 #include "net/url_request/url_request_context_getter.h" | |
50 #include "testing/gtest/include/gtest/gtest.h" | 34 #include "testing/gtest/include/gtest/gtest.h" |
51 #include "third_party/WebKit/public/platform/WebData.h" | 35 #include "third_party/WebKit/public/platform/WebData.h" |
52 #include "third_party/WebKit/public/platform/WebHTTPBody.h" | 36 #include "third_party/WebKit/public/platform/WebHTTPBody.h" |
53 #include "third_party/WebKit/public/platform/WebString.h" | 37 #include "third_party/WebKit/public/platform/WebString.h" |
54 #include "third_party/WebKit/public/platform/WebURLError.h" | |
55 #include "third_party/WebKit/public/platform/WebURLResponse.h" | 38 #include "third_party/WebKit/public/platform/WebURLResponse.h" |
56 #include "third_party/WebKit/public/web/WebDataSource.h" | 39 #include "third_party/WebKit/public/web/WebDataSource.h" |
57 #include "third_party/WebKit/public/web/WebFrame.h" | 40 #include "third_party/WebKit/public/web/WebFrame.h" |
58 #include "third_party/WebKit/public/web/WebHistoryItem.h" | 41 #include "third_party/WebKit/public/web/WebHistoryItem.h" |
59 #include "third_party/WebKit/public/web/WebRuntimeFeatures.h" | 42 #include "third_party/WebKit/public/web/WebRuntimeFeatures.h" |
60 #include "third_party/WebKit/public/web/WebView.h" | 43 #include "third_party/WebKit/public/web/WebView.h" |
61 #include "third_party/WebKit/public/web/WebWindowFeatures.h" | 44 #include "third_party/WebKit/public/web/WebWindowFeatures.h" |
62 #include "ui/events/keycodes/keyboard_codes.h" | 45 #include "ui/events/keycodes/keyboard_codes.h" |
63 #include "ui/gfx/codec/jpeg_codec.h" | 46 #include "ui/gfx/codec/jpeg_codec.h" |
64 #include "ui/gfx/range/range.h" | 47 #include "ui/gfx/range/range.h" |
(...skipping 251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
316 #else | 299 #else |
317 NOTIMPLEMENTED(); | 300 NOTIMPLEMENTED(); |
318 return L'\0'; | 301 return L'\0'; |
319 #endif | 302 #endif |
320 } | 303 } |
321 | 304 |
322 private: | 305 private: |
323 scoped_ptr<MockKeyboard> mock_keyboard_; | 306 scoped_ptr<MockKeyboard> mock_keyboard_; |
324 }; | 307 }; |
325 | 308 |
326 class TestShellContentRendererClient : public ShellContentRendererClient { | |
327 public: | |
328 TestShellContentRendererClient() | |
329 : latest_error_valid_(false), | |
330 latest_error_reason_(0), | |
331 latest_error_stale_copy_in_cache_(false) {} | |
332 | |
333 virtual void GetNavigationErrorStrings( | |
334 content::RenderView* render_view, | |
335 blink::WebFrame* frame, | |
336 const blink::WebURLRequest& failed_request, | |
337 const blink::WebURLError& error, | |
338 std::string* error_html, | |
339 base::string16* error_description) OVERRIDE { | |
340 if (error_html) | |
341 *error_html = "A suffusion of yellow."; | |
342 latest_error_valid_ = true; | |
343 latest_error_reason_ = error.reason; | |
344 latest_error_stale_copy_in_cache_ = error.staleCopyInCache; | |
345 } | |
346 | |
347 bool GetLatestError(int* error_code, bool* stale_cache_entry_present) { | |
348 if (latest_error_valid_) { | |
349 *error_code = latest_error_reason_; | |
350 *stale_cache_entry_present = latest_error_stale_copy_in_cache_; | |
351 } | |
352 return latest_error_valid_; | |
353 } | |
354 | |
355 private: | |
356 bool latest_error_valid_; | |
357 int latest_error_reason_; | |
358 bool latest_error_stale_copy_in_cache_; | |
359 }; | |
360 | |
361 // Must be called on IO thread. | |
362 void InterceptNetworkTransactions(net::URLRequestContextGetter* getter, | |
363 net::Error error) { | |
364 DCHECK(content::BrowserThread::CurrentlyOn(BrowserThread::IO)); | |
365 net::HttpCache* cache( | |
366 getter->GetURLRequestContext()->http_transaction_factory()->GetCache()); | |
367 DCHECK(cache); | |
368 scoped_ptr<net::FailingHttpTransactionFactory> factory( | |
369 new net::FailingHttpTransactionFactory(cache->GetSession(), error)); | |
370 // Throw away old version; since this is a browser test, there is no | |
371 // need to restore the old state. | |
372 cache->SetHttpNetworkTransactionFactoryForTesting( | |
373 factory.PassAs<net::HttpTransactionFactory>()); | |
374 } | |
375 | |
376 void CallOnUIThreadValidatingReturn(const base::Closure& callback, | |
377 int rv) { | |
378 DCHECK_EQ(net::OK, rv); | |
379 BrowserThread::PostTask( | |
380 BrowserThread::UI, FROM_HERE, callback); | |
381 } | |
382 | |
383 // Must be called on IO thread. The callback will be called on | |
384 // completion of cache clearing on the UI thread. | |
385 void BackendClearCache(scoped_ptr<disk_cache::Backend*> backend, | |
386 const base::Closure& callback, | |
387 int rv) { | |
388 DCHECK(*backend); | |
389 DCHECK_EQ(net::OK, rv); | |
390 (*backend)->DoomAllEntries( | |
391 base::Bind(&CallOnUIThreadValidatingReturn, callback)); | |
392 } | |
393 | |
394 // Must be called on IO thread. The callback will be called on | |
395 // completion of cache clearing on the UI thread. | |
396 void ClearCache(net::URLRequestContextGetter* getter, | |
397 const base::Closure& callback) { | |
398 DCHECK(content::BrowserThread::CurrentlyOn(BrowserThread::IO)); | |
399 net::HttpCache* cache( | |
400 getter->GetURLRequestContext()->http_transaction_factory()->GetCache()); | |
401 DCHECK(cache); | |
402 scoped_ptr<disk_cache::Backend*> backend(new disk_cache::Backend*); | |
403 *backend = NULL; | |
404 disk_cache::Backend** backend_ptr = backend.get(); | |
405 | |
406 net::CompletionCallback backend_callback( | |
407 base::Bind(&BackendClearCache, base::Passed(backend.Pass()), callback)); | |
408 | |
409 // backend_ptr is valid until all copies of backend_callback go out | |
410 // of scope. | |
411 if (net::OK == cache->GetBackend(backend_ptr, backend_callback)) { | |
412 // The call completed synchronously, so GetBackend didn't run the callback. | |
413 backend_callback.Run(net::OK); | |
414 } | |
415 } | |
416 | |
417 } // namespace | 309 } // namespace |
418 | 310 |
419 // Test that we get form state change notifications when input fields change. | 311 // Test that we get form state change notifications when input fields change. |
420 TEST_F(RenderViewImplTest, DISABLED_OnNavStateChanged) { | 312 TEST_F(RenderViewImplTest, DISABLED_OnNavStateChanged) { |
421 // Don't want any delay for form state sync changes. This will still post a | 313 // Don't want any delay for form state sync changes. This will still post a |
422 // message so updates will get coalesced, but as soon as we spin the message | 314 // message so updates will get coalesced, but as soon as we spin the message |
423 // loop, it will generate an update. | 315 // loop, it will generate an update. |
424 view()->set_send_content_state_immediately(true); | 316 view()->set_send_content_state_immediately(true); |
425 | 317 |
426 LoadHTML("<input type=\"text\" id=\"elt_text\"></input>"); | 318 LoadHTML("<input type=\"text\" id=\"elt_text\"></input>"); |
(...skipping 1920 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2347 | 2239 |
2348 view()->webview()->clearFocusedNode(); | 2240 view()->webview()->clearFocusedNode(); |
2349 const IPC::Message* msg3 = render_thread_->sink().GetFirstMessageMatching( | 2241 const IPC::Message* msg3 = render_thread_->sink().GetFirstMessageMatching( |
2350 ViewHostMsg_FocusedNodeChanged::ID); | 2242 ViewHostMsg_FocusedNodeChanged::ID); |
2351 EXPECT_TRUE(msg3); | 2243 EXPECT_TRUE(msg3); |
2352 ViewHostMsg_FocusedNodeChanged::Read(msg3, ¶ms); | 2244 ViewHostMsg_FocusedNodeChanged::Read(msg3, ¶ms); |
2353 EXPECT_FALSE(params.a); | 2245 EXPECT_FALSE(params.a); |
2354 render_thread_->sink().ClearMessages(); | 2246 render_thread_->sink().ClearMessages(); |
2355 } | 2247 } |
2356 | 2248 |
2357 // For actual, browser side tests targetting code in RenderView | |
2358 // or RenderViewImpl. | |
2359 class RenderViewBrowserTest : public ContentBrowserTest { | |
2360 public: | |
2361 RenderViewBrowserTest() : renderer_client_(NULL) {} | |
2362 | |
2363 virtual void SetUpCommandLine(CommandLine* command_line) OVERRIDE { | |
2364 // This method is needed to allow interaction with in-process renderer | |
2365 // and use of a test ContentRendererClient. | |
2366 command_line->AppendSwitch(switches::kSingleProcess); | |
2367 } | |
2368 | |
2369 virtual void SetUp() OVERRIDE { | |
2370 // Override setting of renderer client. | |
2371 renderer_client_ = new TestShellContentRendererClient(); | |
2372 SetContentRendererClient( | |
2373 scoped_ptr<ContentRendererClient>(renderer_client_).Pass()); | |
2374 | |
2375 ContentBrowserTest::SetUp(); | |
2376 } | |
2377 | |
2378 // Navigates to the given URL and waits for |num_navigations| to occur, and | |
2379 // the title to change to |expected_title|. | |
2380 void NavigateToURLAndWaitForTitle(const GURL& url, | |
2381 const std::string& expected_title, | |
2382 int num_navigations) { | |
2383 content::TitleWatcher title_watcher( | |
2384 shell()->web_contents(), base::ASCIIToUTF16(expected_title)); | |
2385 | |
2386 content::NavigateToURLBlockUntilNavigationsComplete( | |
2387 shell(), url, num_navigations); | |
2388 | |
2389 EXPECT_EQ(base::ASCIIToUTF16(expected_title), | |
2390 title_watcher.WaitAndGetTitle()); | |
2391 } | |
2392 | |
2393 // Returns true if there is a valid error stored; in this case | |
2394 // |*error_code| and |*stale_cache_entry_present| will be updated | |
2395 // appropriately. | |
2396 // Must be called after the renderer thread is created. | |
2397 bool GetLatestErrorFromRendererClient( | |
2398 int* error_code, bool* stale_cache_entry_present) { | |
2399 bool result = false; | |
2400 | |
2401 PostTaskToInProcessRendererAndWait( | |
2402 base::Bind(&RenderViewBrowserTest::GetLatestErrorFromRendererClient0, | |
2403 renderer_client_, &result, error_code, | |
2404 stale_cache_entry_present)); | |
2405 return result; | |
2406 } | |
2407 | |
2408 private: | |
2409 // Must be run on renderer thread. | |
2410 static void GetLatestErrorFromRendererClient0( | |
2411 TestShellContentRendererClient* renderer_client, | |
2412 bool* result, int* error_code, bool* stale_cache_entry_present) { | |
2413 *result = renderer_client->GetLatestError( | |
2414 error_code, stale_cache_entry_present); | |
2415 } | |
2416 | |
2417 // Actually owned by the superclass, so safe to keep a bare pointer. | |
2418 TestShellContentRendererClient* renderer_client_; | |
2419 }; | |
2420 | |
2421 #if defined(OS_ANDROID) | |
2422 // Flaky https://crbug.com/341745 | |
2423 #define MAYBE_ConfirmCacheInformationPlumbed DISABLED_ConfirmCacheInformationPlu
mbed | |
2424 #else | |
2425 #define MAYBE_ConfirmCacheInformationPlumbed ConfirmCacheInformationPlumbed | |
2426 #endif | |
2427 | |
2428 IN_PROC_BROWSER_TEST_F(RenderViewBrowserTest, | |
2429 MAYBE_ConfirmCacheInformationPlumbed) { | |
2430 ASSERT_TRUE(test_server()->Start()); | |
2431 | |
2432 // Load URL with "nocache" set, to create stale cache. | |
2433 GURL test_url(test_server()->GetURL("files/nocache.html")); | |
2434 NavigateToURLAndWaitForTitle(test_url, "Nocache Test Page", 1); | |
2435 | |
2436 // Reload same URL after forcing an error from the the network layer; | |
2437 // confirm that the error page is told the cached copy exists. | |
2438 int renderer_id = | |
2439 shell()->web_contents()->GetMainFrame()->GetProcess()->GetID(); | |
2440 scoped_refptr<net::URLRequestContextGetter> url_request_context_getter = | |
2441 ShellContentBrowserClient::Get()->browser_context()-> | |
2442 GetRequestContextForRenderProcess(renderer_id); | |
2443 BrowserThread::PostTask( | |
2444 BrowserThread::IO, FROM_HERE, | |
2445 base::Bind(&InterceptNetworkTransactions, url_request_context_getter, | |
2446 net::ERR_FAILED)); | |
2447 | |
2448 // An error results in one completed navigation. | |
2449 content::NavigateToURLBlockUntilNavigationsComplete(shell(), test_url, 1); | |
2450 int error_code = net::OK; | |
2451 bool stale_cache_entry_present = false; | |
2452 ASSERT_TRUE(GetLatestErrorFromRendererClient( | |
2453 &error_code, &stale_cache_entry_present)); | |
2454 EXPECT_EQ(net::ERR_FAILED, error_code); | |
2455 EXPECT_TRUE(stale_cache_entry_present); | |
2456 | |
2457 // Clear the cache and repeat; confirm lack of entry in cache reported. | |
2458 scoped_refptr<MessageLoopRunner> runner = new MessageLoopRunner; | |
2459 BrowserThread::PostTask( | |
2460 BrowserThread::IO, FROM_HERE, | |
2461 base::Bind(&ClearCache, url_request_context_getter, | |
2462 runner->QuitClosure())); | |
2463 runner->Run(); | |
2464 | |
2465 content::NavigateToURLBlockUntilNavigationsComplete(shell(), test_url, 1); | |
2466 | |
2467 error_code = net::OK; | |
2468 stale_cache_entry_present = true; | |
2469 ASSERT_TRUE(GetLatestErrorFromRendererClient( | |
2470 &error_code, &stale_cache_entry_present)); | |
2471 EXPECT_EQ(net::ERR_FAILED, error_code); | |
2472 EXPECT_FALSE(stale_cache_entry_present); | |
2473 } | |
2474 | |
2475 } // namespace content | 2249 } // namespace content |
OLD | NEW |