Bug 1301776 - Added telemetry-tests command with initial telemetry test with ping server
Amended commit with changes.
MozReview-Commit-ID: RvhRtrF7QD
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/__init__.py
@@ -0,0 +1,3 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/requirements.txt
@@ -0,0 +1,4 @@
+firefox-puppeteer
+marionette-driver
+requests==2.11.1
+simplejson
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/runtests.py
@@ -0,0 +1,14 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+from marionette_harness.runtests import cli as mn_cli
+from telemetry_harness.testcase import TelemetryTestCase
+
+
+def cli():
+ mn_cli(testcase_class=TelemetryTestCase)
+
+if __name__ == '__main__':
+ cli()
+
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/setup.py
@@ -0,0 +1,43 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+import os
+
+from setuptools import setup, find_packages
+
+PACKAGE_VERSION = '0.1'
+
+THIS_DIR = os.path.dirname(os.path.realpath(__name__))
+
+
+def read(*parts):
+ with open(os.path.join(THIS_DIR, *parts)) as f:
+ return f.read()
+
+setup(name='telemetry-tests',
+ version=PACKAGE_VERSION,
+ description=('A collection of Mozilla Firefox Telemetry tests run '
+ 'with Marionette'),
+ classifiers=[
+ 'Environment :: Console',
+ 'Intended Audience :: Developers',
+ 'License :: OSI Approved :: Mozilla Public License 2.0 (MPL 2.0)',
+ 'Natural Language :: English',
+ 'Operating System :: OS Independent',
+ 'Programming Language :: Python',
+ 'Topic :: Software Development :: Libraries :: Python Modules',
+ ],
+ keywords='mozilla',
+ author='Firefox Test Engineering Team',
+ author_email='firefox-test-engineering@mozilla.org',
+ url='https://hg.mozilla.org/mozilla-central/toolkit/telemetry/tests',
+ license='MPL 2.0',
+ packages=find_packages(),
+ zip_safe=False,
+ install_requires=read('requirements.txt').splitlines(),
+ include_package_data=True,
+ entry_points="""
+ [console_scripts]
+ telemetry-tests = runtests:cli
+ """)
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/telemetry_harness/__init__.py
@@ -0,0 +1,3 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/telemetry_harness/testcase.py
@@ -0,0 +1,129 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+import gzip
+import os
+import re
+import shutil
+import time
+import urllib
+import pdb
+
+import simplejson as json
+from firefox_puppeteer import PuppeteerMixin
+from marionette_driver.errors import MarionetteException
+from marionette_harness import MarionetteTestCase
+from marionette_harness.runner import httpd
+from marionette_driver.by import By
+from marionette_driver.addons import Addons
+
+
+here = os.path.abspath(os.path.dirname(__file__))
+doc_root = os.path.join(os.path.dirname(here), "www")
+temp_dir = os.path.join(os.path.dirname(here), "temp")
+
+
+class TelemetryTestCase(PuppeteerMixin, MarionetteTestCase):
+
+ _addons_install_button_locator = (By.ID, 'react-view')
+
+ ping_list = []
+
+ def setUp(self, *args, **kwargs):
+ super(TelemetryTestCase, self).setUp()
+
+ # Start and configure server
+ self.httpd = httpd.FixtureServer(doc_root)
+ self.httpd.start()
+ ping_route = [("POST", re.compile('/pings.*'), self.pings)]
+ self.httpd.routes.extend(ping_route)
+
+ self.ping_url = '{}pings'.format(self.httpd.get_url('/'))
+
+ telemetry_prefs = {
+ 'toolkit.telemetry.send.overrideOfficialCheck': True,
+ 'toolkit.telemetry.server': self.ping_url,
+ 'toolkit.telemetry.initDelay': '1',
+ 'datareporting.healthreport.uploadEnabled': True,
+ 'datareporting.policy.dataSubmissionEnabled': False,
+ 'datareporting.policy.dataSubmissionPolicyBypassNotification': True,
+ 'toolkit.telemetry.log.level': 0,
+ 'toolkit.telemetry.log.dump': True
+ }
+
+ # Firefox will be forced to restart with the prefs enforced.
+ self.marionette.enforce_gecko_prefs(telemetry_prefs)
+ if not os.path.exists(temp_dir):
+ os.makedirs(temp_dir)
+
+ def tearDown(self, *args, **kwargs):
+ super(TelemetryTestCase, self).tearDown()
+ self.httpd.stop()
+ # if os.path.exists(temp_dir):
+ # shutil.rmtree(temp_dir, True)
+ self.marionette.close()
+
+ def trigger_ping(self):
+ current_num_pings = len(TelemetryTestCase.ping_list)
+ time_for_ping = 0
+ try:
+ self._install_addon()
+ # self.marionette.restart(clean=False, in_app= False)
+ while not len(self.ping_list) > current_num_pings:
+ self.logger.info("{} seconds elasped waiting for ping...".format(time_for_ping))
+ time.sleep(1)
+ if time_for_ping > 59:
+ self.fail("60 second ping timeout exceeded")
+ time_for_ping += 1
+ self.logger.debug('ping received')
+ return TelemetryTestCase.ping_list.pop()
+ except Exception as e:
+ self.fail('Error generating ping: {}'.format(e.message))
+
+ def _install_addon(self):
+ try:
+ file_url = "http://testpilot.firefox.com/static/addon/addon.xpi"
+ addon_path = os.path.join(temp_dir, 'addon.xpi')
+ self.logger.info(addon_path)
+ urllib.urlretrieve(file_url, addon_path)
+ addons = Addons(self.marionette)
+ addons.install(addon_path, False)
+ except MarionetteException as e:
+ self.fail('{} - Error installing addon: {} - '.format(e.cause, e.message))
+
+ def pings(self, request, response):
+ json_data = json.loads(TelemetryTestCase.unpack(request))
+ self.ping_list.append(json_data)
+ return 200
+
+ @property
+ def client_id(self):
+ return self.marionette.execute_script('Cu.import("resource://gre/modules/ClientID.jsm");'
+ 'return ClientID.getCachedClientID();')
+
+ @property
+ def ping_id(self):
+ pass
+
+ @property
+ def build_id(self):
+ pass
+
+ @property
+ def search_count(self):
+ pass
+
+ @staticmethod
+ def unpack(incoming):
+ post_data = incoming.body
+ if "Content-Encoding" in incoming.headers and incoming.headers["Content-Encoding"] == "gzip":
+ gz_data = post_data
+ with open('temp.gz', 'wb') as gz_file:
+ gz_file.write(gz_data)
+ with gzip.open('temp.gz', 'rb') as unzipped_file:
+ plain_data = unzipped_file.read()
+ os.remove('temp.gz')
+ else:
+ plain_data = post_data
+ return plain_data
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/telemetry_tests/__init__.py
@@ -0,0 +1,3 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
new file mode 100755
--- /dev/null
+++ b/toolkit/components/telemetry/tests/marionette_tests/telemetry_tests/test_telemetry_ping.py
@@ -0,0 +1,23 @@
+# This Source Code Form is subject to the terms of the Mozilla Public
+# License, v. 2.0. If a copy of the MPL was not distributed with this
+# file, You can obtain one at http://mozilla.org/MPL/2.0/.
+
+from telemetry_harness.testcase import TelemetryTestCase
+
+
+class TestPingServer(TelemetryTestCase):
+
+ def test_wait_for_ping(self):
+ with self.marionette.using_context(self.marionette.CONTEXT_CONTENT):
+ self.marionette.navigate('http://www.mozilla.com')
+ with self.marionette.using_context(self.marionette.CONTEXT_CHROME):
+ self.browser.tabbar.open_tab()
+ assert len(self.browser.tabbar.tabs) == 2
+ self.browser.tabbar.close_tab()
+ assert len(self.browser.tabbar.tabs) == 1
+ ping = self.trigger_ping()
+ with self.marionette.using_context(self.marionette.CONTEXT_CONTENT):
+ self.marionette.navigate('http://testpilot.mozilla.com')
+ assert ping['type'] == 'main'
+
+