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
3 // found in the LICENSE file.
5 #include "base/command_line.h"
6 #include "base/file_path.h"
7 #include "base/file_util.h"
8 #include "base/path_service.h"
9 #include "base/string_number_conversions.h"
10 #include "base/string_util.h"
11 #include "base/stringprintf.h"
12 #include "base/test/test_timeouts.h"
13 #include "base/utf_string_conversions.h"
14 #include "chrome/common/chrome_paths.h"
15 #include "chrome/test/automation/tab_proxy.h"
16 #include "chrome/test/ui/ui_perf_test.h"
20 // Provides a UI Test that lets us take the browser to a url, and
21 // wait for a cookie value to be set or a JavaScript expression to evaluate
22 // true before closing the page. It is undefined what happens if you specify
23 // both a cookie and a JS expression.
24 class UrlFetchTest
: public UIPerfTest
{
28 dom_automation_enabled_
= true;
30 struct UrlFetchTestResult
{
31 std::string cookie_value
;
32 std::string javascript_variable
;
36 const CommandLine
* cmd_line
= CommandLine::ForCurrentProcess();
37 if (cmd_line
->HasSwitch("reference_build")) {
43 void RunTest(const GURL
& url
,
44 const char* wait_cookie_name
,
45 const char* wait_cookie_value
,
46 const char* var_to_fetch
,
47 const std::string
& wait_js_expr
,
48 const std::string
& wait_js_frame_xpath
,
49 base::TimeDelta wait_js_timeout
,
50 UrlFetchTestResult
* result
) {
51 scoped_refptr
<TabProxy
> tab(GetActiveTab());
52 ASSERT_EQ(AUTOMATION_MSG_NAVIGATION_SUCCESS
, tab
->NavigateToURL(url
));
54 if (wait_cookie_name
) {
55 if (wait_cookie_value
) {
56 bool completed
= WaitUntilCookieValue(
57 tab
.get(), url
, wait_cookie_name
,
58 TestTimeouts::large_test_timeout(),
60 ASSERT_TRUE(completed
);
62 result
->cookie_value
= WaitUntilCookieNonEmpty(
63 tab
.get(), url
, wait_cookie_name
,
64 TestTimeouts::large_test_timeout());
65 ASSERT_TRUE(result
->cookie_value
.length());
67 } else if (!wait_js_expr
.empty()) {
68 bool completed
= WaitUntilJavaScriptCondition(
70 UTF8ToWide(wait_js_frame_xpath
),
71 UTF8ToWide(wait_js_expr
),
73 ASSERT_TRUE(completed
);
76 std::string script
= StringPrintf(
77 "window.domAutomationController.send(%s);", var_to_fetch
);
80 bool success
= tab
->ExecuteAndExtractString(L
"", ASCIIToWide(script
),
83 result
->javascript_variable
= WideToUTF8(value
);
88 bool WriteValueToFile(std::string value
, const FilePath
& path
) {
89 int retval
= file_util::WriteFile(path
, value
.c_str(), value
.length());
90 return retval
== static_cast<int>(value
.length());
93 // To actually do anything useful, this test should have a url
94 // passed on the command line, eg.
96 // --url=http://foo.bar.com
98 // Additional arguments:
100 // --wait_cookie_name=<name>
101 // Waits for a cookie named <name> to be set before exiting successfully.
103 // --wait_cookie_value=<value>
104 // In conjunction with --wait_cookie_name, this waits for a specific value
105 // to be set. (Incompatible with --wait_cookie_output)
107 // --wait_cookie_output=<filepath>
108 // In conjunction with --wait_cookie_name, this saves the cookie value to
109 // a file at the given path. (Incompatible with --wait_cookie_value)
111 // --wait_js_expr=<jscript_expr>
112 // Waits for a javascript expression to evaluate true before exiting
115 // --wait_js_timeout=<timeout_ms>
116 // In conjunction with --wait_js_condition, this sets the timeout in ms
117 // that we are prepared to wait. If this timeout is exceeded, we will exit
118 // with failure. Note that a timeout greater than the gtest timeout will not
121 // --wait_js_frame_xpath=<xpath>
122 // In conjuction with --wait_js_condition, the JavaScript expression is
123 // executed in the context of the frame that matches the provided xpath.
124 // If this is not specified (or empty string), then the main frame is used.
127 // At the end of the test, fetch the named javascript variable from the page.
129 // --jsvar_output=<filepath>
130 // Write the value of the variable named by '--jsvar' to a file at the given
134 // Use the reference build of chrome for the test.
135 TEST_F(UrlFetchTest
, UrlFetch
) {
136 const CommandLine
* cmd_line
= CommandLine::ForCurrentProcess();
138 if (!cmd_line
->HasSwitch("url"))
141 std::string cookie_name
=
142 cmd_line
->GetSwitchValueASCII("wait_cookie_name");
143 std::string cookie_value
=
144 cmd_line
->GetSwitchValueASCII("wait_cookie_value");
145 std::string js_expr
=
146 cmd_line
->GetSwitchValueASCII("wait_js_expr");
147 std::string js_frame_xpath
=
148 cmd_line
->GetSwitchValueASCII("wait_js_frame_xpath");
149 std::string js_timeout_ms_str
=
150 cmd_line
->GetSwitchValueASCII("wait_js_timeout");
152 std::string jsvar
= cmd_line
->GetSwitchValueASCII("jsvar");
153 int js_timeout_ms
= -1; // no timeout, wait forever
155 if (!js_timeout_ms_str
.empty())
156 base::StringToInt(js_timeout_ms_str
, &js_timeout_ms
);
158 UrlFetchTestResult result
;
159 RunTest(GURL(cmd_line
->GetSwitchValueASCII("url")),
160 cookie_name
.length() > 0 ? cookie_name
.c_str() : NULL
,
161 cookie_value
.length() > 0 ? cookie_value
.c_str() : NULL
,
162 jsvar
.length() > 0 ? jsvar
.c_str() : NULL
,
165 base::TimeDelta::FromMilliseconds(js_timeout_ms
),
168 // Write out the cookie if requested
169 FilePath cookie_output_path
=
170 cmd_line
->GetSwitchValuePath("wait_cookie_output");
171 if (!cookie_output_path
.value().empty()) {
172 ASSERT_TRUE(WriteValueToFile(result
.cookie_value
, cookie_output_path
));
175 // Write out the JS Variable if requested
176 FilePath jsvar_output_path
= cmd_line
->GetSwitchValuePath("jsvar_output");
177 if (!jsvar_output_path
.value().empty()) {
178 ASSERT_TRUE(WriteValueToFile(result
.javascript_variable
,