• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2013 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.
4 
5 #ifndef CHROME_TEST_REMOTING_REMOTE_DESKTOP_BROWSERTEST_H_
6 #define CHROME_TEST_REMOTING_REMOTE_DESKTOP_BROWSERTEST_H_
7 
8 #include "chrome/browser/apps/app_browsertest_util.h"
9 #include "chrome/browser/chrome_notification_types.h"
10 #include "chrome/browser/ui/tabs/tab_strip_model.h"
11 #include "chrome/test/base/ui_test_utils.h"
12 #include "content/public/browser/notification_service.h"
13 #include "content/public/test/browser_test_utils.h"
14 #include "net/dns/mock_host_resolver.h"
15 
16 namespace {
17 // Command line arguments specific to the chromoting browser tests.
18 const char kOverrideUserDataDir[] = "override-user-data-dir";
19 const char kNoCleanup[] = "no-cleanup";
20 const char kNoInstall[] = "no-install";
21 const char kWebAppCrx[] = "webapp-crx";
22 const char kWebAppUnpacked[] = "webapp-unpacked";
23 const char kUsername[] = "username";
24 const char kkPassword[] = "password";
25 const char kMe2MePin[] = "me2me-pin";
26 const char kRemoteHostName[] = "remote-host-name";
27 const char kExtensionName[] = "extension-name";
28 const char kHttpServer[] = "http-server";
29 
30 // ASSERT_TRUE can only be used in void returning functions. This version
31 // should be used in non-void-returning functions.
_ASSERT_TRUE(bool condition)32 inline void _ASSERT_TRUE(bool condition) {
33   ASSERT_TRUE(condition);
34   return;
35 }
36 
37 }  // namespace
38 
39 using extensions::Extension;
40 
41 namespace remoting {
42 
43 class RemoteDesktopBrowserTest : public extensions::PlatformAppBrowserTest {
44  public:
45   RemoteDesktopBrowserTest();
46   virtual ~RemoteDesktopBrowserTest();
47 
48   // InProcessBrowserTest Overrides
49   virtual void SetUp() OVERRIDE;
50   virtual void SetUpOnMainThread() OVERRIDE;
51 
52  protected:
53   // InProcessBrowserTest Overrides
54   virtual void SetUpInProcessBrowserTestFixture() OVERRIDE;
55 
56   // InProcessBrowserTest Overrides
57   virtual void TearDownInProcessBrowserTestFixture() OVERRIDE;
58 
59   // The following helpers each perform a simple task.
60 
61   // Verify the test has access to the internet (specifically google.com)
62   void VerifyInternetAccess();
63 
64   // Open the client page for the browser test to get status of host actions
65   void OpenClientBrowserPage();
66 
67   // Install the chromoting extension from a crx file.
68   void InstallChromotingAppCrx();
69 
70   // Install the unpacked chromoting extension.
71   void InstallChromotingAppUnpacked();
72 
73   // Uninstall the chromoting extension.
74   void UninstallChromotingApp();
75 
76   // Test whether the chromoting extension is installed.
77   void VerifyChromotingLoaded(bool expected);
78 
79   // Launch the chromoting app.
80   void LaunchChromotingApp();
81 
82   // Authorize: grant extended access permission to the user's computer.
83   void Authorize();
84 
85   // Authenticate: sign in to google using the credentials provided.
86   void Authenticate();
87 
88   // Approve: grant the chromoting app necessary permissions.
89   void Approve();
90 
91   // Click on "Get Started" in the Me2Me section and show the host list.
92   void ExpandMe2Me();
93 
94   // Disconnect the active Me2Me session.
95   void DisconnectMe2Me();
96 
97   // Simulate a key event.
98   void SimulateKeyPressWithCode(ui::KeyboardCode keyCode, const char* code);
99 
100   void SimulateKeyPressWithCode(ui::KeyboardCode keyCode,
101                                 const char* code,
102                                 bool control,
103                                 bool shift,
104                                 bool alt,
105                                 bool command);
106 
107   // Simulate typing a character
108   void SimulateCharInput(char c);
109 
110   // Simulate typing a string
111   void SimulateStringInput(const std::string& input);
112 
113   // Helper to simulate a left button mouse click.
114   void SimulateMouseLeftClickAt(int x, int y);
115 
116   // Helper to simulate a mouse click.
117   void SimulateMouseClickAt(
118       int modifiers, blink::WebMouseEvent::Button button, int x, int y);
119 
120   // The following helpers each perform a composite task.
121 
122   // Install the chromoting extension
123   void Install();
124 
125   // Perform all necessary steps (installation, authorization, authentication,
126   // expanding the me2me section) so that the app is ready for a me2me
127   // connection.
128   void SetUpTestForMe2Me();
129 
130   // Clean up after the test.
131   void Cleanup();
132 
133   // Perform all the auth steps: authorization, authentication, etc.
134   // It starts from the chromoting main page unauthenticated and ends up back
135   // on the chromoting main page authenticated and ready to go.
136   void Auth();
137 
138   // Connect to the local host through Me2Me.
139   void ConnectToLocalHost(bool remember_pin);
140 
141   // Connect to a remote host through Me2Me.
142   void ConnectToRemoteHost(const std::string& host_name, bool remember_pin);
143 
144   // Enter the pin number and connect.
145   void EnterPin(const std::string& name, bool remember_pin);
146 
147   // Helper to get the pin number used for me2me authentication.
me2me_pin()148   std::string me2me_pin() { return me2me_pin_; }
149 
150   // Helper to get the name of the remote host to connect to.
remote_host_name()151   std::string remote_host_name() { return remote_host_name_; }
152 
153   // Helper to get the test controller URL.
http_server()154   std::string http_server() { return http_server_; }
155 
156   // Change behavior of the default host resolver to allow DNS lookup
157   // to proceed instead of being blocked by the test infrastructure.
158   void EnableDNSLookupForThisTest(
159     net::RuleBasedHostResolverProc* host_resolver);
160 
161   // We need to reset the DNS lookup when we finish, or the test will fail.
162   void DisableDNSLookupForThisTest();
163 
164   void ParseCommandLine();
165 
166   // Accessor methods.
167 
168   // Helper to get the path to the crx file of the webapp to be tested.
WebAppCrxPath()169   base::FilePath WebAppCrxPath() { return webapp_crx_; }
170 
171   // Helper to get the extension ID of the installed chromoting webapp.
ChromotingID()172   std::string ChromotingID() { return extension_->id(); }
173 
174   // Is this a appsv2 web app?
is_platform_app()175   bool is_platform_app() {
176     return extension_->GetType() == extensions::Manifest::TYPE_PLATFORM_APP;
177   }
178 
179   // Are we testing an unpacked extension?
is_unpacked()180   bool is_unpacked() {
181     return !webapp_unpacked_.empty();
182   }
183 
184   // The "active" WebContents instance the test needs to interact with.
active_web_contents()185   content::WebContents* active_web_contents() {
186     DCHECK(!web_contents_stack_.empty());
187     return web_contents_stack_.back();
188   }
189 
190   // The client WebContents instance the test needs to interact with.
client_web_content()191   content::WebContents* client_web_content() {
192     return client_web_content_;
193   }
194 
app_web_content()195   content::WebContents* app_web_content() {
196     return app_web_content_;
197   }
198 
199   // Whether to perform the cleanup tasks (uninstalling chromoting, etc).
200   // This is useful for diagnostic purposes.
NoCleanup()201   bool NoCleanup() { return no_cleanup_; }
202 
203   // Whether to install the chromoting extension before running the test cases.
204   // This is useful for diagnostic purposes.
NoInstall()205   bool NoInstall() { return no_install_; }
206 
207   // Helper to construct the starting URL of the installed chromoting webapp.
Chromoting_Main_URL()208   GURL Chromoting_Main_URL() {
209     return GURL("chrome-extension://" + ChromotingID() + "/main.html");
210   }
211 
212   // Helper to retrieve the current URL in the active WebContents.
GetCurrentURL()213   GURL GetCurrentURL() {
214     return active_web_contents()->GetURL();
215   }
216 
217   // Helpers to execute JavaScript code on a web page.
218 
219   // Helper to execute a JavaScript code snippet in the active WebContents.
220   void ExecuteScript(const std::string& script);
221 
222   // Helper to execute a JavaScript code snippet in the active WebContents
223   // and wait for page load to complete.
224   void ExecuteScriptAndWaitForAnyPageLoad(const std::string& script);
225 
226   // Helper to execute a JavaScript code snippet in the active WebContents
227   // and extract the boolean result.
ExecuteScriptAndExtractBool(const std::string & script)228   bool ExecuteScriptAndExtractBool(const std::string& script) {
229     return ExecuteScriptAndExtractBool(active_web_contents(), script);
230   }
231 
232   // Helper to execute a JavaScript code snippet and extract the boolean result.
233   static bool ExecuteScriptAndExtractBool(content::WebContents* web_contents,
234                                           const std::string& script);
235 
236   // Helper to execute a JavaScript code snippet in the active WebContents
237   // and extract the int result.
ExecuteScriptAndExtractInt(const std::string & script)238   int ExecuteScriptAndExtractInt(const std::string& script) {
239     return ExecuteScriptAndExtractInt(active_web_contents(), script);
240   }
241 
242   // Helper to execute a JavaScript code snippet and extract the int result.
243   static int ExecuteScriptAndExtractInt(content::WebContents* web_contents,
244                                         const std::string& script);
245 
246   // Helper to execute a JavaScript code snippet in the active WebContents
247   // and extract the string result.
ExecuteScriptAndExtractString(const std::string & script)248   std::string ExecuteScriptAndExtractString(const std::string& script) {
249     return ExecuteScriptAndExtractString(active_web_contents(), script);
250   }
251 
252   // Helper to execute a JavaScript code snippet and extract the string result.
253   static std::string ExecuteScriptAndExtractString(
254       content::WebContents* web_contents, const std::string& script);
255 
256   // Helper to load a JavaScript file from |path| and inject it to
257   // current web_content.  The variable |path| is relative to the directory of
258   // the |browsertest| executable.
259   static bool LoadScript(content::WebContents* web_contents,
260                          const base::FilePath::StringType& path);
261 
262   // Helper to execute a JavaScript browser test.  It creates an object using
263   // the |browserTest.testName| ctor and calls |run| on the created object with
264   // |testData|, which can be any arbitrary object literal. The script
265   // browser_test.js must be loaded (using LoadScript) before calling this
266   // function.
267   void RunJavaScriptTest(content::WebContents* web_contents,
268                          const std::string& testName,
269                          const std::string& testData);
270 
271   // Helper to check whether an html element with the given name exists in
272   // the active WebContents.
HtmlElementExists(const std::string & name)273   bool HtmlElementExists(const std::string& name) {
274     return ExecuteScriptAndExtractBool(
275         "document.getElementById(\"" + name + "\") != null");
276   }
277 
278   // Helper to check whether a html element with the given name is visible in
279   // the active WebContents.
280   bool HtmlElementVisible(const std::string& name);
281 
282   // Click on the named HTML control in the active WebContents.
283   void ClickOnControl(const std::string& name);
284 
285   // Wait for the me2me connection to be established.
286   void WaitForConnection();
287 
288   // Checking whether the localHost has been initialized.
289   bool IsLocalHostReady();
290 
291   // Callback used by EnterPin to check whether the pin form is visible
292   // and to dismiss the host-needs-update dialog.
293   bool IsPinFormVisible();
294 
295   // Callback used by WaitForConnection to check whether the connection
296   // has been established.
297   bool IsSessionConnected();
298 
299   // Callback used by Approve to check whether the chromoting app has
300   // successfully authenticated with the Google services.
IsAuthenticated()301   bool IsAuthenticated() {
302       return IsAuthenticatedInWindow(active_web_contents());
303   }
304 
305   // If the "Host version out-of-date" form is visible, dismiss it.
306   void DismissHostVersionWarningIfVisible();
307 
308   // Callback used by Approve to check whether the chromoting app has
309   // successfully authenticated with the Google services.
310   static bool IsAuthenticatedInWindow(content::WebContents* web_contents);
311 
312   // Callback used to check whether a host action is completed.
313   // Used by browser tests while conditionally waiting for host actions.
314   static bool IsHostActionComplete(
315       content::WebContents* client_web_content, std::string host_action_var);
316 
317  private:
318   // Fields
319 
320   // This test needs to make live DNS requests for access to
321   // GAIA and sync server URLs under google.com. We use a scoped version
322   // to override the default resolver while the test is active.
323   scoped_ptr<net::ScopedDefaultHostResolverProc> mock_host_resolver_override_;
324 
325   // Stores all the WebContents instance in a stack so that we can easily
326   // return to the previous instance.
327   // The active WebContents instance is always stored at the top of the stack.
328   // Initially the stack contains the WebContents instance created by
329   // InProcessBrowserTest as the initial context to run test in.
330   // Whenever a WebContents instance is spawned and needs attention we
331   // push it onto the stack and that becomes the active instance.
332   // And once we are done with the current WebContents instance
333   // we pop it off the stack, returning to the previous instance.
334   std::vector<content::WebContents*> web_contents_stack_;
335 
336   // WebContent of the client page that facilitates communication with
337   // the HTTP server. This is how the remoting browser tests
338   // will get acknowledgments of actions completed on the host.
339   content::WebContents* client_web_content_;
340 
341   // WebContent of the landing page in the chromoting app.
342   content::WebContents* app_web_content_;
343 
344   bool no_cleanup_;
345   bool no_install_;
346   const Extension* extension_;
347   base::FilePath webapp_crx_;
348   base::FilePath webapp_unpacked_;
349   std::string username_;
350   std::string password_;
351   std::string me2me_pin_;
352   std::string remote_host_name_;
353   std::string extension_name_;
354   std::string http_server_;
355 };
356 
357 }  // namespace remoting
358 
359 #endif  // CHROME_TEST_REMOTING_REMOTE_DESKTOP_BROWSERTEST_H_
360