Upstream version 7.35.139.0
[platform/framework/web/crosswalk.git] / src / third_party / trace-viewer / third_party / tvcm / tvcm / browser_controller.py
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
3 # found in the LICENSE file.
4 import unittest
5 import sys
6 import os
7
8 from tvcm import dev_server
9 from tvcm import project as project_module
10 from tvcm import test_runner
11
12 def _TryToImportTelemetry():
13   # Maybe telemetry is just hanging around in PYTHONPATH
14   try:
15     import telemetry
16     return True
17   except:
18     pass
19
20   # Try to find it in a likely location.
21   trace_viewer_path = os.path.join(os.path.dirname(__file__), '..', '..', '..')
22   parent_chrome_path = os.path.join(trace_viewer_path, '..', '..')
23   telemetry_path = os.path.abspath(
24       os.path.join(parent_chrome_path, 'tools', 'telemetry'))
25   if not os.path.exists(os.path.join(telemetry_path, 'telemetry', '__init__.py')):
26     return False
27   if not telemetry_path in sys.path:
28     sys.path.append(telemetry_path)
29   return True
30
31
32 if _TryToImportTelemetry():
33   import telemetry
34   from telemetry.core import browser_finder
35   from telemetry.core import browser_options
36   from telemetry.core import local_server
37   from telemetry.unittest import options_for_unittests as \
38       telemetry_options_for_unittests
39
40   class _LocalDevServer(local_server.LocalServer):
41     def __init__(self, project):
42       super(_LocalDevServer, self).__init__(_LocalDevServerBackend)
43       self.project = project
44
45     def GetBackendStartupArgs(self):
46       return self.project.AsDict()
47
48     @property
49     def url(self):
50       return self.forwarder.url
51
52
53   class _LocalDevServerBackend(local_server.LocalServerBackend):
54     def __init__(self):
55       super(_LocalDevServerBackend, self).__init__()
56       self.server = None
57
58     def StartAndGetNamedPorts(self, args):
59       self.server = dev_server.DevServer(port=0, quiet=True,
60                                          project=project_module.Project.FromDict(args))
61       return [local_server.NamedPort('http', self.server.port)]
62
63     def ServeForever(self):
64       return self.server.serve_forever()
65
66 else:
67   telemetry = None
68
69
70 def IsSupported():
71   return telemetry != None
72
73 def GetAvailableBrowserTypes():
74   if telemetry == None:
75     sys.stderr.write(
76       'Could not find telemetry in $PYTHONPATH. No browsers will run\n')
77     return ''
78   from telemetry.core import browser_finder
79   finder_options = browser_options.BrowserFinderOptions()
80   return ','.join(browser_finder.GetAllAvailableBrowserTypes(finder_options) +
81                   ['any'])
82
83 class BrowserController(object):
84   def __init__(self, project):
85     self._project = project
86     self._browser = None
87     self._tab = None
88     self._server = None
89
90     if telemetry == None:
91       raise Exception('Not supported: trace-viewer must be inside a chrome checkout for this to work.')
92
93     # If run in the context of the telemetry test runner, use
94     # telemetry's browser options instead.
95     if telemetry_options_for_unittests.AreSet():
96       finder_options = telemetry_options_for_unittests.GetCopy()
97     else:
98       finder_options = browser_options.BrowserFinderOptions()
99       parser = finder_options.CreateParser('telemetry_perf_test.py')
100       from tvcm import test_runner
101       finder_options, _ = parser.parse_args(
102         ['--browser', test_runner.BROWSER_TYPE_TO_USE])
103
104
105     finder_options.browser_options.warn_if_no_flash = False
106     browser_to_create = browser_finder.FindBrowser(finder_options)
107     if not browser_to_create:
108       raise Exception(
109           'Failed to find the specified browser. ' +
110           ' Its binary is probably broken.')
111
112     self._browser = browser_to_create.Create()
113     self._tab = None
114
115     try:
116       self._browser.Start()
117       self._tab = self._browser.tabs[0]
118
119       self._server = _LocalDevServer(self._project)
120       self._browser.StartLocalServer(self._server)
121
122     except:
123       self._browser.Close()
124       raise
125
126   def NavigateToPath(self, path):
127     self._tab.Navigate(self._server.url + path)
128     self._tab.WaitForDocumentReadyStateToBeComplete()
129
130   def EvaluateJavaScript(self, js, timeout=120):
131     return self._tab.EvaluateJavaScript(js, timeout)
132
133   def WaitForJavaScriptExpression(self, js, timeout=120):
134     self._tab.WaitForJavaScriptExpression(js, timeout)
135
136   def EvaluateThennableAndWait(self, js, timeout=120):
137     if js.endswith(';'):
138       raise Exception('Must not end with ;');
139
140     full_js = """
141     window.__thennableSucceeded = undefined;
142     window.__thennableResult = undefined;
143     (function() {
144       var thennable;
145       try {
146         thennable = %s;
147       } catch(e) {
148         window.__thennableSucceeded = false;
149         window.__thennableResult = e.stack ? e.stack : e;
150         return;
151       }
152       thennable.then(
153           function(res) {
154             window.__thennableSucceeded = true;
155             window.__thennableResult = res;
156           },
157           function(err) {
158             window.__thennableSucceeded = false;
159             if (typeof(err) === 'string') {
160               window.__thennableResult = err;
161               return;
162             }
163             if (err.stack)
164                window.__thennableResult = err.stack;
165             else
166                window.__thennableResult = err;
167           });
168     })();
169 """ % js
170     self._tab.ExecuteJavaScript(full_js)
171     self._tab.WaitForJavaScriptExpression('window.__thennableSucceeded !== undefined',
172                                           timeout=timeout)
173     val = self._tab.EvaluateJavaScript('window.__thennableSucceeded')
174     if val == False:
175       raise Exception(str(self._tab.EvaluateJavaScript(
176           'window.__thennableResult')))
177     return self._tab.EvaluateJavaScript('window.__thennableResult')
178
179   @property
180   def stdout_enabled(self, enabled):
181     if enabled:
182       self._tab.message_output_stream = sys.stderr
183     else:
184       self._tab.message_output_stream = None
185
186   def __enter__(self):
187     return self
188
189   def __exit__(self, *args):
190     self.Close()
191
192   def Close(self):
193     if self._server:
194       self._server.Close()
195       self._server = None
196
197     if self._tab:
198       self._tab = None
199
200     if self._browser:
201       self._browser.Close()
202       self._browser = None