Пример #1
0
    def _handle_source_code_dialog(self):
        logging.info("Waiting for the source code dialog.")

        def get_source_code_dialog():
            return self.find_control(control_type="Window",
                                     name="main.c",
                                     parent=self.suite.top_window(),
                                     recurse=False)

        wait_for_condition(lambda: get_source_code_dialog().is_visible())
        source_code_dialog = get_source_code_dialog()

        logging.info("Found source code dialog. Checking contents...")
        source_code_edit = self.find_control(control_type="Edit",
                                             name="",
                                             parent=source_code_dialog,
                                             recurse=False)
        self.expect_true(
            '#include <ggp_c/ggp.h>' in source_code_edit.get_line(0),
            "Source code dialog shows the correct file.")

        logging.info("All good. Closing the dialog...")
        close_button = self.find_control(control_type="Button",
                                         name="Close",
                                         parent=source_code_dialog,
                                         recurse=True)
        close_button.click_input()
Пример #2
0
    def _execute(self, process_filter):
        # Finding FilterProcesses/ProcessList occationally throws from within pywinauto. This is not
        # understood. The while loop with the try/except block is a workaround for that.
        while True:
            try:
                filter_edit = self.find_control('Edit', 'FilterProcesses')
                break
            except KeyError:
                logging.info('Find FilterProcesses failed. Try again.')

        while True:
            try:
                process_list = self.find_control('Table', 'ProcessList')
                break
            except KeyError:
                logging.info('Find ProcessList failed. Try again.')

        logging.info('Waiting for process list to be populated')
        wait_for_condition(lambda: process_list.item_count() > 0, 30)
        logging.info('Setting filter text for process list')
        if process_filter:
            filter_edit.set_focus()
            filter_edit.set_edit_text('')
            send_keys(process_filter)
        # Wait for the process to show up - it may still be starting
        wait_for_condition(lambda: process_list.item_count() > 0, 30)

        logging.info('Process selected, continuing to main window...')
        process_list.children(control_type='DataItem')[0].double_click_input()
        _wait_for_main_window(self.suite.application)
        window = self.suite.top_window(True)
        self.expect_eq(window.class_name(), "OrbitMainWindow",
                       'Main window is visible')
        window.maximize()
Пример #3
0
    def _execute(self):
        window = self.suite.top_window()

        logging.info('Start connecting to gamelet.')
        if flags.FLAGS.enable_ui_beta:
            connect_radio = self.find_control('RadioButton', 'ConnectToStadia')
            connect_radio.click_input()

        # Wait for the first data item in the instance list to exist
        # We're not using find_control here because magic lookup enables us to easily wait for the existence of a row
        window.InstanceList.click_input()
        window.InstanceList.DataItem0.wait('exists', timeout=100)
        instance_list = self.find_control('Table', 'InstanceList')
        logging.info('Found %s rows in the instance list', instance_list.item_count())
        self.expect_true(instance_list.item_count() >= 1, 'Found at least one instance')

        window.InstanceList.DataItem0.double_click_input()
        logging.info('Connecting to Instance, waiting for the process list...')

        if flags.FLAGS.enable_ui_beta:
            # In the new UI, use small waits until the process list is active, and then some more for the
            # semi-transparent "loading" Overlay of the tables to disappear...
            wait_for_condition(lambda: self.find_control('Custom', 'ProcessesFrame').is_enabled() is True, 15)
            wait_for_condition(lambda: self.find_control('Table', 'ProcessList').is_active(), 10)
            # TODO(b/177037834): Get rid of this sleep and correctly wait for the overlay to be hidden
            time.sleep(2)
        else:
            wait_for_main_window(self.suite.application)
            window = self.suite.top_window(True)
            self.expect_eq(window.class_name(), "OrbitMainWindow", 'Main window is visible')
        logging.info('Process list ready')
Пример #4
0
    def _execute(self, process_filter):
        if flags.FLAGS.enable_ui_beta:
            filter_edit = self.find_control('Edit', 'FilterProcesses')
            process_list = self.find_control('Table', 'ProcessList')
        else:
            process_data_view = DataViewPanel(self.find_control('Group', 'ProcessesDataView'))
            filter_edit = process_data_view.filter
            process_list = process_data_view.table

        logging.info('Waiting for process list to be populated')
        wait_for_condition(lambda: process_list.item_count() > 0, 30)
        logging.info('Setting filter text for process list')
        if process_filter:
            filter_edit.set_focus()
            filter_edit.set_edit_text('')
            send_keys(process_filter)
        # Wait for the process to show up - it may still be starting
        wait_for_condition(lambda: process_list.item_count() > 0, 30)

        if flags.FLAGS.enable_ui_beta:
            logging.info('Process selected, continuing to main window...')
            process_list.children(control_type='DataItem')[0].double_click_input()
            wait_for_main_window(self.suite.application)
            window = self.suite.top_window(True)
            self.expect_eq(window.class_name(), "OrbitMainWindow", 'Main window is visible')
        else:
            process_list.children(control_type='TreeItem')[0].click_input()
Пример #5
0
 def _wait_and_verify_capture_interrupted(self):
     logging.info("Verifying that the capture was stopped by OrbitService")
     wait_for_condition(lambda: self.find_control(
         'Window', 'Capture interrupted', recurse=False, raise_on_failure=False) is not None,
                        max_seconds=300)
     dialog = self.find_control('Window', 'Capture interrupted')
     self.find_control('Button', 'OK', parent=dialog).click_input()
Пример #6
0
    def _execute(self, filter_strings: str or Iterable[str]):
        if isinstance(filter_strings, str):
            filter_strings = [filter_strings]
        connect_radio = self.find_control('RadioButton', 'LoadCapture')
        connect_radio.click_input()

        filter_capture_files = self.find_control('Edit', 'FilterCaptureFiles')
        succeeded = False
        for filter_string in filter_strings:
            filter_capture_files.set_edit_text(filter_string)

            capture_file_list = self.find_control('Table', 'CaptureFileList')
            try:
                wait_for_condition(lambda: capture_file_list.item_count() > 0,
                                   30)
            except OrbitE2EError:
                continue
            succeeded = True
            capture_file_list.children(
                control_type='DataItem')[0].double_click_input()

            # Unless the file does not exist, Orbit's main window will open and contain the "Loading capture" dialog.
            _wait_for_main_window(self.suite.application)
            # As there is a new top window (Orbit main window), we need to update the top window.
            self.suite.top_window(force_update=True)
            break

        if not succeeded:
            raise OrbitE2EError(
                f'Did not find any capture in filter strings: "{filter_strings}"'
            )
Пример #7
0
    def _execute(self, function_name):
        cell, index = self.find_function_cell(function_name)
        cell.click_input(button='right')
        self.find_context_menu_item('Enable frame track(s)').click_input()

        tree_view = self.find_control('Tree', parent=self._live_tab)
        wait_for_condition(
            lambda: "F" in tree_view.children()[index - 1].window_text())
Пример #8
0
 def _wait_for_capture_completion(self):
     logging.info("Waiting for capture to finalize...")
     wait_for_condition(
         lambda: self.find_control('Window',
                                   'Finalizing capture',
                                   recurse=False,
                                   raise_on_failure=False) is None,
         max_seconds=120)
     logging.info("Capturing finished")
Пример #9
0
 def _execute(self):
     time.sleep(1)
     app_menu = self.suite.top_window().descendants(
         control_type="MenuBar")[1]
     app_menu.item_by_path("File->End Session").click_input()
     wait_for_condition(
         lambda: self.suite.application.top_window().class_name() ==
         "orbit_session_setup::SessionSetupDialog", 30)
     self.suite.top_window(force_update=True)
Пример #10
0
    def _execute(self):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        self._load_presets()
        wait_for_condition(lambda: self._try_verify_functions_are_hooked)

        Capture().execute(self.suite)

        logging.info('Verifying function call counts')
        VerifyFunctionCallCount(function_name='DrawFrame', min_calls=30, max_calls=3000).execute(self.suite)
        VerifyFunctionCallCount(function_name='GgpIssueFrameToken', min_calls=30, max_calls=3000).execute(self.suite)
Пример #11
0
    def _execute(self, module_search_string: str, expect_loaded: bool = True):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        logging.info('Start verifying module %s is %s.', module_search_string,
                     "loaded" if expect_loaded else "not loaded")
        modules_dataview = DataViewPanel(self.find_control("Group", "ModulesDataView"))
        wait_for_condition(lambda: modules_dataview.get_row_count() > 0, 100)
        modules_dataview.filter.set_focus()
        modules_dataview.filter.set_edit_text('')
        send_keys(module_search_string)
        wait_for_condition(lambda: modules_dataview.get_row_count() > 0)
        self.expect_true('*' in modules_dataview.get_item_at(0, 0).texts()[0], 'Module is loaded.')
Пример #12
0
 def _execute(self):
     logging.info('Select next project')
     project_combo_box = self.find_control(name='ProjectSelectionComboBox')
     # wait until loading is done
     wait_for_condition(lambda: project_combo_box.is_enabled() is True, 25)
     project_combo_box.click_input()
     logging.info('Found and opened project combo box, sending down arrow and enter')
     send_keys('{DOWN}{ENTER}')
     # After project changing, loading takes place. Wait until the overlay is hidden
     wait_for_condition(
         lambda: self.find_control('Group', 'InstanceListOverlay', raise_on_failure=False) is
         None, 100)
     logging.info('Successfully selected next project')
Пример #13
0
    def _execute(self):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        functions_dataview = DataViewPanel(self.find_control("Group", "FunctionsDataView"))
        logging.info('Waiting for function list to be populated...')
        wait_for_condition(lambda: functions_dataview.get_row_count() > 0, 100)
        functions_dataview.filter.set_focus()
        functions_dataview.filter.set_edit_text('')
        functions_dataview.get_item_at(0, 0).click_input('left')
        # Hit Ctrl+a to select all functions.
        send_keys('^a')
        functions_dataview.get_item_at(0, 0).click_input('right')
        self.find_context_menu_item('Unhook').click_input()
Пример #14
0
    def _execute(self, module_search_string: str):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        logging.info('Start loading symbols for module %s',
                     module_search_string)
        modules_dataview = DataViewPanel(
            self.find_control("Group", "ModulesDataView"))

        logging.info('Waiting for module list to be populated...')
        wait_for_condition(lambda: modules_dataview.get_row_count() > 0, 100)

        logging.info('Filtering and loading')
        modules_dataview.filter.set_focus()
        modules_dataview.filter.set_edit_text('')
        send_keys(module_search_string)
        wait_for_condition(lambda: modules_dataview.get_row_count() == 1)
        modules_dataview.get_item_at(0, 0).click_input('right')

        self.find_context_menu_item('Load Symbols').click_input()

        logging.info('Waiting for * to indicate loaded modules')

        wait_for_condition(
            lambda: modules_dataview.get_item_at(0, 4).texts()[0] == "*", 100)

        functions_dataview = DataViewPanel(
            self.find_control("Group", "FunctionsDataView"))
        wait_for_condition(lambda: functions_dataview.get_row_count() > 0)
Пример #15
0
    def _execute(self):
        instance_list = self.find_control('Table', 'InstanceList')
        refresh_button = self.find_control('Button', 'RefreshInstanceList')
        logging.info('Found instance list and refresh button, clicking refresh button')
        refresh_button.click_input()

        instance_list_overlay = self.find_control(None, 'InstanceListOverlay')
        self.expect_true(instance_list_overlay.is_visible(), "Instance overlay is visible")
        logging.info('Found InstanceListOverlay and its visible')

        wait_for_condition(
            lambda: self.find_control('Group', 'InstanceListOverlay', raise_on_failure=False) is
            None, 100)
        logging.info('Loading done, overlay is hidden')
        self.expect_true(_get_number_of_instances_in_list(self) >= 1, 'Found at least one instance')
Пример #16
0
    def _execute(self):
        instance_list_overlay = self.find_control('Group', 'InstanceListOverlay')
        self.expect_true(instance_list_overlay.is_visible(), "Instance overlay is visible")
        disconnect_button = self.find_control('Button', 'Disconnect')
        logging.info(
            'Instance overlay visible and Disconnect button was found; performing disconnect from the instance'
        )
        disconnect_button.click_input()

        logging.info('Waiting for instance overlay to dissapear')
        wait_for_condition(lambda: self.find_control(
            'Group', 'InstanceListOverlay', raise_on_failure=False) is None)
        logging.info('Loading done, overlay is hidden')
        self.expect_true(_get_number_of_instances_in_list(self) >= 1, 'Found at least one instance')
        wait_for_condition(lambda: self.find_control(
            'Group', 'ProcessListOverlay', raise_on_failure=False) is None)
Пример #17
0
    def _execute(self, filter_string: str = "", expected_track_count=None):
        """
        :param filter_string: The string to be entered in the filter edit. Note that pywinauto's `keyboard.send_keys` is
            used, so certain special characters need to be escaped by enclosing them in {}.
        :param expected_track_count: If not None, this test will verify the amount of tracks after filtering
        """
        toolbar = self.find_control("ToolBar", "CaptureToolBar")
        track_filter = self.find_control("Edit", "FilterTracks", parent=toolbar)

        logging.info("Setting track filter text: '{}'".format(filter_string))
        track_filter.set_focus()
        track_filter.set_edit_text('')
        # Using send_keys instead of set_edit_text directly because set_edit_text ignores the wait timings...
        keyboard.send_keys(filter_string)

        if expected_track_count is not None:
            wait_for_condition(lambda: len(self._find_tracks()) == expected_track_count)
Пример #18
0
    def _handle_file_not_found_message_box(self):
        logging.info('Waiting for message box')

        def get_message_box():
            return self.find_control(control_type="Window",
                                     name="Source code file not found",
                                     parent=self.suite.top_window(),
                                     recurse=False)

        wait_for_condition(lambda: get_message_box().is_visible())

        logging.info('Message box found - Clicking "Choose file..."')
        choose_file_button = self.find_control(control_type="Button",
                                               name="Choose file...",
                                               parent=get_message_box(),
                                               recurse=True)
        choose_file_button.click_input()
Пример #19
0
    def _execute(self, function_name):
        cell, index = self.find_function_cell(function_name)
        cell.click_input(button='right')
        self.find_context_menu_item('Enable frame track(s)').click_input()

        tree_view = self.find_control('Tree', parent=self._live_tab)
        wait_for_condition(
            lambda: "F" in tree_view.children()[index - 1].window_text())

        logging.info("Verifying existence of track in the Capture window")
        match_tracks = MatchTracks(
            expected_names=["Frame track based on %s" % function_name],
            allow_additional_tracks=True)
        match_tracks.execute(self.suite)

        check_timers = CheckTimers(track_name_contains=function_name)
        check_timers.execute(self.suite)
Пример #20
0
    def _execute(self, project_name: str):
        logging.info('Select project with name ' + project_name)
        project_combo_box = self.find_control(name='ProjectSelectionComboBox')
        # wait until loading is done
        wait_for_condition(lambda: project_combo_box.is_enabled() is True, 25)
        project_combo_box.click_input()

        project = self.find_combo_box_item(text=project_name)
        logging.info('Expanded project combo box and found entry ' + project_name)
        project.click_input()
        # After project changing, loading takes place. Wait until the overlay is hidden
        wait_for_condition(
            lambda: self.find_control('Group', 'InstanceListOverlay', raise_on_failure=False) is
            None, 100)
        logging.info('Successfully selected project ' + project_name +
                     'and waited until loading is done')
        self.expect_true(_get_number_of_instances_in_list(self) >= 1, 'Found at least one instance')
Пример #21
0
    def _provoke_goto_source_action(self, function_search_string: str):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        logging.info('Start showing source code for function {}'.format(function_search_string))
        functions_dataview = DataViewPanel(self.find_control("Group", "FunctionsDataView"))

        logging.info('Waiting for function list to be populated...')
        wait_for_condition(lambda: functions_dataview.get_row_count() > 0, 100)

        logging.info('Filtering functions')
        functions_dataview.filter.set_focus()
        functions_dataview.filter.set_edit_text('')
        send_keys(function_search_string)
        wait_for_condition(lambda: functions_dataview.get_row_count() == 1)
        functions_dataview.get_item_at(0, 0).click_input('right')

        logging.info('Click on "Go to Source code"')
        self.find_context_menu_item('Go to Source code').click_input()
Пример #22
0
    def _execute(self, capture_file_path: str, expect_fail=False):
        # Lets ensure that we are actually in the connection window, as this test might also be executed after the
        # main window has been opened.
        _wait_for_connection_window(self.suite.application)
        self.suite.top_window(force_update=True)
        logging.info('Starting to load a capture.')
        connect_radio = self.find_control('RadioButton', 'LoadCapture')
        connect_radio.click_input()

        others_button = self.find_control('Button', '...')
        others_button.click_input()

        file_name_edit = self.find_control('Edit', 'File name:')

        if not os.path.isabs(capture_file_path):
            automation_tests_dir = os.path.join(os.path.dirname(__file__),
                                                '..')
            capture_file_path = os.path.join(automation_tests_dir,
                                             capture_file_path)

        file_name_edit.set_edit_text(capture_file_path)

        logging.info(f'Trying to load capture file: {capture_file_path}')
        start_session_button = self.find_control('Button', 'Start Session')
        start_session_button.click_input()

        # Unless the file does not exist, Orbit's main window will open next and contain the "Loading capture" dialog.
        _wait_for_main_window(self.suite.application)
        # As there is a new top window (Orbit main window), we need to update the top window.
        self.suite.top_window(force_update=True)

        logging.info("Waiting for capture to load...")
        wait_for_condition(lambda: self.find_control(
            'Window', 'Loading capture', raise_on_failure=False) is None,
                           max_seconds=120)
        logging.info("Capture Loading finished")

        if expect_fail:
            self.find_control('Window', 'Error while loading capture')
            ok_button = self.find_control('Button', 'OK')
            ok_button.click_input()
Пример #23
0
    def _execute(self):
        logging.info('Starting "All Instances" checkbox test.')
        # First wait until all loading is done.
        wait_for_condition(
            lambda: self.find_control('Group',
                                      'InstanceListOverlay',
                                      raise_on_failure=False) is None, 100)
        check_box = self.find_control('CheckBox', 'AllInstancesCheckBox')
        logging.info('Found checkbox')

        instance_count = _get_number_of_instances_in_list(self)

        check_box.click_input()
        logging.info(
            'Clicked All Instances check box, waiting until loading is done')
        wait_for_condition(
            lambda: self.find_control('Group',
                                      'InstanceListOverlay',
                                      raise_on_failure=False) is None, 100)
        self.expect_true(
            instance_count <= _get_number_of_instances_in_list(self),
            'Instance list contains at least same amount of instances as before.'
        )
        logging.info('Loading successful, instance number increased')

        check_box.click_input()
        wait_for_condition(
            lambda: self.find_control('Group',
                                      'InstanceListOverlay',
                                      raise_on_failure=False) is None, 100)
        self.expect_true(
            _get_number_of_instances_in_list(self) >= 1,
            'Instance list contains at least one instance')
        logging.info('Second click on check box successful')
Пример #24
0
    def _execute(self):
        window = self.suite.top_window()

        logging.info('Start connecting to gamelet.')
        connect_radio = self.find_control('RadioButton', 'ConnectToStadia')
        connect_radio.click_input()

        # Wait for the first data item in the instance list to exist
        # We're not using find_control here because magic lookup enables us to easily wait for the existence of a row
        window.InstanceList.click_input()
        window.InstanceList.DataItem0.wait('exists', timeout=100)
        self.expect_true(
            _get_number_of_instances_in_list(self) >= 1,
            'Found at least one instance')

        window.InstanceList.DataItem0.double_click_input()
        logging.info('Connecting to Instance, waiting for the process list...')

        # In the new UI, use small waits until the process list is active, and then some more for the
        # semi-transparent "loading" Overlay of the tables to disappear
        wait_for_condition(
            lambda: self.find_control('Custom', 'ProcessesFrame').is_enabled()
            is True, 25)
        wait_for_condition(
            lambda: self.find_control('Table', 'ProcessList').is_active(), 10)
        # This is a bit annoying, but since the overlay is invisible when loading is done, we need to check for
        # absence of the overlay... not sure if there is a better way
        wait_for_condition(lambda: self.find_control(
            'Group', 'ProcessListOverlay', raise_on_failure=False) is None)
        logging.info('Process list ready')
Пример #25
0
    def _handle_file_open_dialog(self):
        logging.info("Waiting for File Open Dialog")

        def get_file_open_dialog():
            return self.find_control(control_type="Window",
                                     name_contains="Choose ",
                                     parent=self.suite.top_window(),
                                     recurse=False)

        wait_for_condition(lambda: get_file_open_dialog().is_visible())
        file_open_dialog = get_file_open_dialog()
        logging.info(
            "File Open Dialog is now visible. Looking for file edit...")

        logging.info("File Edit was found. Entering file path...")
        file_edit = self.find_control(control_type="Edit",
                                      name="File name:",
                                      parent=file_open_dialog,
                                      recurse=True)
        file_edit.set_focus()
        file_edit.set_edit_text('')

        # The test needs the source code file "main.c" from the hello_ggp example
        # to be available on the machine. On the E2E test infrastructure the example
        # project will be extracted to C:\build\scratch\test\hello_ggp.
        #
        # To run this test in developer machines, the patch can be overwritten by a
        # command line flag. Keep in mind, it needs to be an absolute path, which
        # is understood by the Windows file open dialog, when pasted into the filename
        # field.
        send_keys(flags.FLAGS.source_code_file)

        logging.info("Clicking the open button...")
        file_open_button = self.find_control(control_type="Button",
                                             name="Open",
                                             parent=file_open_dialog,
                                             recurse=False)
        file_open_button.click_input()
Пример #26
0
    def _execute(self, module_search_string: str, expect_fail=False):
        """
        :param module_search_string: String to enter in the module filter field, the first entry in the list of
            remaining modules will be loaded
        :param expect_fail: If True, the test will succeed if loading symbols results in an error message
        """
        _show_symbols_and_functions_tabs(self.suite.top_window())

        logging.info('Start loading symbols for module %s',
                     module_search_string)
        modules_dataview = DataViewPanel(
            self.find_control("Group", "ModulesDataView"))

        logging.info('Waiting for module list to be populated...')
        wait_for_condition(lambda: modules_dataview.get_row_count() > 0, 100)

        logging.info('Filtering and loading')
        modules_dataview.filter.set_focus()
        modules_dataview.filter.set_edit_text('')
        send_keys(module_search_string)
        wait_for_condition(lambda: modules_dataview.get_row_count() == 1)
        modules_dataview.get_item_at(0, 0).click_input('right')

        self.find_context_menu_item('Load Symbols').click_input()

        logging.info('Waiting for * to indicate loaded modules')

        # The Loading column which should get filled with the "*" is the first column (0)
        if expect_fail:
            wait_for_condition(lambda: _find_and_close_error_dialog(
                self.suite.top_window()) is not None)
        else:
            wait_for_condition(
                lambda: modules_dataview.get_item_at(0, 0).texts()[0] == "*",
                100)

        VerifySymbolsLoaded(symbol_search_string=module_search_string,
                            expect_loaded=not expect_fail).execute(self.suite)
Пример #27
0
    def _execute(self, function_search_string):
        _show_symbols_and_functions_tabs(self.suite.top_window())

        logging.info('Hooking function based on search "%s"', function_search_string)
        functions_dataview = DataViewPanel(self.find_control("Group", "FunctionsDataView"))

        logging.info('Waiting for function list to be populated...')
        wait_for_condition(lambda: functions_dataview.get_row_count() > 0, 100)

        logging.info('Filtering and hooking')
        functions_dataview.filter.set_focus()
        functions_dataview.filter.set_edit_text('')
        send_keys(function_search_string)
        wait_for_condition(lambda: functions_dataview.get_row_count() == 1)
        functions_dataview.get_item_at(0, 0).click_input('right')

        self.find_context_menu_item('Hook').click_input()
        wait_for_condition(lambda: '✓' in functions_dataview.get_item_at(0, 0).texts()[0])
Пример #28
0
def _wait_for_connection_window(application: Application):
    wait_for_condition(lambda: application.top_window().class_name() ==
                       "orbit_session_setup::SessionSetupDialog",
                       max_seconds=30)
Пример #29
0
def _wait_for_main_window(application: Application):
    wait_for_condition(
        lambda: application.top_window().class_name() == "OrbitMainWindow",
        max_seconds=30)