@@ -1,509 +0,0 @@
1−# -*- Mode: Python; coding: utf-8; indent-tabs-mode: nil; tab-width: 4 -*-
2−#
3−# Copyright 2015 Canonical Ltd.
4−#
5−# This program is free software; you can redistribute it and/or modify
6−# it under the terms of the GNU General Public License version 3, as published
7−# by the Free Software Foundation.
8−#
9−# This program is distributed in the hope that it will be useful,
10−# but WITHOUT ANY WARRANTY; without even the implied warranty of
11−# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12−# GNU General Public License for more details.
13−#
14−# You should have received a copy of the GNU General Public License
15−# along with this program. If not, see <http://www.gnu.org/licenses/>
16−
17−import logging
18−import re
19−
20−import autopilot
21−from autopilot import introspection
22−from ubuntuuitoolkit import UbuntuUIToolkitCustomProxyObjectBase
23−
24−from unity8.settings_wizard import override_proxy_timeout
25−
26−logger = logging.getLogger(__name__)
27−
28−
29−def get_wizard(current_page):
30− return current_page.get_root_instance().select_single(Wizard)
31−
32−
33−class Wizard(UbuntuUIToolkitCustomProxyObjectBase):
34− """High-level helper to navigate through the pages of the wizard"""
35−
36− def get_language_page(self):
37− return self.wait_select_single(
38− objectName='languagePage', visible='True')
39−
40− def get_current_page(self):
41− return self.wait_select_single('Page', visible='True')
42−
43− def get_sim_page(self):
44− return self.wait_select_single(
45− objectName='simPage', visible='True')
46−
47− def get_password_page(self):
48− return self.wait_select_single(
49− objectName='passwdPage', visible='True')
50−
51− def get_password_entry_page(self):
52− return self.wait_select_single(
53− objectName='passwdSetPage', visible='True')
54−
55− def get_confirm_password_page(self):
56− return self.wait_select_single(
57− objectName='passwdConfirmPage', visible='True')
58−
59− def get_wifi_connect_page(self):
60− return self.wait_select_single(
61− objectName='wifiPage', visible='True')
62−
63− def get_reporting_page(self):
64− return self.wait_select_single(
65− objectName='reportingPage', visible='True')
66−
67− def get_finished_page(self):
68− return self.wait_select_single(
69− objectName='finishedPage', visible='True')
70−
71−
72−class WizardLanguagePage(UbuntuUIToolkitCustomProxyObjectBase):
73− """Helper class to interact with the language welcome page"""
74−
75− # This class was renamed from LanguagePage to WizardLanguagePage because
76− # there is a class with the same name in the system settings custom proxy
77− # objects. Reported in http://pad.lv/1422904. --elopio - 2015-02-17
78−
79− @classmethod
80− def validate_dbus_object(cls, path, state):
81− name = introspection.get_classname_from_path(path)
82− if name == b'Page':
83− if state['objectName'][1] == 'languagePage':
84− return True
85− return False
86−
87− def _get_language_button(self):
88− return self.select_single(
89− 'ComboButton', objectName='languageCombo')
90−
91− def _get_continue_button(self):
92− return self.select_single('StackButton', text='Continue')
93−
94− def _swipe_to_language(self, list, language):
95− """Swipe to the chosen language in the given list"""
96− list.swipe_to_top()
97− while not list.atYEnd:
98− try:
99− item = list.select_single(
100− 'LabelVisual', text=language, visible='True')
101− item.swipe_into_view()
102− return item
103− except introspection.dbus.StateNotFoundError:
104− list.swipe_to_show_more_below()
105− # item could not be found
106− raise introspection.dbus.StateNotFoundError
107−
108− @autopilot.logging.log_action(logger.info)
109− def select_language(self, language):
110− """Select a different language from the list"""
111− combo_button = self._get_language_button()
112− self.pointing_device.click_object(combo_button)
113− language_list = combo_button.wait_select_single(
114− 'UbuntuListView11', visible='True')
115− item = self._swipe_to_language(language_list, language)
116− self.pointing_device.click_object(item)
117−
118− def get_selected_language(self):
119− return self._get_language_button().get_properties()['text']
120−
121− @autopilot.logging.log_action(logger.info)
122− def continue_(self):
123− self.pointing_device.click_object(self._get_continue_button())
124− wizard = get_wizard(self)
125− next_page = wizard.get_current_page()
126− sim_inserted = True
127− if next_page.objectName == 'simPage':
128− # no sim is inserted
129− next_page = wizard.get_sim_page()
130− sim_inserted = False
131− else:
132− # sim is inserted
133− next_page = wizard.get_password_page()
134− return sim_inserted, next_page
135−
136−
137−class SimPage(UbuntuUIToolkitCustomProxyObjectBase):
138− """Helper class to interact with the no sim notification page"""
139−
140− @classmethod
141− def validate_dbus_object(cls, path, state):
142− name = introspection.get_classname_from_path(path)
143− if name == b'Page':
144− if state['objectName'][1] == 'simPage':
145− return True
146− return False
147−
148− def _get_back_button(self):
149− return self.select_single('StackButton', text='Back')
150−
151− def _get_skip_button(self):
152− return self.select_single('StackButton', text='Skip')
153−
154− @autopilot.logging.log_action(logger.info)
155− def back(self):
156− self.pointing_device.click_object(self._get_back_button())
157− return get_wizard(self).get_languge_page()
158−
159− @autopilot.logging.log_action(logger.info)
160− def skip(self):
161− self.pointing_device.click_object(self._get_skip_button())
162− return get_wizard(self).get_password_page()
163−
164−
165−class PasswordPage(UbuntuUIToolkitCustomProxyObjectBase):
166− """Helper class to interact with the password security page"""
167−
168− SECURITY_SWIPE = 'Swipe'
169− SECURITY_PASSCODE = 'Passcode'
170− SECURITY_PASSPHRASE = 'Passphrase'
171−
172− @classmethod
173− def validate_dbus_object(cls, path, state):
174− name = introspection.get_classname_from_path(path)
175− if name == b'Page':
176− if state['objectName'][1] == 'passwdPage':
177− return True
178− return False
179−
180− def _get_option_name(self, formatted_name):
181− # the option name is formatted as follows:
182− # need to read the name between bold tags
183− # '<b>Passcode</b> (4 digits only)'
184− formatted_pattern = re.compile(r'<b>(.*?)</b>.*',
185− re.IGNORECASE | re.DOTALL)
186− name = None
187− match = formatted_pattern.search(formatted_name)
188− if match:
189− name = match.group(1)
190− return name
191−
192− def _get_all_options(self):
193− return self.select_many('OptionSelectorDelegate')
194−
195− def _get_continue_button(self):
196− return self.select_single('StackButton', text='Continue')
197−
198− def _get_back_button(self):
199− return self.select_single('StackButton', text='Back')
200−
201− def _get_selected_option(self):
202− return self.select_single(
203− 'OptionSelectorDelegate', visible='True', selected='True')
204−
205− def get_selected_security_option(self):
206− name_fmt = self._get_selected_option().get_properties()['subText']
207− return self._get_option_name(name_fmt)
208−
209− @autopilot.logging.log_action(logger.info)
210− def select_security_option(self, selected_option):
211− options = self._get_all_options()
212− for option in options:
213− name = self._get_option_name(option.get_properties()['subText'])
214− if name == selected_option:
215− self.pointing_device.click_object(option)
216−
217− @autopilot.logging.log_action(logger.info)
218− def back(self, sim_inserted):
219− self.pointing_device.click_object(self._get_back_button())
220− wizard = get_wizard(self)
221− if sim_inserted:
222− page = wizard.get_languge_page()
223− else:
224− page = wizard.get_sim_page()
225− return page
226−
227− @autopilot.logging.log_action(logger.info)
228− def continue_(self):
229− option = self.get_selected_security_option()
230− self.pointing_device.click_object(self._get_continue_button())
231− wizard = get_wizard(self)
232− if option == self.SECURITY_SWIPE:
233− next_page = wizard.get_wifi_connect_page()
234− else:
235− next_page = wizard.get_password_entry_page()
236− return next_page
237−
238−
239−class PasswordEntryPage(UbuntuUIToolkitCustomProxyObjectBase):
240− """Helper class to interact with the pin entry page"""
241−
242− @classmethod
243− def validate_dbus_object(cls, path, state):
244− name = introspection.get_classname_from_path(path)
245− if name == b'Page':
246− if state['objectName'][1] == 'passwdSetPage':
247− return True
248− return False
249−
250− def _get_pinpad_button(self, char):
251− return self.select_single('PinPadButton', text=char)
252−
253− def _get_continue_button(self):
254− return self.select_single('StackButton', text='Continue')
255−
256− def _get_back_button(self):
257− return self.select_single('StackButton', text='Back')
258−
259− def _get_text_field(self):
260− return self.select_single('QQuickTextInput')
261−
262− @autopilot.logging.log_action(logger.info)
263− def enter_pin(self, pin):
264− for char in pin:
265− self.pointing_device.click_object(self._get_pinpad_button(char))
266− return get_wizard(self).get_confirm_password_page()
267−
268− @autopilot.logging.log_action(logger.info)
269− def enter_text(self, text):
270− self.pointing_device.click_object(self._get_text_field())
271− autopilot.input.Keyboard.create().type(text)
272−
273− @autopilot.logging.log_action(logger.info)
274− def back(self):
275− self.pointing_device.click_object(self._get_back_button())
276− return get_wizard(self).get_password_page()
277−
278− @autopilot.logging.log_action(logger.info)
279− def continue_(self):
280− autopilot.input.Keyboard.create().press_and_release('Enter')
281− return get_wizard(self).get_confirm_password_page()
282−
283−
284−class ConfirmPasswordPage(UbuntuUIToolkitCustomProxyObjectBase):
285− """Helper class to interact with the pin confirmation page"""
286−
287− @classmethod
288− def validate_dbus_object(cls, path, state):
289− name = introspection.get_classname_from_path(path)
290− if name == b'Page':
291− if state['objectName'][1] == 'passwdConfirmPage':
292− return True
293− return False
294−
295− def _get_pinpad_button(self, char):
296− return self.select_single('PinPadButton', text=char)
297−
298− def _get_continue_button(self):
299− return self.select_single('StackButton', text='Continue')
300−
301− def _get_back_button(self):
302− return self.select_single('StackButton', text='Back')
303−
304− def _get_text_field(self):
305− return self.select_single('QQuickTextInput')
306−
307− @autopilot.logging.log_action(logger.info)
308− def enter_pin(self, pin):
309− for char in pin:
310− self.pointing_device.click_object(self._get_pinpad_button(char))
311− return get_wizard(self).get_wifi_connect_page()
312−
313− @autopilot.logging.log_action(logger.info)
314− def enter_text(self, text):
315− self.pointing_device.click_object(self._get_text_field())
316− autopilot.input.Keyboard.create().type(text)
317−
318− @autopilot.logging.log_action(logger.info)
319− def back(self):
320− self.pointing_device.click_object(self._get_back_button())
321− return get_wizard(self).get_password_page()
322−
323− @autopilot.logging.log_action(logger.info)
324− def continue_(self):
325− autopilot.input.Keyboard.create().press_and_release('Enter')
326− return get_wizard(self).get_wifi_connect_page()
327−
328−
329−class WifiConnectPage(UbuntuUIToolkitCustomProxyObjectBase):
330− """Helper class to interact with the Wi-Fi network list page"""
331−
332− @classmethod
333− def validate_dbus_object(cls, path, state):
334− name = introspection.get_classname_from_path(path)
335− if name == b'Page':
336− if state['objectName'][1] == 'wifiPage':
337− return True
338− return False
339−
340− def _get_all_networks(self):
341− try:
342− networks = self.select_many('Standard', objectName='accessPoint',
343− visible='True')
344− except:
345− networks = []
346− return networks
347−
348− def _get_network(self, ssid):
349− return self.wait_select_single(
350− 'Standard', objectName='accessPoint', text=ssid, visible='True')
351−
352− def _get_network_checkbox(self, ssid):
353− return self._get_network(ssid).select_single(
354− 'CheckBox', visible='True')
355−
356− def _get_notification(self, unity):
357− logger.info('Waiting longer for notification object')
358− with override_proxy_timeout(unity, 30):
359− return unity.wait_select_single(
360− Notification, objectName='notification1', visible='True')
361−
362− def _get_back_button(self):
363− return self.wait_select_single(
364− 'StackButton', text='Back', visible='True')
365−
366− def _get_skip_button(self):
367− return self.wait_select_single(
368− 'StackButton', text='Skip', visible='True')
369−
370− def _get_continue_button(self):
371− return self.wait_select_single(
372− 'StackButton', text='Continue', visible='True')
373−
374− def _get_next_button(self):
375− # Since the phone state is unknown, this returns skip||continue
376− # depending on which one is visible
377− buttons = self.select_many('StackButton')
378− for button in buttons:
379− if button.text == "Continue" or button.text == "Skip":
380− return button
381− raise introspection.dbus.StateNotFoundError
382−
383− def is_any_network_checked(self):
384− networks = self._get_all_networks()
385− for network in networks:
386− checkbox = network.select_single('CheckBox', visible='True')
387− if checkbox.get_properties()['checked']:
388− return True
389− return False
390−
391− def is_any_network_found(self):
392− num_neworks = len(self._get_all_networks())
393− return True if num_neworks > 0 else False
394−
395− def is_network_checked(self, ssid):
396− return self._get_network_checkbox(ssid).get_properties()['checked']
397−
398− @autopilot.logging.log_action(logger.info)
399− def select_network(self, unity, ssid):
400− self.pointing_device.click_object(self._get_network_checkbox(ssid))
401− return PasswordNotification(self._get_notification(unity))
402−
403− @autopilot.logging.log_action(logger.info)
404− def advance_page(self):
405− """ Advance the wizard regardless of weather or not
406− continue||skip button is present """
407− self.pointing_device.click_object(self._get_next_button())
408− return get_wizard(self).get_reporting_page()
409−
410− @autopilot.logging.log_action(logger.info)
411− def back(self):
412− self.pointing_device.click_object(self._get_back_button())
413− return get_wizard(self).get_password_page()
414−
415− @autopilot.logging.log_action(logger.info)
416− def skip(self):
417− self.pointing_device.click_object(self._get_skip_button())
418− return get_wizard(self).get_reporting_page()
419−
420− @autopilot.logging.log_action(logger.info)
421− def continue_(self):
422− self.pointing_device.click_object(self._get_continue_button())
423− return get_wizard(self).get_reporting_page()
424−
425−
426−class Notification(UbuntuUIToolkitCustomProxyObjectBase):
427− """Base class for notification objects"""
428− pass
429−
430−
431−class PasswordNotification(Notification):
432− """Helper class to interact with the password entry notification"""
433−
434− def __init__(self, notification):
435− self.notification = notification
436−
437− def _get_connect_button(self):
438− return self.notification.wait_select_single(
439− 'Button', text='Connect', objectName='notify_button0')
440−
441− def _get_cancel_buttoon(self):
442− return self.notification.wait_select_single(
443− 'Button', text='Cancel', objectName='notify_button1')
444−
445− def _get_text_field(self):
446− return self.notification.wait_select_single('TextField')
447−
448− @autopilot.logging.log_action(logger.info)
449− def enter_text(self, text):
450− self._get_text_field().write(text)
451−
452− @autopilot.logging.log_action(logger.info)
453− def connect(self):
454− self.notification.pointing_device.click_object(
455− self._get_connect_button())
456−
457− @autopilot.logging.log_action(logger.info)
458− def cancel(self):
459− self.notification.pointing_device.click_object(
460− self._get_cancel_buttoon())
461−
462−
463−class ReportingPage(UbuntuUIToolkitCustomProxyObjectBase):
464− """Helper class to interact with the reporting page"""
465−
466− @classmethod
467− def validate_dbus_object(cls, path, state):
468− name = introspection.get_classname_from_path(path)
469− if name == b'Page':
470− if state['objectName'][1] == 'reportingPage':
471− return True
472− return False
473−
474− def _get_continue_button(self):
475− return self.select_single('StackButton', text='Continue')
476−
477− def _get_back_button(self):
478− return self.select_single('StackButton', text='Back')
479−
480− @autopilot.logging.log_action(logger.info)
481− def back(self):
482− self.pointing_device.click_object(self._get_back_button())
483− return get_wizard(self).get_wifi_connect_page()
484−
485− @autopilot.logging.log_action(logger.info)
486− def continue_(self):
487− self.pointing_device.click_object(self._get_continue_button())
488− return get_wizard(self).get_finished_page()
489−
490−
491−class FinishedPage(UbuntuUIToolkitCustomProxyObjectBase):
492− """Helper class to interact with the finished page"""
493−
494− @classmethod
495− def validate_dbus_object(cls, path, state):
496− name = introspection.get_classname_from_path(path)
497− if name == b'Page':
498− if state['objectName'][1] == 'finishedPage':
499− return True
500− return False
501−
502− def _get_finish_button(self):
503− return self.wait_select_single(
504− 'StackButton', text='Finish', visible='True')
505−
506− @autopilot.logging.log_action(logger.info)
507− def finish(self):
508− self.pointing_device.click_object(self._get_finish_button())
509− self.wait_until_destroyed()