--- a/dom/media/test/external/external_media_harness/testcase.py
+++ b/dom/media/test/external/external_media_harness/testcase.py
@@ -6,25 +6,25 @@ import re
import os
import time
from marionette import BrowserMobProxyTestCaseMixin, MarionetteTestCase, Marionette
from marionette_driver import Wait
from marionette_driver.errors import TimeoutException
from marionette.marionette_test import SkipTest
-from firefox_puppeteer.testcases import BaseFirefoxTestCase
+from firefox_puppeteer import PuppeteerMixin
from external_media_tests.utils import (timestamp_now, verbose_until)
from external_media_tests.media_utils.video_puppeteer import (
VideoException,
VideoPuppeteer
)
-class MediaTestCase(BaseFirefoxTestCase, MarionetteTestCase):
+class MediaTestCase(PuppeteerMixin, MarionetteTestCase):
"""
Necessary methods for MSE playback
:param video_urls: Urls you are going to play as part of the tests.
"""
def __init__(self, *args, **kwargs):
--- a/dom/media/test/external/requirements.txt
+++ b/dom/media/test/external/requirements.txt
@@ -12,9 +12,9 @@ moznetwork==0.27
mozprocess==0.23
mozprofile==0.28
mozrunner==6.12
moztest==0.7
mozversion==1.4
wptserve==1.3.0
marionette-client==3.1.0
marionette-driver==2.0.0
-firefox-puppeteer >= 52.0.0, <53.0.0
+firefox-puppeteer >= 52.1.0, <53.0.0
--- a/testing/firefox-ui/harness/firefox_ui_harness/testcases.py
+++ b/testing/firefox-ui/harness/firefox_ui_harness/testcases.py
@@ -7,24 +7,33 @@ import pprint
from datetime import datetime
import mozfile
from marionette import MarionetteTestCase
from marionette_driver import Wait
from marionette_driver.errors import NoSuchWindowException
+from firefox_puppeteer import PuppeteerMixin
from firefox_puppeteer.api.prefs import Preferences
from firefox_puppeteer.api.software_update import SoftwareUpdate
-from firefox_puppeteer.testcases import BaseFirefoxTestCase
from firefox_puppeteer.ui.update_wizard import UpdateWizardDialog
-class FirefoxTestCase(BaseFirefoxTestCase, MarionetteTestCase):
- """ Integrate MarionetteTestCase with BaseFirefoxTestCase by reordering MRO """
+class FirefoxTestCase(PuppeteerMixin, MarionetteTestCase):
+ """Base TestCase class for Firefox Desktop tests.
+
+ This class enhances the MarionetteTestCase class with PuppeteerMixin on top
+ of MarionetteTestCase by reordering the MRO.
+
+ If you're extending the inheritance tree further to make specialized
+ TestCases, favour the use of super() as opposed to explicit calls to a
+ parent class.
+
+ """
pass
class UpdateTestCase(FirefoxTestCase):
TIMEOUT_UPDATE_APPLY = 300
TIMEOUT_UPDATE_CHECK = 30
TIMEOUT_UPDATE_DOWNLOAD = 360
@@ -50,17 +59,17 @@ class UpdateTestCase(FirefoxTestCase):
self.update_mar_channels = set(kwargs.pop('update_mar_channels'))
self.default_mar_channels = None
self.updates = []
def setUp(self, is_fallback=False):
super(UpdateTestCase, self).setUp()
- self.software_update = SoftwareUpdate(lambda: self.marionette)
+ self.software_update = SoftwareUpdate(self.marionette)
self.download_duration = None
# Bug 604364 - Preparation to test multiple update steps
self.current_update_index = 0
# Ensure that there exists no already partially downloaded update
self.remove_downloaded_update()
@@ -217,29 +226,30 @@ class UpdateTestCase(FirefoxTestCase):
:param timeout: How long to wait for the download to finish. Optional, default to 360s.
"""
def download_via_update_wizard(dialog):
""" Download the update via the old update wizard dialog.
:param dialog: Instance of :class:`UpdateWizardDialog`.
"""
- prefs = Preferences(lambda: self.marionette)
+ prefs = Preferences(self.marionette)
prefs.set_pref(self.PREF_APP_UPDATE_ALTWINDOWTYPE, dialog.window_type)
try:
# If updates have already been found, proceed to download
if dialog.wizard.selected_panel in [dialog.wizard.updates_found_basic,
dialog.wizard.error_patching,
]:
dialog.select_next_page()
# If incompatible add-on are installed, skip over the wizard page
# TODO: Remove once we no longer support version Firefox 45.0ESR
- if self.utils.compare_version(self.appinfo.version, '49.0a1') == -1:
+ if self.puppeteer.utils.compare_version(self.puppeteer.appinfo.version,
+ '49.0a1') == -1:
if dialog.wizard.selected_panel == dialog.wizard.incompatible_list:
dialog.select_next_page()
# Updates were stored in the cache, so no download is necessary
if dialog.wizard.selected_panel in [dialog.wizard.finished,
dialog.wizard.finished_background,
]:
pass
@@ -309,17 +319,17 @@ class UpdateTestCase(FirefoxTestCase):
self.software_update.force_fallback()
# Restart Firefox to apply the downloaded update
self.restart(callback=lambda: about_window.deck.apply.button.click())
def download_and_apply_forced_update(self):
# The update wizard dialog opens automatically after the restart but with a short delay
dialog = Wait(self.marionette, ignored_exceptions=[NoSuchWindowException]).until(
- lambda _: self.windows.switch_to(lambda win: type(win) is UpdateWizardDialog)
+ lambda _: self.puppeteer.windows.switch_to(lambda win: type(win) is UpdateWizardDialog)
)
# In case of a broken complete update the about window has to be used
if self.updates[self.current_update_index]['patch']['is_complete']:
about_window = None
try:
self.assertEqual(dialog.wizard.selected_panel,
dialog.wizard.error)
--- a/testing/firefox-ui/harness/requirements.txt
+++ b/testing/firefox-ui/harness/requirements.txt
@@ -1,5 +1,5 @@
-firefox-puppeteer >= 52.0.0, <53.0.0
+firefox-puppeteer >= 52.1.0, <53.0.0
marionette-client >= 2.3.0
mozfile >= 1.2
mozinfo >= 0.8
mozinstall >= 1.12
--- a/testing/firefox-ui/tests/functional/keyboard_shortcuts/test_browser_window.py
+++ b/testing/firefox-ui/tests/functional/keyboard_shortcuts/test_browser_window.py
@@ -32,17 +32,17 @@ class TestBrowserWindowShortcuts(Firefox
current_name = self.marionette.execute_script("""
return window.document.activeElement.localName;
""")
# This doesn't test anything if we're already at input.
self.assertNotEqual(current_name, "input")
# TODO: To be moved to the upcoming search library
- if self.platform == 'linux':
+ if self.puppeteer.platform == 'linux':
key = 'searchFocusUnix.commandkey'
else:
key = 'searchFocus.commandkey'
self.browser.send_shortcut(self.browser.get_entity(key), accel=True)
# TODO: Check that the right input box is focused
# Located below searchbar as class="autocomplete-textbox textbox-input"
# Anon locator has not been released yet (bug 1080764)
--- a/testing/firefox-ui/tests/functional/locationbar/test_access_locationbar.py
+++ b/testing/firefox-ui/tests/functional/locationbar/test_access_locationbar.py
@@ -8,17 +8,17 @@ from firefox_ui_harness.testcases import
class TestAccessLocationBar(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
# Clear complete history so there's no interference from previous entries.
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
self.test_urls = [
'layout/mozilla_projects.html',
'layout/mozilla.html',
'layout/mozilla_mission.html'
]
self.test_urls = [self.marionette.absolute_url(t)
for t in self.test_urls]
@@ -29,32 +29,32 @@ class TestAccessLocationBar(FirefoxTestC
def test_access_locationbar_history(self):
# Open some local pages, then about:blank
def load_urls():
with self.marionette.using_context('content'):
for url in self.test_urls:
self.marionette.navigate(url)
- self.places.wait_for_visited(self.test_urls, load_urls)
+ self.puppeteer.places.wait_for_visited(self.test_urls, load_urls)
with self.marionette.using_context('content'):
self.marionette.navigate('about:blank')
# Need to blur url bar or autocomplete won't load - bug 1038614
self.marionette.execute_script("""arguments[0].blur();""", script_args=[self.urlbar])
# Clear contents of url bar to focus, then arrow down for list of visited sites
# Verify that autocomplete is open and results are displayed
self.locationbar.clear()
- self.urlbar.send_keys(self.keys.ARROW_DOWN)
+ self.urlbar.send_keys(self.puppeteer.keys.ARROW_DOWN)
Wait(self.marionette).until(lambda _: self.autocomplete_results.is_open)
Wait(self.marionette).until(lambda _: len(self.autocomplete_results.visible_results) > 1)
# Arrow down again to select first item in list, appearing in reversed order, as loaded.
# Verify first item.
- self.urlbar.send_keys(self.keys.ARROW_DOWN)
+ self.urlbar.send_keys(self.puppeteer.keys.ARROW_DOWN)
Wait(self.marionette).until(lambda _: self.autocomplete_results.selected_index == '0')
self.assertIn('mission', self.locationbar.value)
# Navigate to the currently selected url
# Verify it loads by comparing the page url to the test url
- self.urlbar.send_keys(self.keys.ENTER)
+ self.urlbar.send_keys(self.puppeteer.keys.ENTER)
self.assertEqual(self.locationbar.value, self.test_urls[-1])
--- a/testing/firefox-ui/tests/functional/locationbar/test_escape_autocomplete.py
+++ b/testing/firefox-ui/tests/functional/locationbar/test_escape_autocomplete.py
@@ -8,17 +8,17 @@ from firefox_ui_harness.testcases import
class TestEscapeAutocomplete(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
# Clear complete history so there's no interference from previous entries.
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
self.test_urls = [
'layout/mozilla.html',
'layout/mozilla_community.html',
]
self.test_urls = [self.marionette.absolute_url(t)
for t in self.test_urls]
@@ -32,24 +32,24 @@ class TestEscapeAutocomplete(FirefoxTest
FirefoxTestCase.tearDown(self)
def test_escape_autocomplete(self):
# Open some local pages
def load_urls():
with self.marionette.using_context('content'):
for url in self.test_urls:
self.marionette.navigate(url)
- self.places.wait_for_visited(self.test_urls, load_urls)
+ self.puppeteer.places.wait_for_visited(self.test_urls, load_urls)
# Clear the location bar, type the test string, check that autocomplete list opens
self.locationbar.clear()
self.locationbar.urlbar.send_keys(self.test_string)
self.assertEqual(self.locationbar.value, self.test_string)
Wait(self.marionette).until(lambda _: self.autocomplete_results.is_open)
# Press escape, check location bar value, check autocomplete list closed
- self.locationbar.urlbar.send_keys(self.keys.ESCAPE)
+ self.locationbar.urlbar.send_keys(self.puppeteer.keys.ESCAPE)
self.assertEqual(self.locationbar.value, self.test_string)
Wait(self.marionette).until(lambda _: not self.autocomplete_results.is_open)
# Press escape again and check that locationbar returns to the page url
- self.locationbar.urlbar.send_keys(self.keys.ESCAPE)
+ self.locationbar.urlbar.send_keys(self.puppeteer.keys.ESCAPE)
self.assertEqual(self.locationbar.value, self.test_urls[-1])
--- a/testing/firefox-ui/tests/functional/locationbar/test_favicon_in_autocomplete.py
+++ b/testing/firefox-ui/tests/functional/locationbar/test_favicon_in_autocomplete.py
@@ -11,20 +11,20 @@ class TestFaviconInAutocomplete(FirefoxT
PREF_SUGGEST_SEARCHES = 'browser.urlbar.suggest.searches'
PREF_SUGGEST_BOOKMARK = 'browser.urlbar.suggest.bookmark'
def setUp(self):
FirefoxTestCase.setUp(self)
# Disable suggestions for searches and bookmarks to get results only for history
- self.prefs.set_pref(self.PREF_SUGGEST_SEARCHES, False)
- self.prefs.set_pref(self.PREF_SUGGEST_BOOKMARK, False)
+ self.puppeteer.prefs.set_pref(self.PREF_SUGGEST_SEARCHES, False)
+ self.puppeteer.prefs.set_pref(self.PREF_SUGGEST_BOOKMARK, False)
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
self.test_urls = [self.marionette.absolute_url('layout/mozilla.html')]
self.test_string = 'mozilla'
self.test_favicon = 'mozilla_favicon.ico'
self.autocomplete_results = self.browser.navbar.locationbar.autocomplete_results
@@ -36,17 +36,17 @@ class TestFaviconInAutocomplete(FirefoxT
finally:
FirefoxTestCase.tearDown(self)
def test_favicon_in_autocomplete(self):
# Open the test page
def load_urls():
with self.marionette.using_context('content'):
self.marionette.navigate(self.test_urls[0])
- self.places.wait_for_visited(self.test_urls, load_urls)
+ self.puppeteer.places.wait_for_visited(self.test_urls, load_urls)
locationbar = self.browser.navbar.locationbar
# Clear the location bar, type the test string, check that autocomplete list opens
locationbar.clear()
locationbar.urlbar.send_keys(self.test_string)
self.assertEqual(locationbar.value, self.test_string)
Wait(self.marionette).until(lambda _: self.autocomplete_results.is_complete)
--- a/testing/firefox-ui/tests/functional/locationbar/test_suggest_bookmarks.py
+++ b/testing/firefox-ui/tests/functional/locationbar/test_suggest_bookmarks.py
@@ -17,48 +17,48 @@ class TestStarInAutocomplete(FirefoxTest
def setUp(self):
FirefoxTestCase.setUp(self)
self.bookmark_panel = None
self.test_urls = [self.marionette.absolute_url('layout/mozilla_grants.html')]
# Disable search suggestions to only get results for history and bookmarks
- self.prefs.set_pref(self.PREF_SUGGEST_SEARCHES, False)
+ self.puppeteer.prefs.set_pref(self.PREF_SUGGEST_SEARCHES, False)
with self.marionette.using_context('content'):
self.marionette.navigate('about:blank')
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
def tearDown(self):
# Close the autocomplete results
try:
if self.bookmark_panel:
self.marionette.execute_script("""
arguments[0].hidePopup();
""", script_args=[self.bookmark_panel])
self.browser.navbar.locationbar.autocomplete_results.close()
- self.places.restore_default_bookmarks()
+ self.puppeteer.places.restore_default_bookmarks()
self.marionette.clear_pref(self.PREF_SUGGEST_SEARCHES)
finally:
FirefoxTestCase.tearDown(self)
def test_star_in_autocomplete(self):
search_string = 'grants'
def visit_urls():
with self.marionette.using_context('content'):
for url in self.test_urls:
self.marionette.navigate(url)
# Navigate to all the urls specified in self.test_urls and wait for them to
# be registered as visited
- self.places.wait_for_visited(self.test_urls, visit_urls)
+ self.puppeteer.places.wait_for_visited(self.test_urls, visit_urls)
# Bookmark the current page using the bookmark menu
self.browser.menubar.select_by_id('bookmarksMenu',
'menu_bookmarkThisPage')
# TODO: Replace hard-coded selector with library method when one is available
self.bookmark_panel = self.marionette.find_element(By.ID, 'editBookmarkPanel')
done_button = self.marionette.find_element(By.ID, 'editBookmarkPanelDoneButton')
@@ -66,17 +66,17 @@ class TestStarInAutocomplete(FirefoxTest
Wait(self.marionette).until(
lambda mn: self.bookmark_panel.get_attribute('panelopen') == 'true')
done_button.click()
# We must open the blank page so the autocomplete result isn't "Switch to tab"
with self.marionette.using_context('content'):
self.marionette.navigate('about:blank')
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
# Focus the locationbar, delete any contents there, and type the search string
locationbar = self.browser.navbar.locationbar
locationbar.clear()
locationbar.urlbar.send_keys(search_string)
autocomplete_results = locationbar.autocomplete_results
# Wait for the search string to be present, for the autocomplete results to appear
--- a/testing/firefox-ui/tests/functional/private_browsing/test_about_private_browsing.py
+++ b/testing/firefox-ui/tests/functional/private_browsing/test_about_private_browsing.py
@@ -11,17 +11,17 @@ from firefox_puppeteer.ui.browser.window
class TestAboutPrivateBrowsing(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
# Use a fake local support URL
support_url = 'about:blank?'
- self.prefs.set_pref('app.support.baseURL', support_url)
+ self.puppeteer.prefs.set_pref('app.support.baseURL', support_url)
self.pb_url = support_url + 'private-browsing'
def tearDown(self):
try:
self.marionette.clear_pref('app.support.baseURL')
finally:
FirefoxTestCase.tearDown(self)
--- a/testing/firefox-ui/tests/functional/security/test_dv_certificate.py
+++ b/testing/firefox-ui/tests/functional/security/test_dv_certificate.py
@@ -16,17 +16,17 @@ class TestDVCertificate(FirefoxTestCase)
self.identity_popup = self.browser.navbar.locationbar.identity_popup
self.url = 'https://ssl-dv.mozqa.com'
def tearDown(self):
try:
self.browser.switch_to()
self.identity_popup.close(force=True)
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_dv_cert(self):
with self.marionette.using_context('content'):
self.marionette.navigate(self.url)
# The lock icon should be shown
--- a/testing/firefox-ui/tests/functional/security/test_ev_certificate.py
+++ b/testing/firefox-ui/tests/functional/security/test_ev_certificate.py
@@ -16,17 +16,17 @@ class TestEVCertificate(FirefoxTestCase)
self.identity_popup = self.locationbar.identity_popup
self.url = 'https://ssl-ev.mozqa.com/'
def tearDown(self):
try:
self.browser.switch_to()
self.identity_popup.close(force=True)
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_ev_certificate(self):
with self.marionette.using_context('content'):
self.marionette.navigate(self.url)
# The lock icon should be shown
@@ -34,17 +34,17 @@ class TestEVCertificate(FirefoxTestCase)
self.locationbar.connection_icon.value_of_css_property('list-style-image'))
# Check the identity box
self.assertEqual(self.locationbar.identity_box.get_attribute('className'),
'verifiedIdentity')
# Get the information from the certificate
cert = self.browser.tabbar.selected_tab.certificate
- address = self.security.get_address_from_certificate(cert)
+ address = self.puppeteer.security.get_address_from_certificate(cert)
# Check the identity popup label displays
self.assertEqual(self.locationbar.identity_organization_label.get_attribute('value'),
cert['organization'])
self.assertEqual(self.locationbar.identity_country_label.get_attribute('value'),
'(' + address['country'] + ')')
# Open the identity popup
--- a/testing/firefox-ui/tests/functional/security/test_no_certificate.py
+++ b/testing/firefox-ui/tests/functional/security/test_no_certificate.py
@@ -18,17 +18,17 @@ class TestNoCertificate(FirefoxTestCase)
self.identity_popup = self.locationbar.identity_popup
self.url = self.marionette.absolute_url('layout/mozilla.html')
def tearDown(self):
try:
self.browser.switch_to()
self.identity_popup.close(force=True)
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_no_certificate(self):
with self.marionette.using_context('content'):
self.marionette.navigate(self.url)
# Check the favicon
--- a/testing/firefox-ui/tests/functional/security/test_safe_browsing_notification.py
+++ b/testing/firefox-ui/tests/functional/security/test_safe_browsing_notification.py
@@ -32,31 +32,31 @@ class TestSafeBrowsingNotificationBar(Fi
# Malware URL object
{
'button_property': 'safebrowsing.notAnAttackButton.label',
'report_page': 'stopbadware.org',
'unsafe_page': 'https://www.itisatrap.org/firefox/its-an-attack.html'
}
]
- self.prefs.set_pref('browser.safebrowsing.phishing.enabled', True)
- self.prefs.set_pref('browser.safebrowsing.malware.enabled', True)
+ self.puppeteer.prefs.set_pref('browser.safebrowsing.phishing.enabled', True)
+ self.puppeteer.prefs.set_pref('browser.safebrowsing.malware.enabled', True)
# Give the browser a little time, because SafeBrowsing.jsm takes a while
# between start up and adding the example urls to the db.
# hg.mozilla.org/mozilla-central/file/46aebcd9481e/browser/base/content/browser.js#l1194
time.sleep(3)
# TODO: Bug 1139544: While we don't have a reliable way to close the safe browsing
# notification bar when a test fails, run this test in a new tab.
self.browser.tabbar.open_tab()
def tearDown(self):
try:
- self.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
+ self.puppeteer.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
self.browser.tabbar.close_all_tabs([self.browser.tabbar.tabs[0]])
self.marionette.clear_pref('browser.safebrowsing.phishing.enabled')
self.marionette.clear_pref('browser.safebrowsing.malware.enabled')
finally:
FirefoxTestCase.tearDown(self)
def test_notification_bar(self):
with self.marionette.using_context('content'):
@@ -96,17 +96,17 @@ class TestSafeBrowsingNotificationBar(Fi
Wait(self.marionette, timeout=self.browser.timeout_page_load).until(
expected.element_present(By.ID, 'main-feature'),
message='Expected target element "#main-feature" has not been found',
)
self.assertEquals(self.marionette.get_url(), self.browser.get_final_url(unsafe_page))
# Clean up here since the permission gets set in this function
- self.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
+ self.puppeteer.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
# Check the not a forgery or attack button in the notification bar
def check_not_badware_button(self, button_property, report_page):
with self.marionette.using_context('chrome'):
# TODO: update to use safe browsing notification bar class when bug 1139544 lands
label = self.browser.get_property(button_property)
button = (self.marionette.find_element(By.ID, 'content')
.find_element('anon attribute', {'label': label}))
--- a/testing/firefox-ui/tests/functional/security/test_safe_browsing_warning_pages.py
+++ b/testing/firefox-ui/tests/functional/security/test_safe_browsing_warning_pages.py
@@ -18,31 +18,31 @@ class TestSafeBrowsingWarningPages(Firef
# Unwanted software URL
'https://www.itisatrap.org/firefox/unwanted.html',
# Phishing URL
'https://www.itisatrap.org/firefox/its-a-trap.html',
# Malware URL
'https://www.itisatrap.org/firefox/its-an-attack.html'
]
- self.prefs.set_pref('browser.safebrowsing.phishing.enabled', True)
- self.prefs.set_pref('browser.safebrowsing.malware.enabled', True)
+ self.puppeteer.prefs.set_pref('browser.safebrowsing.phishing.enabled', True)
+ self.puppeteer.prefs.set_pref('browser.safebrowsing.malware.enabled', True)
# Give the browser a little time, because SafeBrowsing.jsm takes a
# while between start up and adding the example urls to the db.
# hg.mozilla.org/mozilla-central/file/46aebcd9481e/browser/base/content/browser.js#l1194
time.sleep(3)
# TODO: Bug 1139544: While we don't have a reliable way to close the safe browsing
# notification bar when a test fails, run this test in a new tab.
self.browser.tabbar.open_tab()
def tearDown(self):
try:
- self.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
+ self.puppeteer.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
self.browser.tabbar.close_all_tabs([self.browser.tabbar.tabs[0]])
self.marionette.clear_pref('browser.safebrowsing.malware.enabled')
self.marionette.clear_pref('browser.safebrowsing.phishing.enabled')
finally:
FirefoxTestCase.tearDown(self)
def test_warning_pages(self):
with self.marionette.using_context("content"):
@@ -103,9 +103,9 @@ class TestSafeBrowsingWarningPages(Firef
button = self.marionette.find_element(By.ID, 'ignoreWarningButton')
button.click()
Wait(self.marionette, timeout=self.browser.timeout_page_load).until(
expected.element_present(By.ID, 'main-feature'))
self.assertEquals(self.marionette.get_url(), self.browser.get_final_url(unsafe_page))
# Clean up by removing safe browsing permission for unsafe page
- self.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
+ self.puppeteer.utils.permissions.remove('https://www.itisatrap.org', 'safe-browsing')
--- a/testing/firefox-ui/tests/functional/security/test_ssl_disabled_error_page.py
+++ b/testing/firefox-ui/tests/functional/security/test_ssl_disabled_error_page.py
@@ -12,23 +12,23 @@ from firefox_ui_harness.testcases import
class TestSSLDisabledErrorPage(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
self.url = 'https://tlsv1-0.mozqa.com'
- self.utils.sanitize({"sessions": True})
+ self.puppeteer.utils.sanitize({"sessions": True})
# Disable SSL 3.0, TLS 1.0 and TLS 1.1 for secure connections
# by forcing the use of TLS 1.2
# see: http://kb.mozillazine.org/Security.tls.version.*#Possible_values_and_their_effects
- self.prefs.set_pref('security.tls.version.min', 3)
- self.prefs.set_pref('security.tls.version.max', 3)
+ self.puppeteer.prefs.set_pref('security.tls.version.min', 3)
+ self.puppeteer.prefs.set_pref('security.tls.version.max', 3)
def tearDown(self):
try:
self.marionette.clear_pref('security.tls.version.min')
self.marionette.clear_pref('security.tls.version.max')
finally:
FirefoxTestCase.tearDown(self)
--- a/testing/firefox-ui/tests/functional/security/test_ssl_status_after_restart.py
+++ b/testing/firefox-ui/tests/functional/security/test_ssl_status_after_restart.py
@@ -27,24 +27,24 @@ class TestSSLStatusAfterRestart(FirefoxT
{
'url': 'https://ssl-ov.mozqa.com/',
'identity': '',
'type': 'secure'
}
)
# Set browser to restore previous session
- self.prefs.set_pref('browser.startup.page', 3)
+ self.puppeteer.prefs.set_pref('browser.startup.page', 3)
self.locationbar = self.browser.navbar.locationbar
self.identity_popup = self.locationbar.identity_popup
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
self.browser.tabbar.close_all_tabs([self.browser.tabbar.tabs[0]])
self.browser.switch_to()
self.identity_popup.close(force=True)
self.marionette.clear_pref('browser.startup.page')
finally:
FirefoxTestCase.tearDown(self)
@skip_if_e10s
@@ -96,17 +96,17 @@ class TestSSLStatusAfterRestart(FirefoxT
lambda _: self.identity_popup.view.security.more_info_button.click())
# Verify that the current panel is the security panel
self.assertEqual(page_info.deck.selected_panel, page_info.deck.security)
# Verify the domain listed on the security panel
# If this is a wildcard cert, check only the domain
if cert['commonName'].startswith('*'):
- self.assertIn(self.security.get_domain_from_common_name(cert['commonName']),
+ self.assertIn(self.puppeteer.security.get_domain_from_common_name(cert['commonName']),
page_info.deck.security.domain.get_attribute('value'),
'Expected domain found in certificate for ' + url)
else:
self.assertEqual(page_info.deck.security.domain.get_attribute('value'),
cert['commonName'],
'Domain value matches certificate common name.')
# Verify the owner listed on the security panel
--- a/testing/firefox-ui/tests/functional/security/test_submit_unencrypted_info_warning.py
+++ b/testing/firefox-ui/tests/functional/security/test_submit_unencrypted_info_warning.py
@@ -13,17 +13,17 @@ from firefox_ui_harness.testcases import
class TestSubmitUnencryptedInfoWarning(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
self.url = 'https://ssl-dv.mozqa.com/data/firefox/security/unencryptedsearch.html'
self.test_string = 'mozilla'
- self.prefs.set_pref('security.warn_submit_insecure', True)
+ self.puppeteer.prefs.set_pref('security.warn_submit_insecure', True)
def tearDown(self):
try:
self.marionette.clear_pref('security.warn_submit_insecure')
finally:
FirefoxTestCase.tearDown(self)
def test_submit_unencrypted_info_warning(self):
--- a/testing/firefox-ui/tests/functional/sessionstore/test_restore_windows_after_restart.py
+++ b/testing/firefox-ui/tests/functional/sessionstore/test_restore_windows_after_restart.py
@@ -59,17 +59,17 @@ class TestRestoreWindowsAfterRestart(Fir
the browser, and then ensures that the standard tabs have been
restored, and that the private ones have not.
"""
self.open_windows(self.test_windows)
self.open_windows(self.private_windows, is_private=True)
self.restart()
- windows = self.windows.all
+ windows = self.puppeteer.windows.all
# There's no guarantee that Marionette will return us an
# iterator for the opened windows that will match the
# order within our window list. Instead, we'll convert
# the list of URLs within each open window to a set of
# tuples that will allow us to do a direct comparison
# while allowing the windows to be in any order.
opened_windows = set()
--- a/testing/firefox-ui/tests/puppeteer/test_about_window.py
+++ b/testing/firefox-ui/tests/puppeteer/test_about_window.py
@@ -10,17 +10,17 @@ class TestAboutWindow(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
self.about_window = self.browser.open_about_window()
self.deck = self.about_window.deck
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_basic(self):
self.assertEqual(self.about_window.window_type, 'Browser:About')
def test_elements(self):
"""Test correct retrieval of elements."""
@@ -59,10 +59,10 @@ class TestAboutWindow(FirefoxTestCase):
open_strategies = ('menu',
opener,
)
self.about_window.close()
for trigger in open_strategies:
about_window = self.browser.open_about_window(trigger=trigger)
- self.assertEquals(about_window, self.windows.current)
+ self.assertEquals(about_window, self.puppeteer.windows.current)
about_window.close()
--- a/testing/firefox-ui/tests/puppeteer/test_appinfo.py
+++ b/testing/firefox-ui/tests/puppeteer/test_appinfo.py
@@ -7,22 +7,23 @@ from firefox_ui_harness.testcases import
class TestAppInfo(FirefoxTestCase):
def test_valid_properties(self):
binary = self.marionette.bin
version_info = mozversion.get_version(binary=binary)
- self.assertEqual(self.appinfo.ID, version_info['application_id'])
- self.assertEqual(self.appinfo.name, version_info['application_name'])
- self.assertEqual(self.appinfo.vendor, version_info['application_vendor'])
- self.assertEqual(self.appinfo.version, version_info['application_version'])
+ self.assertEqual(self.puppeteer.appinfo.ID, version_info['application_id'])
+ self.assertEqual(self.puppeteer.appinfo.name, version_info['application_name'])
+ self.assertEqual(self.puppeteer.appinfo.vendor, version_info['application_vendor'])
+ self.assertEqual(self.puppeteer.appinfo.version, version_info['application_version'])
# Bug 1298328 - Platform buildid mismatch due to incremental builds
- # self.assertEqual(self.appinfo.platformBuildID, version_info['platform_buildid'])
- self.assertEqual(self.appinfo.platformVersion, version_info['platform_version'])
- self.assertIsNotNone(self.appinfo.locale)
- self.assertIsNotNone(self.appinfo.user_agent)
- self.assertIsNotNone(self.appinfo.XPCOMABI)
+ # self.assertEqual(self.puppeteer.appinfo.platformBuildID,
+ # version_info['platform_buildid'])
+ self.assertEqual(self.puppeteer.appinfo.platformVersion, version_info['platform_version'])
+ self.assertIsNotNone(self.puppeteer.appinfo.locale)
+ self.assertIsNotNone(self.puppeteer.appinfo.user_agent)
+ self.assertIsNotNone(self.puppeteer.appinfo.XPCOMABI)
def test_invalid_properties(self):
with self.assertRaises(AttributeError):
- self.appinfo.unknown
+ self.puppeteer.appinfo.unknown
--- a/testing/firefox-ui/tests/puppeteer/test_l10n.py
+++ b/testing/firefox-ui/tests/puppeteer/test_l10n.py
@@ -8,17 +8,17 @@ from marionette_driver.errors import Mar
from firefox_puppeteer.api.l10n import L10n
from firefox_ui_harness.testcases import FirefoxTestCase
class TestL10n(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
- self.l10n = L10n(lambda: self.marionette)
+ self.l10n = L10n(self.marionette)
def tearDown(self):
FirefoxTestCase.tearDown(self)
def test_dtd_entity_chrome(self):
dtds = ['chrome://global/locale/about.dtd',
'chrome://browser/locale/baseMenuOverlay.dtd']
--- a/testing/firefox-ui/tests/puppeteer/test_notifications.py
+++ b/testing/firefox-ui/tests/puppeteer/test_notifications.py
@@ -12,27 +12,27 @@ from firefox_puppeteer.ui.browser.notifi
)
class TestNotifications(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
- self.prefs.set_pref('extensions.install.requireSecureOrigin', False)
+ self.puppeteer.prefs.set_pref('extensions.install.requireSecureOrigin', False)
self.addons_url = self.marionette.absolute_url('addons/extensions/')
- self.utils.permissions.add(self.marionette.baseurl, 'install')
+ self.puppeteer.utils.permissions.add(self.marionette.baseurl, 'install')
def tearDown(self):
try:
self.marionette.clear_pref('extensions.install.requireSecureOrigin')
self.marionette.clear_pref('xpinstall.signatures.required')
- self.utils.permissions.remove(self.addons_url, 'install')
+ self.puppeteer.utils.permissions.remove(self.addons_url, 'install')
if self.browser.notification:
self.browser.notification.close(force=True)
finally:
FirefoxTestCase.tearDown(self)
def test_open_close_notification(self):
"""Trigger and dismiss a notification"""
@@ -64,17 +64,17 @@ class TestNotifications(FirefoxTestCase)
"""Trigger a notification with an origin"""
self.trigger_addon_notification('restartless_addon_signed.xpi')
self.assertIn(self.browser.notification.origin, self.marionette.baseurl)
self.assertIsNotNone(self.browser.notification.label)
def test_addon_install_failed_notification(self):
"""Trigger add-on blocked notification using an unsigned add-on"""
# Ensure that installing unsigned extensions will fail
- self.prefs.set_pref('xpinstall.signatures.required', True)
+ self.puppeteer.prefs.set_pref('xpinstall.signatures.required', True)
self.trigger_addon_notification(
'restartless_addon_unsigned.xpi',
notification=AddOnInstallFailedNotification)
def trigger_addon_notification(self, addon, notification=AddOnInstallConfirmationNotification):
with self.marionette.using_context('content'):
self.marionette.navigate(self.addons_url)
--- a/testing/firefox-ui/tests/puppeteer/test_page_info_window.py
+++ b/testing/firefox-ui/tests/puppeteer/test_page_info_window.py
@@ -4,17 +4,17 @@
from firefox_ui_harness.testcases import FirefoxTestCase
class TestPageInfoWindow(FirefoxTestCase):
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_elements(self):
"""Test correct retrieval of elements."""
page_info = self.browser.open_page_info_window()
self.assertNotEqual(page_info.dtds, [])
@@ -63,36 +63,36 @@ class TestPageInfoWindow(FirefoxTestCase
self.browser.menubar.select_by_id('tools-menu', 'menu_pageInfo')
open_strategies = ('menu',
'shortcut',
opener,
)
for trigger in open_strategies:
- if trigger == 'shortcut' and self.platform == 'windows_nt':
+ if trigger == 'shortcut' and self.puppeteer.platform == 'windows_nt':
# The shortcut for page info window does not exist on windows.
self.assertRaises(ValueError, self.browser.open_page_info_window,
trigger=trigger)
continue
page_info = self.browser.open_page_info_window(trigger=trigger)
- self.assertEquals(page_info, self.windows.current)
+ self.assertEquals(page_info, self.puppeteer.windows.current)
page_info.close()
def test_close_window(self):
"""Test various closing strategies."""
def closer(win):
win.send_shortcut(win.get_entity('closeWindow.key'), accel=True)
# Close a tab by each trigger method
close_strategies = ('menu',
'shortcut',
closer,
)
for trigger in close_strategies:
# menu only works on OS X
- if trigger == 'menu' and self.platform != 'darwin':
+ if trigger == 'menu' and self.puppeteer.platform != 'darwin':
continue
page_info = self.browser.open_page_info_window()
page_info.close(trigger=trigger)
self.assertTrue(page_info.closed)
--- a/testing/firefox-ui/tests/puppeteer/test_places.py
+++ b/testing/firefox-ui/tests/puppeteer/test_places.py
@@ -13,18 +13,18 @@ class TestPlaces(FirefoxTestCase):
FirefoxTestCase.setUp(self)
self.urls = [self.marionette.absolute_url('layout/mozilla_governance.html'),
self.marionette.absolute_url('layout/mozilla_grants.html'),
]
def tearDown(self):
try:
- self.places.restore_default_bookmarks()
- self.places.remove_all_history()
+ self.puppeteer.places.restore_default_bookmarks()
+ self.puppeteer.places.remove_all_history()
finally:
FirefoxTestCase.tearDown(self)
def get_all_urls_in_history(self):
return self.marionette.execute_script("""
let hs = Components.classes["@mozilla.org/browser/nav-history-service;1"]
.getService(Components.interfaces.nsINavHistoryService);
let urls = [];
@@ -39,46 +39,47 @@ class TestPlaces(FirefoxTestCase):
}
root.containerOpen = false;
return urls;
""")
def test_plugins(self):
# TODO: Once we use a plugin, add a test case to verify that the data will be removed
- self.places.clear_plugin_data()
+ self.puppeteer.places.clear_plugin_data()
def test_bookmarks(self):
star_button = self.marionette.find_element(By.ID, 'bookmarks-menu-button')
# Visit URLs and bookmark them all
for url in self.urls:
with self.marionette.using_context('content'):
self.marionette.navigate(url)
- Wait(self.marionette).until(lambda _: self.places.is_bookmark_star_button_ready())
+ Wait(self.marionette).until(
+ lambda _: self.puppeteer.places.is_bookmark_star_button_ready())
star_button.click()
- Wait(self.marionette).until(lambda _: self.places.is_bookmarked(url))
+ Wait(self.marionette).until(lambda _: self.puppeteer.places.is_bookmarked(url))
- ids = self.places.get_folder_ids_for_url(url)
+ ids = self.puppeteer.places.get_folder_ids_for_url(url)
self.assertEqual(len(ids), 1)
- self.assertEqual(ids[0], self.places.bookmark_folders.unfiled)
+ self.assertEqual(ids[0], self.puppeteer.places.bookmark_folders.unfiled)
# Restore default bookmarks, so the added URLs are gone
- self.places.restore_default_bookmarks()
+ self.puppeteer.places.restore_default_bookmarks()
for url in self.urls:
- self.assertFalse(self.places.is_bookmarked(url))
+ self.assertFalse(self.puppeteer.places.is_bookmarked(url))
def test_history(self):
self.assertEqual(len(self.get_all_urls_in_history()), 0)
# Visit pages and check that they are all present
def load_urls():
with self.marionette.using_context('content'):
for url in self.urls:
self.marionette.navigate(url)
- self.places.wait_for_visited(self.urls, load_urls)
+ self.puppeteer.places.wait_for_visited(self.urls, load_urls)
self.assertEqual(self.get_all_urls_in_history(), self.urls)
# Check that both pages are no longer in the remove_all_history
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
self.assertEqual(len(self.get_all_urls_in_history()), 0)
--- a/testing/firefox-ui/tests/puppeteer/test_prefs.py
+++ b/testing/firefox-ui/tests/puppeteer/test_prefs.py
@@ -26,121 +26,121 @@ class testPreferences(FirefoxTestCase):
self.marionette.clear_pref('browser.tabs.loadBookmarksInBackground')
self.marionette.clear_pref('browser.tabs.maxOpenBeforeWarn')
self.marionette.clear_pref('browser.startup.homepage')
finally:
FirefoxTestCase.tearDown(self)
def test_get_pref(self):
# check correct types
- self.assertTrue(isinstance(self.prefs.get_pref(self.bool_pref),
+ self.assertTrue(isinstance(self.puppeteer.prefs.get_pref(self.bool_pref),
bool))
- self.assertTrue(isinstance(self.prefs.get_pref(self.int_pref),
+ self.assertTrue(isinstance(self.puppeteer.prefs.get_pref(self.int_pref),
int))
- self.assertTrue(isinstance(self.prefs.get_pref(self.string_pref),
+ self.assertTrue(isinstance(self.puppeteer.prefs.get_pref(self.string_pref),
basestring))
# unknown
- self.assertIsNone(self.prefs.get_pref(self.unknown_pref))
+ self.assertIsNone(self.puppeteer.prefs.get_pref(self.unknown_pref))
# default branch
- orig_value = self.prefs.get_pref(self.int_pref)
- self.prefs.set_pref(self.int_pref, 99999)
- self.assertEqual(self.prefs.get_pref(self.int_pref), 99999)
- self.assertEqual(self.prefs.get_pref(self.int_pref, True), orig_value)
+ orig_value = self.puppeteer.prefs.get_pref(self.int_pref)
+ self.puppeteer.prefs.set_pref(self.int_pref, 99999)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.int_pref), 99999)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.int_pref, True), orig_value)
# complex value
properties_file = 'chrome://branding/locale/browserconfig.properties'
- self.assertEqual(self.prefs.get_pref('browser.startup.homepage'),
+ self.assertEqual(self.puppeteer.prefs.get_pref('browser.startup.homepage'),
properties_file)
- value = self.prefs.get_pref('browser.startup.homepage',
- interface='nsIPrefLocalizedString')
+ value = self.puppeteer.prefs.get_pref('browser.startup.homepage',
+ interface='nsIPrefLocalizedString')
self.assertNotEqual(value, properties_file)
def test_set_pref_casted_values(self):
# basestring as boolean
- self.prefs.set_pref(self.bool_pref, '')
- self.assertFalse(self.prefs.get_pref(self.bool_pref))
+ self.puppeteer.prefs.set_pref(self.bool_pref, '')
+ self.assertFalse(self.puppeteer.prefs.get_pref(self.bool_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.bool_pref)
- self.prefs.set_pref(self.bool_pref, 'unittest')
- self.assertTrue(self.prefs.get_pref(self.bool_pref))
+ self.puppeteer.prefs.set_pref(self.bool_pref, 'unittest')
+ self.assertTrue(self.puppeteer.prefs.get_pref(self.bool_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.bool_pref)
# int as boolean
- self.prefs.set_pref(self.bool_pref, 0)
- self.assertFalse(self.prefs.get_pref(self.bool_pref))
+ self.puppeteer.prefs.set_pref(self.bool_pref, 0)
+ self.assertFalse(self.puppeteer.prefs.get_pref(self.bool_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.bool_pref)
- self.prefs.set_pref(self.bool_pref, 5)
- self.assertTrue(self.prefs.get_pref(self.bool_pref))
+ self.puppeteer.prefs.set_pref(self.bool_pref, 5)
+ self.assertTrue(self.puppeteer.prefs.get_pref(self.bool_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.bool_pref)
# boolean as int
- self.prefs.set_pref(self.int_pref, False)
- self.assertEqual(self.prefs.get_pref(self.int_pref), 0)
+ self.puppeteer.prefs.set_pref(self.int_pref, False)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.int_pref), 0)
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.int_pref)
- self.prefs.set_pref(self.int_pref, True)
- self.assertEqual(self.prefs.get_pref(self.int_pref), 1)
+ self.puppeteer.prefs.set_pref(self.int_pref, True)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.int_pref), 1)
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.int_pref)
# int as string
- self.prefs.set_pref(self.string_pref, 54)
- self.assertEqual(self.prefs.get_pref(self.string_pref), '54')
+ self.puppeteer.prefs.set_pref(self.string_pref, 54)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.string_pref), '54')
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.string_pref)
def test_set_pref_invalid(self):
self.assertRaises(AssertionError,
- self.prefs.set_pref, self.new_pref, None)
+ self.puppeteer.prefs.set_pref, self.new_pref, None)
def test_set_pref_new_preference(self):
- self.prefs.set_pref(self.new_pref, True)
- self.assertTrue(self.prefs.get_pref(self.new_pref))
+ self.puppeteer.prefs.set_pref(self.new_pref, True)
+ self.assertTrue(self.puppeteer.prefs.get_pref(self.new_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.new_pref)
- self.prefs.set_pref(self.new_pref, 5)
- self.assertEqual(self.prefs.get_pref(self.new_pref), 5)
+ self.puppeteer.prefs.set_pref(self.new_pref, 5)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.new_pref), 5)
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.new_pref)
- self.prefs.set_pref(self.new_pref, 'test')
- self.assertEqual(self.prefs.get_pref(self.new_pref), 'test')
+ self.puppeteer.prefs.set_pref(self.new_pref, 'test')
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.new_pref), 'test')
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.new_pref)
def test_set_pref_new_values(self):
- self.prefs.set_pref(self.bool_pref, True)
- self.assertTrue(self.prefs.get_pref(self.bool_pref))
+ self.puppeteer.prefs.set_pref(self.bool_pref, True)
+ self.assertTrue(self.puppeteer.prefs.get_pref(self.bool_pref))
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.bool_pref)
- self.prefs.set_pref(self.int_pref, 99999)
- self.assertEqual(self.prefs.get_pref(self.int_pref), 99999)
+ self.puppeteer.prefs.set_pref(self.int_pref, 99999)
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.int_pref), 99999)
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.int_pref)
- self.prefs.set_pref(self.string_pref, 'test_string')
- self.assertEqual(self.prefs.get_pref(self.string_pref), 'test_string')
+ self.puppeteer.prefs.set_pref(self.string_pref, 'test_string')
+ self.assertEqual(self.puppeteer.prefs.get_pref(self.string_pref), 'test_string')
# Remove when all self.marionette methods are implemented
# Please see Bug 1293588
self.marionette.clear_pref(self.string_pref)
--- a/testing/firefox-ui/tests/puppeteer/test_security.py
+++ b/testing/firefox-ui/tests/puppeteer/test_security.py
@@ -15,17 +15,17 @@ class TestSecurity(FirefoxTestCase):
with self.marionette.using_context(self.marionette.CONTEXT_CONTENT):
self.marionette.navigate(url)
cert = self.browser.tabbar.tabs[0].certificate
self.assertIn(cert['commonName'], url)
self.assertEqual(cert['organization'], 'Mozilla Corporation')
self.assertEqual(cert['issuerOrganization'], 'DigiCert Inc')
- address = self.security.get_address_from_certificate(cert)
+ address = self.puppeteer.security.get_address_from_certificate(cert)
self.assertIsNotNone(address)
self.assertIsNotNone(address['city'])
self.assertIsNotNone(address['country'])
self.assertIsNotNone(address['postal_code'])
self.assertIsNotNone(address['state'])
self.assertIsNotNone(address['street'])
def test_get_certificate(self):
--- a/testing/firefox-ui/tests/puppeteer/test_software_update.py
+++ b/testing/firefox-ui/tests/puppeteer/test_software_update.py
@@ -8,17 +8,17 @@ from firefox_ui_harness.testcases import
from firefox_puppeteer.api.software_update import SoftwareUpdate
class TestSoftwareUpdate(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
- self.software_update = SoftwareUpdate(lambda: self.marionette)
+ self.software_update = SoftwareUpdate(self.marionette)
self.saved_mar_channels = self.software_update.mar_channels.channels
self.software_update.mar_channels.channels = set(['expected', 'channels'])
def tearDown(self):
try:
self.software_update.mar_channels.channels = self.saved_mar_channels
finally:
@@ -67,17 +67,17 @@ class TestSoftwareUpdate(FirefoxTestCase
def test_staging_directory(self):
self.assertTrue(self.software_update.staging_directory)
class TestUpdateChannel(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
- self.software_update = SoftwareUpdate(lambda: self.marionette)
+ self.software_update = SoftwareUpdate(self.marionette)
self.saved_channel = self.software_update.update_channel.default_channel
self.software_update.update_channel.default_channel = 'expected_channel'
def tearDown(self):
try:
self.software_update.update_channel.default_channel = self.saved_channel
finally:
@@ -93,17 +93,17 @@ class TestUpdateChannel(FirefoxTestCase)
self.software_update.update_channel.default_channel = 'new_channel'
self.assertEqual(self.software_update.update_channel.default_channel, 'new_channel')
class TestMARChannels(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
- self.software_update = SoftwareUpdate(lambda: self.marionette)
+ self.software_update = SoftwareUpdate(self.marionette)
self.saved_mar_channels = self.software_update.mar_channels.channels
self.software_update.mar_channels.channels = set(['expected', 'channels'])
def tearDown(self):
try:
self.software_update.mar_channels.channels = self.saved_mar_channels
finally:
--- a/testing/firefox-ui/tests/puppeteer/test_toolbars.py
+++ b/testing/firefox-ui/tests/puppeteer/test_toolbars.py
@@ -14,17 +14,17 @@ class TestNavBar(FirefoxTestCase):
FirefoxTestCase.setUp(self)
self.navbar = self.browser.navbar
self.url = self.marionette.absolute_url('layout/mozilla.html')
with self.marionette.using_context('content'):
self.marionette.navigate('about:blank')
- # TODO: check why self.places.remove_all_history() does not work here
+ # TODO: check why self.puppeteer.places.remove_all_history() does not work here
self.marionette.execute_script("""
let count = gBrowser.sessionHistory.count;
gBrowser.sessionHistory.PurgeHistory(count);
""")
def test_elements(self):
self.assertEqual(self.navbar.back_button.get_attribute('localName'), 'toolbarbutton')
self.assertEqual(self.navbar.forward_button.get_attribute('localName'), 'toolbarbutton')
--- a/testing/firefox-ui/tests/puppeteer/test_update_wizard.py
+++ b/testing/firefox-ui/tests/puppeteer/test_update_wizard.py
@@ -19,17 +19,17 @@ class TestUpdateWizard(FirefoxTestCase):
""")
self.dialog = self.browser.open_window(callback=opener,
expected_window_class=UpdateWizardDialog)
self.wizard = self.dialog.wizard
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
FirefoxTestCase.tearDown(self)
def test_basic(self):
self.assertEqual(self.dialog.window_type, 'Update:Wizard')
self.assertNotEqual(self.dialog.dtds, [])
self.assertNotEqual(self.dialog.properties, [])
--- a/testing/firefox-ui/tests/puppeteer/test_utils.py
+++ b/testing/firefox-ui/tests/puppeteer/test_utils.py
@@ -6,40 +6,40 @@ from firefox_ui_harness.testcases import
class TestSanitize(FirefoxTestCase):
def setUp(self):
FirefoxTestCase.setUp(self)
# Clear all previous history and cookies.
- self.places.remove_all_history()
+ self.puppeteer.places.remove_all_history()
self.marionette.delete_all_cookies()
self.urls = [
'layout/mozilla_projects.html',
'layout/mozilla.html',
'layout/mozilla_mission.html',
'cookies/cookie_single.html'
]
self.urls = [self.marionette.absolute_url(url) for url in self.urls]
# Open the test urls, including the single cookie setting page.
def load_urls():
with self.marionette.using_context('content'):
for url in self.urls:
self.marionette.navigate(url)
- self.places.wait_for_visited(self.urls, load_urls)
+ self.puppeteer.places.wait_for_visited(self.urls, load_urls)
def tearDown(self):
FirefoxTestCase.tearDown(self)
def test_sanitize_history(self):
""" Clears history. """
- self.assertEqual(self.places.get_all_urls_in_history(), self.urls)
- self.utils.sanitize(data_type={"history": True})
- self.assertEqual(self.places.get_all_urls_in_history(), [])
+ self.assertEqual(self.puppeteer.places.get_all_urls_in_history(), self.urls)
+ self.puppeteer.utils.sanitize(data_type={"history": True})
+ self.assertEqual(self.puppeteer.places.get_all_urls_in_history(), [])
def test_sanitize_cookies(self):
""" Clears cookies. """
self.assertIsNotNone(self.marionette.get_cookie('litmus_1'))
- self.utils.sanitize(data_type={"cookies": True})
+ self.puppeteer.utils.sanitize(data_type={"cookies": True})
self.assertIsNone(self.marionette.get_cookie('litmus_1'))
--- a/testing/firefox-ui/tests/puppeteer/test_windows.py
+++ b/testing/firefox-ui/tests/puppeteer/test_windows.py
@@ -22,75 +22,75 @@ class BaseWindowTestCase(FirefoxTestCase
doesn't have enough time to get itself all sorted before
the timeout gets hit, which results in the parent killing
the content process manually, which generates a crash report,
which causes these tests to orange. We side-step this by
setting dom.ipc.tabs.shutdownTimeoutSecs to 0, which disables
the shutdown timer.
"""
FirefoxTestCase.setUp(self)
- self.prefs.set_pref('dom.ipc.tabs.shutdownTimeoutSecs', 0)
+ self.puppeteer.prefs.set_pref('dom.ipc.tabs.shutdownTimeoutSecs', 0)
def tearDown(self):
try:
self.marionette.clear_pref('dom.ipc.tabs.shutdownTimeoutSecs')
finally:
FirefoxTestCase.tearDown(self)
class TestWindows(BaseWindowTestCase):
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
BaseWindowTestCase.tearDown(self)
def test_switch_to(self):
url = self.marionette.absolute_url('layout/mozilla.html')
# Open two more windows
for index in range(0, 2):
self.marionette.execute_script(""" window.open(); """)
- windows = self.windows.all
+ windows = self.puppeteer.windows.all
self.assertEquals(len(windows), 3)
# Switch to the 2nd window
- self.windows.switch_to(windows[1].handle)
+ self.puppeteer.windows.switch_to(windows[1].handle)
self.assertEquals(windows[1].handle, self.marionette.current_chrome_window_handle)
# TODO: Needs updated tabs module for improved navigation
with self.marionette.using_context('content'):
self.marionette.navigate(url)
# Switch to the last window and find 2nd window by URL
- self.windows.switch_to(windows[2].handle)
+ self.puppeteer.windows.switch_to(windows[2].handle)
# TODO: A window can have multiple tabs, so this may need an update
# when the tabs module gets implemented
def find_by_url(win):
with win.marionette.using_context('content'):
return win.marionette.get_url() == url
- self.windows.switch_to(find_by_url)
+ self.puppeteer.windows.switch_to(find_by_url)
self.assertEquals(windows[1].handle, self.marionette.current_chrome_window_handle)
- self.windows.switch_to(find_by_url)
+ self.puppeteer.windows.switch_to(find_by_url)
# Switching to an unknown handles has to fail
self.assertRaises(NoSuchWindowException,
- self.windows.switch_to, "humbug")
+ self.puppeteer.windows.switch_to, "humbug")
self.assertRaises(NoSuchWindowException,
- self.windows.switch_to, lambda win: False)
+ self.puppeteer.windows.switch_to, lambda win: False)
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
self.browser.switch_to()
- self.assertEqual(len(self.windows.all), 1)
+ self.assertEqual(len(self.puppeteer.windows.all), 1)
def test_switch_to_unknown_window_type(self):
def open_by_js(_):
with self.marionette.using_context('chrome'):
self.marionette.execute_script("""
window.open('chrome://browser/content/safeMode.xul', '_blank',
'chrome,centerscreen,resizable=no');
""")
@@ -99,50 +99,48 @@ class TestWindows(BaseWindowTestCase):
win.close()
self.browser.switch_to()
class TestBaseWindow(BaseWindowTestCase):
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
BaseWindowTestCase.tearDown(self)
def test_basics(self):
# force BaseWindow instance
- win1 = BaseWindow(lambda: self.marionette, self.browser.handle)
+ win1 = BaseWindow(self.marionette, self.browser.handle)
self.assertEquals(win1.handle, self.marionette.current_chrome_window_handle)
self.assertEquals(win1.window_element,
self.marionette.find_element(By.CSS_SELECTOR, ':root'))
self.assertEquals(win1.window_element.get_attribute('windowtype'),
self.marionette.get_window_type())
self.assertFalse(win1.closed)
# Test invalid parameters for BaseWindow constructor
- self.assertRaises(TypeError,
- BaseWindow, self.marionette, self.browser.handle)
self.assertRaises(errors.UnknownWindowError,
- BaseWindow, lambda: self.marionette, 10)
+ BaseWindow, self.marionette, 10)
# Test invalid shortcuts
self.assertRaises(KeyError,
win1.send_shortcut, 'l', acel=True)
def test_open_close(self):
# force BaseWindow instance
- win1 = BaseWindow(lambda: self.marionette, self.browser.handle)
+ win1 = BaseWindow(self.marionette, self.browser.handle)
# Open a new window (will be focused), and check states
win2 = win1.open_window()
# force BaseWindow instance
- win2 = BaseWindow(lambda: self.marionette, win2.handle)
+ win2 = BaseWindow(self.marionette, win2.handle)
self.assertEquals(len(self.marionette.chrome_window_handles), 2)
self.assertNotEquals(win1.handle, win2.handle)
self.assertEquals(win2.handle, self.marionette.current_chrome_window_handle)
win2.close()
self.assertTrue(win2.closed)
@@ -157,103 +155,103 @@ class TestBaseWindow(BaseWindowTestCase)
window.marionette.execute_script(""" window.open(); """)
def closer(window):
window.marionette.execute_script(""" window.close(); """)
win2 = win1.open_window(callback=opener)
# force BaseWindow instance
- win2 = BaseWindow(lambda: self.marionette, win2.handle)
+ win2 = BaseWindow(self.marionette, win2.handle)
self.assertEquals(len(self.marionette.chrome_window_handles), 2)
win2.close(callback=closer)
win1.focus()
# Check for an unexpected window class
self.assertRaises(errors.UnexpectedWindowTypeError,
win1.open_window, expected_window_class=BaseWindow)
- self.windows.close_all([win1])
+ self.puppeteer.windows.close_all([win1])
def test_switch_to_and_focus(self):
# force BaseWindow instance
- win1 = BaseWindow(lambda: self.marionette, self.browser.handle)
+ win1 = BaseWindow(self.marionette, self.browser.handle)
# Open a new window (will be focused), and check states
win2 = win1.open_window()
# force BaseWindow instance
- win2 = BaseWindow(lambda: self.marionette, win2.handle)
+ win2 = BaseWindow(self.marionette, win2.handle)
self.assertEquals(win2.handle, self.marionette.current_chrome_window_handle)
- self.assertEquals(win2.handle, self.windows.focused_chrome_window_handle)
+ self.assertEquals(win2.handle, self.puppeteer.windows.focused_chrome_window_handle)
self.assertFalse(win1.focused)
self.assertTrue(win2.focused)
# Switch back to win1 without moving the focus, but focus separately
win1.switch_to()
self.assertEquals(win1.handle, self.marionette.current_chrome_window_handle)
self.assertTrue(win2.focused)
win1.focus()
self.assertTrue(win1.focused)
# Switch back to win2 by focusing it directly
win2.focus()
self.assertEquals(win2.handle, self.marionette.current_chrome_window_handle)
- self.assertEquals(win2.handle, self.windows.focused_chrome_window_handle)
+ self.assertEquals(win2.handle, self.puppeteer.windows.focused_chrome_window_handle)
self.assertTrue(win2.focused)
# Close win2, and check that it keeps active but looses focus
win2.switch_to()
win2.close()
win1.switch_to()
class TestBrowserWindow(BaseWindowTestCase):
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
BaseWindowTestCase.tearDown(self)
def test_basic(self):
self.assertNotEqual(self.browser.dtds, [])
self.assertNotEqual(self.browser.properties, [])
self.assertFalse(self.browser.is_private)
self.assertIsNotNone(self.browser.menubar)
self.assertIsNotNone(self.browser.navbar)
self.assertIsNotNone(self.browser.tabbar)
def test_open_close(self):
# open and close a new browser windows by menu
win2 = self.browser.open_browser(trigger='menu')
- self.assertEquals(win2, self.windows.current)
+ self.assertEquals(win2, self.puppeteer.windows.current)
self.assertFalse(self.browser.is_private)
win2.close(trigger='menu')
# open and close a new browser window by shortcut
win2 = self.browser.open_browser(trigger='shortcut')
- self.assertEquals(win2, self.windows.current)
+ self.assertEquals(win2, self.puppeteer.windows.current)
self.assertFalse(self.browser.is_private)
win2.close(trigger='shortcut')
# open and close a new private browsing window
win2 = self.browser.open_browser(is_private=True)
- self.assertEquals(win2, self.windows.current)
+ self.assertEquals(win2, self.puppeteer.windows.current)
self.assertTrue(win2.is_private)
win2.close()
# open and close a new private browsing window
win2 = self.browser.open_browser(trigger='shortcut', is_private=True)
- self.assertEquals(win2, self.windows.current)
+ self.assertEquals(win2, self.puppeteer.windows.current)
self.assertTrue(win2.is_private)
win2.close()
# force closing a window
win2 = self.browser.open_browser()
- self.assertEquals(win2, self.windows.current)
+ self.assertEquals(win2, self.puppeteer.windows.current)
win2.close(force=True)
--- a/testing/firefox-ui/tests/update/direct/test_direct_update.py
+++ b/testing/firefox-ui/tests/update/direct/test_direct_update.py
@@ -7,15 +7,15 @@ from firefox_ui_harness.testcases import
class TestDirectUpdate(UpdateTestCase):
def setUp(self):
UpdateTestCase.setUp(self, is_fallback=False)
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
UpdateTestCase.tearDown(self)
def test_update(self):
self.download_and_apply_available_update(force_fallback=False)
self.check_update_applied()
--- a/testing/firefox-ui/tests/update/fallback/test_fallback_update.py
+++ b/testing/firefox-ui/tests/update/fallback/test_fallback_update.py
@@ -7,16 +7,16 @@ from firefox_ui_harness.testcases import
class TestFallbackUpdate(UpdateTestCase):
def setUp(self):
UpdateTestCase.setUp(self, is_fallback=True)
def tearDown(self):
try:
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
finally:
UpdateTestCase.tearDown(self)
def test_update(self):
self.download_and_apply_available_update(force_fallback=True)
self.download_and_apply_forced_update()
self.check_update_applied()
--- a/testing/puppeteer/firefox/firefox_puppeteer/__init__.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/__init__.py
@@ -1,90 +1,9 @@
# 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 decorators import use_class_as_property
-
-
-__version__ = '52.0.0'
+from firefox_puppeteer.mixins import PuppeteerMixin
+from firefox_puppeteer.puppeteer import Puppeteer
-class Puppeteer(object):
- """The puppeteer class is used to expose libraries to test cases.
-
- example:
- `class MyTestCase(MarionetteTestCase, Puppeteer)`
-
- Each library can be referenced by its puppeteer name as a member of a
- the TestCase instance. For example, from within a test method, the
- "current_window" member of the "Browser" class can be accessed via
- "self.browser.current_window".
- """
-
- def __init__(self):
- self.marionette = None
-
- def get_marionette(self):
- return self.marionette
-
- @use_class_as_property('api.appinfo.AppInfo')
- def appinfo(self):
- """
- Provides access to members of the appinfo api.
-
- See the :class:`~api.appinfo.AppInfo` reference.
- """
-
- @use_class_as_property('api.keys.Keys')
- def keys(self):
- """
- Provides a definition of control keys to use with keyboard shortcuts.
- For example, keys.CONTROL or keys.ALT.
- See the :class:`~api.keys.Keys` reference.
- """
-
- @use_class_as_property('api.places.Places')
- def places(self):
- """Provides low-level access to several bookmark and history related actions.
-
- See the :class:`~api.places.Places` reference.
- """
-
- @use_class_as_property('api.utils.Utils')
- def utils(self):
- """Provides an api for interacting with utility actions.
-
- See the :class:`~api.utils.Utils` reference.
- """
-
- @property
- def platform(self):
- """Returns the lowercased platform name.
-
- :returns: Platform name
- """
- return self.marionette.session_capabilities['platformName']
-
- @use_class_as_property('api.prefs.Preferences')
- def prefs(self):
- """
- Provides an api for setting and inspecting preferences, as see in
- about:config.
-
- See the :class:`~api.prefs.Preferences` reference.
- """
-
- @use_class_as_property('api.security.Security')
- def security(self):
- """
- Provides an api for accessing security related properties and helpers.
-
- See the :class:`~api.security.Security` reference.
- """
-
- @use_class_as_property('ui.windows.Windows')
- def windows(self):
- """
- Provides shortcuts to the top-level windows.
-
- See the :class:`~ui.window.Windows` reference.
- """
+__version__ = '52.1.0'
--- a/testing/puppeteer/firefox/firefox_puppeteer/api/keys.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/api/keys.py
@@ -4,17 +4,14 @@
import marionette_driver
class Keys(marionette_driver.keys.Keys):
"""Proxy to marionette's keys with an "accel" provided for convenience
testing across platforms."""
- def __init__(self, marionette_getter):
- self.marionette_getter = marionette_getter
-
- caps = self.marionette_getter().session_capabilities
- self.isDarwin = caps['platformName'] == 'darwin'
+ def __init__(self, marionette):
+ self.isDarwin = marionette.session_capabilities['platformName'] == 'darwin'
@property
def ACCEL(self):
return self.META if self.isDarwin else self.CONTROL
--- a/testing/puppeteer/firefox/firefox_puppeteer/api/software_update.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/api/software_update.py
@@ -77,18 +77,18 @@ class ActiveUpdate(BaseLib):
""")
class MARChannels(BaseLib):
"""Class to handle the allowed MAR channels as listed in update-settings.ini."""
INI_SECTION = 'Settings'
INI_OPTION = 'ACCEPTED_MAR_CHANNEL_IDS'
- def __init__(self, marionette_getter):
- BaseLib.__init__(self, marionette_getter)
+ def __init__(self, marionette):
+ BaseLib.__init__(self, marionette)
self._ini_file_path = self.marionette.execute_script("""
Components.utils.import('resource://gre/modules/Services.jsm');
let file = Services.dirsvc.get('GreD', Components.interfaces.nsIFile);
file.append('update-settings.ini');
return file.path;
@@ -163,25 +163,25 @@ class MARChannels(BaseLib):
class SoftwareUpdate(BaseLib):
"""The SoftwareUpdate API adds support for an easy access to the update process."""
PREF_APP_DISTRIBUTION = 'distribution.id'
PREF_APP_DISTRIBUTION_VERSION = 'distribution.version'
PREF_APP_UPDATE_URL = 'app.update.url'
PREF_APP_UPDATE_URL_OVERRIDE = 'app.update.url.override'
PREF_DISABLED_ADDONS = 'extensions.disabledAddons'
- def __init__(self, marionette_getter):
- BaseLib.__init__(self, marionette_getter)
+ def __init__(self, marionette):
+ BaseLib.__init__(self, marionette)
- self.app_info = AppInfo(marionette_getter)
- self.prefs = Preferences(marionette_getter)
+ self.app_info = AppInfo(marionette)
+ self.prefs = Preferences(marionette)
- self._update_channel = UpdateChannel(marionette_getter)
- self._mar_channels = MARChannels(marionette_getter)
- self._active_update = ActiveUpdate(marionette_getter)
+ self._update_channel = UpdateChannel(marionette)
+ self._mar_channels = MARChannels(marionette)
+ self._active_update = ActiveUpdate(marionette)
@property
def ABI(self):
"""Get the customized ABI for the update service.
:returns: ABI version
"""
abi = self.app_info.XPCOMABI
@@ -373,20 +373,20 @@ class SoftwareUpdate(BaseLib):
return url
class UpdateChannel(BaseLib):
"""Class to handle the update channel as listed in channel-prefs.js"""
REGEX_UPDATE_CHANNEL = re.compile(r'("app\.update\.channel", ")([^"].*)(?=")')
- def __init__(self, marionette_getter):
- BaseLib.__init__(self, marionette_getter)
+ def __init__(self, marionette):
+ BaseLib.__init__(self, marionette)
- self.prefs = Preferences(marionette_getter)
+ self.prefs = Preferences(marionette)
self.file_path = self.marionette.execute_script("""
Components.utils.import('resource://gre/modules/Services.jsm');
let file = Services.dirsvc.get('PrfDef', Components.interfaces.nsIFile);
file.append('channel-prefs.js');
return file.path;
--- a/testing/puppeteer/firefox/firefox_puppeteer/api/utils.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/api/utils.py
@@ -8,17 +8,17 @@ from firefox_puppeteer.base import BaseL
class Utils(BaseLib):
"""Low-level access to utility actions."""
def __init__(self, *args, **kwargs):
BaseLib.__init__(self, *args, **kwargs)
- self._permissions = Permissions(lambda: self.marionette)
+ self._permissions = Permissions(self.marionette)
@property
def permissions(self):
"""Handling of various permissions for hosts.
:returns: Instance of the Permissions class.
"""
return self._permissions
--- a/testing/puppeteer/firefox/firefox_puppeteer/base.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/base.py
@@ -1,23 +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/.
class BaseLib(object):
"""A base class that handles lazily setting the "client" class attribute."""
- def __init__(self, marionette_getter):
- if not callable(marionette_getter):
- raise TypeError('Invalid callback for "marionette_getter": %s' % marionette_getter)
-
- self._marionette = None
- self._marionette_getter = marionette_getter
+ def __init__(self, marionette):
+ self._marionette = marionette
@property
def marionette(self):
- if self._marionette is None:
- self._marionette = self._marionette_getter()
return self._marionette
-
- def get_marionette(self):
- return self.marionette
--- a/testing/puppeteer/firefox/firefox_puppeteer/decorators.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/decorators.py
@@ -23,13 +23,13 @@ class use_class_as_property(object):
@wraps(func)
def _(cls, *args, **kwargs):
tag = '_{}_{}'.format(self.mod_name, self.cls_name)
prop = getattr(cls, tag, None)
if not prop:
module = import_module('.{}'.format(self.mod_name),
'firefox_puppeteer')
- prop = getattr(module, self.cls_name)(cls.get_marionette)
+ prop = getattr(module, self.cls_name)(cls.marionette)
setattr(cls, tag, prop)
func(cls, *args, **kwargs)
return prop
return _
rename from testing/puppeteer/firefox/firefox_puppeteer/testcases/base.py
rename to testing/puppeteer/firefox/firefox_puppeteer/mixins.py
--- a/testing/puppeteer/firefox/firefox_puppeteer/testcases/base.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/mixins.py
@@ -1,44 +1,37 @@
# 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 unittest
-
-from firefox_puppeteer import Puppeteer
+from firefox_puppeteer.puppeteer import Puppeteer
from firefox_puppeteer.ui.browser.window import BrowserWindow
-class BaseFirefoxTestCase(unittest.TestCase, Puppeteer):
- """Base TestCase class for Firefox Desktop tests.
+class PuppeteerMixin(object):
+ """Mix-in class for Firefox specific API modules exposed to test scope.
- This is designed to enhance MarionetteTestCase by inserting the Puppeteer
- mixin class (so Firefox specific API modules are exposed to test scope) and
- providing common set-up and tear-down code for Firefox tests.
+ It also provides common set-up and tear-down code for Firefox tests.
- Child classes are expected to also subclass MarionetteTestCase such that
- MarionetteTestCase is inserted into the MRO after FirefoxTestCase but before
- unittest.TestCase.
+ Child test case classes are expected to also subclass MarionetteTestCase such
+ that PuppeteerMixin is followed by MarionetteTestCase. This will insert the
+ Puppeteer mixin before the MarionetteTestCase into the MRO.
example:
- `class AwesomeTestCase(FirefoxTestCase, MarionetteTestCase)`
+ `class MyTestCase(PuppeteerMixin, MarionetteTestCase)`
The key role of MarionetteTestCase is to set self.marionette appropriately
- in `__init__`. Any TestCase class that satisfies this requirement is
+ in `setUp()`. Any TestCase class that satisfies this requirement is
compatible with this class.
If you're extending the inheritance tree further to make specialized
TestCases, favour the use of super() as opposed to explicit calls to a
parent class.
"""
- def __init__(self, *args, **kwargs):
- super(BaseFirefoxTestCase, self).__init__(*args, **kwargs)
-
def _check_and_fix_leaked_handles(self):
handle_count = len(self.marionette.window_handles)
url = []
try:
# Verify the existence of leaked tabs and print their URLs.
if self._start_handle_count < handle_count:
message = ('A test must not leak window handles. This test started with '
@@ -50,52 +43,54 @@ class BaseFirefoxTestCase(unittest.TestC
url.append(' %s' % self.marionette.get_url())
self.assertListEqual(self._init_tab_handles, self.marionette.window_handles,
message + ','.join(url))
finally:
# For clean-up make sure we work on a proper browser window
if not self.browser or self.browser.closed:
# Find a proper replacement browser window
# TODO: We have to make this less error prone in case no browser is open.
- self.browser = self.windows.switch_to(lambda win: type(win) is BrowserWindow)
+ self.browser = self.puppeteer.windows.switch_to(
+ lambda win: type(win) is BrowserWindow)
# Ensure to close all the remaining chrome windows to give following
# tests a proper start condition and make them not fail.
- self.windows.close_all([self.browser])
+ self.puppeteer.windows.close_all([self.browser])
self.browser.focus()
# Also close all remaining tabs
self.browser.tabbar.close_all_tabs([self.browser.tabbar.tabs[0]])
self.browser.tabbar.tabs[0].switch_to()
def restart(self, **kwargs):
"""Restart Firefox and re-initialize data.
:param flags: Specific restart flags for Firefox
"""
self.marionette.restart(in_app=not kwargs.get('clean'), **kwargs)
# Ensure that we always have a valid browser instance available
- self.browser = self.windows.switch_to(lambda win: type(win) is BrowserWindow)
+ self.browser = self.puppeteer.windows.switch_to(lambda win: type(win) is BrowserWindow)
def setUp(self, *args, **kwargs):
- super(BaseFirefoxTestCase, self).setUp(*args, **kwargs)
+ super(PuppeteerMixin, self).setUp(*args, **kwargs)
self._start_handle_count = len(self.marionette.window_handles)
self._init_tab_handles = self.marionette.window_handles
self.marionette.set_context('chrome')
- self.browser = self.windows.current
+ self.puppeteer = Puppeteer(self.marionette)
+ self.browser = self.puppeteer.windows.current
self.browser.focus()
with self.marionette.using_context(self.marionette.CONTEXT_CONTENT):
# Ensure that we have a default page opened
- self.marionette.navigate(self.prefs.get_pref('browser.newtab.url'))
+ self.marionette.navigate(self.puppeteer.prefs.get_pref('browser.newtab.url'))
def tearDown(self, *args, **kwargs):
self.marionette.set_context('chrome')
try:
# This code should be run after all other tearDown code
# so that in case of a failure, further tests will not run
# in a state that is more inconsistent than necessary.
self._check_and_fix_leaked_handles()
finally:
- super(BaseFirefoxTestCase, self).tearDown(*args, **kwargs)
+ super(PuppeteerMixin, self).tearDown(*args, **kwargs)
new file mode 100644
--- /dev/null
+++ b/testing/puppeteer/firefox/firefox_puppeteer/puppeteer.py
@@ -0,0 +1,84 @@
+# 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 decorators import use_class_as_property
+
+
+class Puppeteer(object):
+ """The puppeteer class is used to expose additional API and UI libraries.
+
+ Each library can be referenced by its puppeteer name as a member of a
+ Puppeteer instance. For example, the `current_window` member of the
+ `Browser` class can be accessed via `puppeteer.browser.current_window`.
+ """
+
+ def __init__(self, marionette):
+ self._marionette = marionette
+
+ @property
+ def marionette(self):
+ return self._marionette
+
+ @use_class_as_property('api.appinfo.AppInfo')
+ def appinfo(self):
+ """
+ Provides access to members of the appinfo api.
+
+ See the :class:`~api.appinfo.AppInfo` reference.
+ """
+
+ @use_class_as_property('api.keys.Keys')
+ def keys(self):
+ """
+ Provides a definition of control keys to use with keyboard shortcuts.
+ For example, keys.CONTROL or keys.ALT.
+ See the :class:`~api.keys.Keys` reference.
+ """
+
+ @use_class_as_property('api.places.Places')
+ def places(self):
+ """Provides low-level access to several bookmark and history related actions.
+
+ See the :class:`~api.places.Places` reference.
+ """
+
+ @use_class_as_property('api.utils.Utils')
+ def utils(self):
+ """Provides an api for interacting with utility actions.
+
+ See the :class:`~api.utils.Utils` reference.
+ """
+
+ @property
+ def platform(self):
+ """Returns the lowercased platform name.
+
+ :returns: Platform name
+ """
+ return self.marionette.session_capabilities['platformName']
+
+ @use_class_as_property('api.prefs.Preferences')
+ def prefs(self):
+ """
+ Provides an api for setting and inspecting preferences, as see in
+ about:config.
+
+ See the :class:`~api.prefs.Preferences` reference.
+ """
+
+ @use_class_as_property('api.security.Security')
+ def security(self):
+ """
+ Provides an api for accessing security related properties and helpers.
+
+ See the :class:`~api.security.Security` reference.
+ """
+
+ @use_class_as_property('ui.windows.Windows')
+ def windows(self):
+ """
+ Provides shortcuts to the top-level windows.
+
+ See the :class:`~ui.window.Windows` reference.
+ """
deleted file mode 100644
--- a/testing/puppeteer/firefox/firefox_puppeteer/testcases/__init__.py
+++ /dev/null
@@ -1,5 +0,0 @@
-# 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 firefox_puppeteer.testcases.base import BaseFirefoxTestCase
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/about_window/deck.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/about_window/deck.py
@@ -22,17 +22,17 @@ class Deck(UIBaseLib):
'checkingForUpdates': CheckingForUpdatesPanel,
'downloadAndInstall': DownloadAndInstallPanel,
'downloadFailed': DownloadFailedPanel,
'downloading': DownloadingPanel,
'noUpdatesFound': NoUpdatesFoundPanel,
}
panel = self.element.find_element(By.ID, panel_id)
- return mapping.get(panel_id, Panel)(lambda: self.marionette, self.window, panel)
+ return mapping.get(panel_id, Panel)(self.marionette, self.window, panel)
# Properties for visual elements of the deck #
@property
def apply(self):
"""The :class:`ApplyPanel` instance for the apply panel.
:returns: :class:`ApplyPanel` instance.
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/about_window/window.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/about_window/window.py
@@ -24,12 +24,12 @@ class AboutWindow(BaseWindow):
def deck(self):
"""The :class:`Deck` instance which represents the deck.
:returns: Reference to the deck.
"""
self.switch_to()
deck = self.window_element.find_element(By.ID, 'updateDeck')
- return Deck(lambda: self.marionette, self, deck)
+ return Deck(self.marionette, self, deck)
Windows.register_window(AboutWindow.window_type, AboutWindow)
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/base.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/base.py
@@ -6,22 +6,22 @@ from marionette_driver.marionette import
from firefox_puppeteer.base import BaseLib
from firefox_puppeteer.ui.windows import BaseWindow
class UIBaseLib(BaseLib):
"""A base class for all UI element wrapper classes inside a chrome window."""
- def __init__(self, marionette_getter, window, element):
+ def __init__(self, marionette, window, element):
assert isinstance(window, BaseWindow)
assert isinstance(element, HTMLElement)
- BaseLib.__init__(self, marionette_getter)
+ BaseLib.__init__(self, marionette)
self._window = window
self._element = element
@property
def element(self):
"""Returns the reference to the underlying DOM element.
:returns: Reference to the DOM element
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/tabbar.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/tabbar.py
@@ -21,17 +21,17 @@ class TabBar(UIBaseLib):
@property
def menupanel(self):
"""A :class:`MenuPanel` instance which represents the menu panel
at the far right side of the tabs toolbar.
:returns: :class:`MenuPanel` instance.
"""
- return MenuPanel(lambda: self.marionette, self.window)
+ return MenuPanel(self.marionette, self.window)
@property
def newtab_button(self):
"""The DOM element which represents the new tab button.
:returns: Reference to the new tab button.
"""
return self.toolbar.find_element(By.ANON_ATTRIBUTE, {'anonid': 'tabs-newtab-button'})
@@ -39,17 +39,17 @@ class TabBar(UIBaseLib):
@property
def tabs(self):
"""List of all the :class:`Tab` instances of the current browser window.
:returns: List of :class:`Tab` instances.
"""
tabs = self.toolbar.find_elements(By.TAG_NAME, 'tab')
- return [Tab(lambda: self.marionette, self.window, tab) for tab in tabs]
+ return [Tab(self.marionette, self.window, tab) for tab in tabs]
@property
def toolbar(self):
"""The DOM element which represents the tab toolbar.
:returns: Reference to the tabs toolbar.
"""
return self.element
@@ -201,20 +201,20 @@ class TabBar(UIBaseLib):
""", script_args=[tab_element])
return handle
class Tab(UIBaseLib):
"""Wraps a tab DOM element."""
- def __init__(self, marionette_getter, window, element):
- UIBaseLib.__init__(self, marionette_getter, window, element)
+ def __init__(self, marionette, window, element):
+ UIBaseLib.__init__(self, marionette, window, element)
- self._security = Security(lambda: self.marionette)
+ self._security = Security(self.marionette)
self._handle = None
# Properties for visual elements of tabs #
@property
def close_button(self):
"""The DOM element which represents the tab close button.
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/toolbars.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/toolbars.py
@@ -44,17 +44,17 @@ class NavBar(UIBaseLib):
def locationbar(self):
"""Provides access to the DOM elements contained in the
locationbar.
See the :class:`LocationBar` reference.
"""
if not self._locationbar:
urlbar = self.marionette.find_element(By.ID, 'urlbar')
- self._locationbar = LocationBar(lambda: self.marionette, self.window, urlbar)
+ self._locationbar = LocationBar(self.marionette, self.window, urlbar)
return self._locationbar
@property
def menu_button(self):
"""Provides access to the DOM element menu button in the navbar.
:returns: Reference to the menu button element.
@@ -83,17 +83,17 @@ class LocationBar(UIBaseLib):
@property
def autocomplete_results(self):
"""Provides access to and methods for the location bar
autocomplete results.
See the :class:`AutocompleteResults` reference."""
if not self._autocomplete_results:
popup = self.marionette.find_element(By.ID, 'PopupAutoCompleteRichResult')
- self._autocomplete_results = AutocompleteResults(lambda: self.marionette,
+ self._autocomplete_results = AutocompleteResults(self.marionette,
self.window, popup)
return self._autocomplete_results
def clear(self):
"""Clears the contents of the url bar (via the DELETE shortcut)."""
self.focus('shortcut')
self.urlbar.send_keys(keys.Keys.DELETE)
@@ -207,17 +207,17 @@ class LocationBar(UIBaseLib):
def identity_popup(self):
"""Provides utility members for accessing and manipulating the
identity popup.
See the :class:`IdentityPopup` reference.
"""
if not self._identity_popup:
popup = self.marionette.find_element(By.ID, 'identity-popup')
- self._identity_popup = IdentityPopup(lambda: self.marionette,
+ self._identity_popup = IdentityPopup(self.marionette,
self.window, popup)
return self._identity_popup
def load_url(self, url):
"""Load the specified url in the location bar by synthesized
keystrokes.
@@ -447,17 +447,17 @@ class IdentityPopup(UIBaseLib):
def view(self):
"""Provides utility members for accessing and manipulating the
identity popup's multi view.
See the :class:`IdentityPopupMultiView` reference.
"""
if not self._view:
view = self.marionette.find_element(By.ID, 'identity-popup-multiView')
- self._view = IdentityPopupMultiView(lambda: self.marionette, self.window, view)
+ self._view = IdentityPopupMultiView(self.marionette, self.window, view)
return self._view
class IdentityPopupMultiView(UIBaseLib):
def _create_view_for_id(self, view_id):
"""Creates an instance of :class:`IdentityPopupView` for the specified view id.
@@ -466,17 +466,17 @@ class IdentityPopupMultiView(UIBaseLib):
:returns: :class:`IdentityPopupView` instance
"""
mapping = {'identity-popup-mainView': IdentityPopupMainView,
'identity-popup-securityView': IdentityPopupSecurityView,
}
view = self.marionette.find_element(By.ID, view_id)
- return mapping.get(view_id, IdentityPopupView)(lambda: self.marionette, self.window, view)
+ return mapping.get(view_id, IdentityPopupView)(self.marionette, self.window, view)
@property
def main(self):
"""The DOM element which represents the main view.
:returns: Reference to the main view.
"""
return self._create_view_for_id('identity-popup-mainView')
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/window.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/browser/window.py
@@ -1,14 +1,15 @@
# 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_driver import By, Wait
from marionette_driver.errors import NoSuchElementException
+
from firefox_puppeteer.ui.about_window.window import AboutWindow
from firefox_puppeteer.ui.browser.notifications import (
AddOnInstallBlockedNotification,
AddOnInstallConfirmationNotification,
AddOnInstallCompleteNotification,
AddOnInstallFailedNotification,
AddOnProgressNotification,
BaseNotification)
@@ -74,17 +75,17 @@ class BrowserWindow(BaseWindow):
the back, forward and home buttons. It also contains the location bar.
See the :class:`~ui.browser.toolbars.NavBar` reference.
"""
self.switch_to()
if not self._navbar:
navbar = self.window_element.find_element(By.ID, 'nav-bar')
- self._navbar = NavBar(lambda: self.marionette, self, navbar)
+ self._navbar = NavBar(self.marionette, self, navbar)
return self._navbar
@property
def notification(self):
"""Provides access to the currently displayed notification."""
notifications_map = {
@@ -96,17 +97,17 @@ class BrowserWindow(BaseWindow):
}
try:
notification = self.window_element.find_element(
By.CSS_SELECTOR, '#notification-popup popupnotification')
notification_id = notification.get_attribute('id')
return notifications_map.get(notification_id, BaseNotification)(
- lambda: self.marionette, self, notification)
+ self.marionette, self, notification)
except NoSuchElementException:
return None # no notification is displayed
def wait_for_notification(self, notification_class=BaseNotification,
timeout=5):
"""Waits for the specified notification to be displayed.
@@ -137,17 +138,17 @@ class BrowserWindow(BaseWindow):
"""Provides access to the tab bar.
See the :class:`~ui.browser.tabbar.TabBar` reference.
"""
self.switch_to()
if not self._tabbar:
tabbrowser = self.window_element.find_element(By.ID, 'tabbrowser-tabs')
- self._tabbar = TabBar(lambda: self.marionette, self, tabbrowser)
+ self._tabbar = TabBar(self.marionette, self, tabbrowser)
return self._tabbar
def close(self, trigger='menu', force=False):
"""Closes the current browser window by using the specified trigger.
:param trigger: Optional, method to close the current browser window. This can
be a string with one of `menu` or `shortcut`, or a callback which gets triggered
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/pageinfo/deck.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/pageinfo/deck.py
@@ -20,17 +20,17 @@ class Deck(UIBaseLib):
mapping = {'feedPanel': FeedPanel,
'generalPanel': GeneralPanel,
'mediaPanel': MediaPanel,
'permPanel': PermissionsPanel,
'securityPanel': SecurityPanel
}
panel = self.element.find_element(By.ID, panel_id)
- return mapping.get(panel_id, Panel)(lambda: self.marionette, self.window, panel)
+ return mapping.get(panel_id, Panel)(self.marionette, self.window, panel)
# Properties for visual elements of the deck #
@property
def feed(self):
"""The :class:`FeedPanel` instance for the feed panel.
:returns: :class:`FeedPanel` instance.
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/pageinfo/window.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/pageinfo/window.py
@@ -28,17 +28,17 @@ class PageInfoWindow(BaseWindow):
@property
def deck(self):
"""The :class:`Deck` instance which represents the deck.
:returns: Reference to the deck.
"""
deck = self.window_element.find_element(By.ID, 'mainDeck')
- return Deck(lambda: self.marionette, self, deck)
+ return Deck(self.marionette, self, deck)
def close(self, trigger='shortcut', force=False):
"""Closes the current page info window by using the specified trigger.
:param trigger: Optional, method to close the current window. This can
be a string with one of `menu` (OS X only) or `shortcut`, or a callback
which gets triggered with the current :class:`PageInfoWindow` as parameter.
Defaults to `shortcut`.
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/update_wizard/dialog.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/update_wizard/dialog.py
@@ -29,17 +29,17 @@ class UpdateWizardDialog(BaseWindow):
@property
def wizard(self):
"""The :class:`Wizard` instance which represents the wizard.
:returns: Reference to the wizard.
"""
# The deck is also the root element
wizard = self.marionette.find_element(By.ID, 'updates')
- return Wizard(lambda: self.marionette, self, wizard)
+ return Wizard(self.marionette, self, wizard)
def select_next_page(self):
"""Clicks on "Next" button, and waits for the next page to show up."""
current_panel = self.wizard.selected_panel
self.wizard.next_button.click()
Wait(self.marionette).until(
lambda _: self.wizard.selected_panel != current_panel,
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/update_wizard/wizard.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/update_wizard/wizard.py
@@ -37,17 +37,17 @@ class Wizard(UIBaseLib):
'updatesfoundbasic': UpdatesFoundBasicPanel,
# TODO: Remove once we no longer support version Firefox 45.0ESR
'incompatibleCheck': IncompatibleCheckPanel,
'incompatibleList': IncompatibleListPanel,
}
panel = self.element.find_element(By.ID, panel_id)
- return mapping.get(panel_id, Panel)(lambda: self.marionette, self.window, panel)
+ return mapping.get(panel_id, Panel)(self.marionette, self.window, panel)
# Properties for visual buttons of the wizard #
@property
def _buttons(self):
return self.element.find_element(By.ANON_ATTRIBUTE, {'anonid': 'Buttons'})
@property
--- a/testing/puppeteer/firefox/firefox_puppeteer/ui/windows.py
+++ b/testing/puppeteer/firefox/firefox_puppeteer/ui/windows.py
@@ -108,19 +108,19 @@ class Windows(BaseLib):
self.switch_to(handle)
window_type = self.marionette.get_window_type()
finally:
# Ensure to switch back to the original window
if handle != current_handle:
self.switch_to(current_handle)
if window_type in self.windows_map:
- window = self.windows_map[window_type](lambda: self.marionette, handle)
+ window = self.windows_map[window_type](self.marionette, handle)
else:
- window = BaseWindow(lambda: self.marionette, handle)
+ window = BaseWindow(self.marionette, handle)
if expected_class is not None and type(window) is not expected_class:
raise errors.UnexpectedWindowTypeError('Expected window "%s" but got "%s"' %
(expected_class, type(window)))
# Before continuing ensure the chrome window has been completed loading
Wait(self.marionette).until(
lambda _: self.loaded(handle),
@@ -208,21 +208,21 @@ class Windows(BaseLib):
class BaseWindow(BaseLib):
"""Base class for any kind of chrome window."""
# l10n class attributes will be set by each window class individually
dtds = []
properties = []
- def __init__(self, marionette_getter, window_handle):
- BaseLib.__init__(self, marionette_getter)
- self._l10n = L10n(self.get_marionette)
- self._prefs = Preferences(self.get_marionette)
- self._windows = Windows(self.get_marionette)
+ def __init__(self, marionette, window_handle):
+ BaseLib.__init__(self, marionette)
+ self._l10n = L10n(self.marionette)
+ self._prefs = Preferences(self.marionette)
+ self._windows = Windows(self.marionette)
if window_handle not in self.marionette.chrome_window_handles:
raise errors.UnknownWindowError('Window with handle "%s" does not exist' %
window_handle)
self._handle = window_handle
def __eq__(self, other):
return self.handle == other.handle