Example #1
0
    def do_compare(self, str_arg):
        """
        compare a snapshot file with an expected image file(by default in PNG format). this usually follows
        a takesnapshot step in a testcase.
        if the snapshot file is identical with the expected target file, return True.
        otherwise return False.

        (Note: UI checking depends on various external factors, for example, different screen brightness value would
        make the snapshots different, leading to unexpected compare results. therefore comparing snapshots is no longer
        recommended. If you insist on automated pixel-level UI testcases, make sure you have these factors well managed)

        format: compare <live captured snapshot> <target prepared snapshot>
        e.g. 'setup' is a predefined directory to hold prepared snapshots, you may define your own directories.
        takesnapshot app_drawer_icon_on_screen.png
        compare app_drawer_icon_on_screen.png setup/designed_app_drawer_icon.png
        """
        arg = validateString(str_arg)
        source, target = arg.split(' ', 1)
        if os.path.isfile(source):
            # Mar 27 @swang: if target file doesn't exist, copy source file to setup directory for later test
            # 2015-08-27: decided to go to fail path
            if not os.path.isfile(target):
                # copy(source, target)
                self.resultFlag = False
                raise ValueError('COMPARE FAILED: target file not found.')
            # if not self.__compareImage(source, target):
            if not filecmp.cmp(source, target):
                printLog(self.threadName + 'COMPARE FAILED: source file and target file DIFFER!', logging.WARNING)
                self.resultFlag = False
        else:
            self.resultFlag = False
            raise ValueError('COMPARE FAILED: source file not found.')
Example #2
0
    def do_comparex(self, str_arg):
        """
        compare a snapshot file with a set of expected files
        if the snapshot file is identical with one of the files, return True.
        otherwise return False.

        """
        arg = validateString(str_arg)
        file1, fileset = arg.split(' ', 1)
        if len(fileset) == 0:
            self.resultFlag = False
            raise ValueError('Bad parameter. Please check your script.')
        if not os.path.isfile(file1):
            self.resultFlag = False
            raise ValueError(file1 + ' not exist, Please check your script.')
        # f_list=[pp1 for pp1 in fileset.split(' ') if pp1!='']
        for fn in fileset.split(' '):
            # print file1, f2
            if not os.path.isfile(fn):
                self.resultFlag = False
                raise ValueError(fn + ' not exist, Please check your script.')
            if self.__compareImage(file1, fn):
                self.resultFlag = True
                print('[Found match. %s and %s are identical.]' % (file1, fn))
                return
        print('[No match found.]')
        self.resultFlag = False
Example #3
0
 def do_takesnapshot(self, str_arg):
     """
     take snapshot of the full screen and save it to the file with the given filename
     format: takesnapshot [filename]
     e.g. takesnapshot a1.png
     @param str_arg: filename (string)
     """
     img = None
     fname = validateString(str_arg)
     try:
         # self.adbc.wake()
         printLog(self.threadName + 'taking snapshot (0,50,%d,%d) ...' %
                  (self.scn_width, self.scn_height))
         img = self.adbc.takeSnapshot(reconnect=True)
         # PIL code
         img = img.crop((0, 50, self.scn_width, self.scn_height))
         img.save(fname, SNAPSHOT_IMAGE_FORMAT)
         # if self.scn_width>SNAPSHOT_WIDTH:
         #    self.compressImage(fname)
         #    os.remove(fname)
         #    im.save(fname)
         printLog(self.threadName + 'snapshot saved as %s' % fname)
     except EnvironmentError:
         self.resultFlag = False
         if DEBUG:
             traceback.print_exc()
     finally:
         img = None
Example #4
0
 def do_checkTextInclusion(self, str_arg):
     """
     check if the given text is included in the message of the specified resource id. (2015-07-22)
     e.g. checkTextInclusion id/icon_descriptive_text icon to see your Zones.
     """
     # printLog(self.threadName + "[running command 'checkTextInclusion %s']" % str_arg)
     arg = validateString(str_arg)
     ret = arg.split(' ', 1)
     if len(ret) == 1:
         self.resultFlag = False
         raise ValueError('Lacking argument of checkTextInclusion.')
     if iDevice.dump_view:
         self.__dumpview()
     try:
         viewId = ret[0].strip()
         printLog("finding view by id %s ..." % viewId, logging.DEBUG)
         tmpView = self.vc.findViewById(viewId)
         if not tmpView:
             self.resultFlag = False
             printLog(self.threadName + '%s is not visible.' % viewId, logging.ERROR)
             return
         else:
             # get element text, and compare it with the given text value
             tempText = tmpView.getText()
             printLog(self.threadName + '[text on screen: %s]' % tempText)
             if not ret[1].strip() in tempText.strip():
                 self.resultFlag = False
     except Exception, e:
         self.resultFlag = False
         printLog(self.threadName + 'Exception in do_check: %s' % e.message, logging.ERROR)
Example #5
0
    def do_swipe(self, str_arg=''):
        """
        swipe the screen in the given direction (left, right, up or down)
        e.g. swipe left
        @param str_arg: the direction argument (string)
        @return: result (boolean)
        """
        direction = validateString(str_arg)
        if direction == 'left':
            arg = '(%d,%d) (%d,%d)' % (
                int(self.scn_width * 0.9), int(self.scn_height * 0.5), int(self.scn_width * 0.1),
                int(self.scn_height * 0.5))
        elif direction == 'right':
            arg = '(%d,%d) (%d,%d)' % (
                int(self.scn_width * 0.1), int(self.scn_height * 0.5), int(self.scn_width * 0.9),
                int(self.scn_height * 0.5))
        elif direction == 'up':
            arg = '(%d,%d) (%d,%d)' % (int(self.scn_width * 0.5), self.scn_height - 200, int(self.scn_width * 0.5), 0)
        elif direction == 'down':
            arg = '(%d,%d) (%d,%d)' % (int(self.scn_width * 0.5), 100, int(self.scn_width * 0.5), self.scn_height)
        else:
            self.resultFlag = False
            raise ValueError("do_swipe: bad argument.")

        return self.do_drag(arg)
Example #6
0
    def do_check(self, str_arg):
        """
        check id existency(not visibility! sometimes a view does not show up, e.g. widgets in the other launcher page),
        if text is given, check if it is identical with what shows on the screen.
        2015-08-26: merged the checkchild method with this one.

        format: check <id>[(child path id sequence)] [text]
        Note: DO NOT INCLUDE SPACE IN THE CHILD PATH

        e.g. check id/title_text Personalize Homescreen
        e.g. check id/parent(4,3,2,2) my text is text

        @param str_arg: it takes two formats:
            1. The target id, and text to be compared (optional)
            2. The unique parent id, the path from parent to target child view, the target text (optional)
        @return boolean
        """
        # printLog(self.threadName + "[running command 'check %s']" % str_arg)
        str_arg = validateString(str_arg)

        # parse the args
        args = str_arg.split(' ', 1)
        viewId = args[0].strip()
        if len(args) < 2:
            target_text = ''
        else:
            target_text = args[1]
        try:
            # get the target view
            tv = self.__getView(viewId)
            if tv:
                if DEBUG:
                    printLog(self.threadName + 'Found target view %s.' % viewId, logging.DEBUG)
                if len(target_text) > 0:
                    # get element text, and compare it with the given text value
                    # tmpView=self.vc.findViewWithText(ret[1].strip())
                    tempText = tv.getText()
                    printLog(self.threadName + '[Text on screen: %s, expected text: %s]' % (tempText, target_text),
                             logging.DEBUG)
                    if tempText == target_text:
                        # printLog('CHECK PASS! Text match.', logging.DEBUG)
                        self.resultFlag = True
                    else:
                        printLog(self.threadName + 'CHECK FAILED! Text not match!', logging.ERROR)
                        self.resultFlag = False
            else:
                printLog(self.threadName + 'Target view %s not found.' % viewId, logging.ERROR)
                self.resultFlag = False

        except Exception, e:
            self.resultFlag = False
            printLog(self.threadName + 'Exception in do_check: %s' % e.message, logging.ERROR)
            if DEBUG:
                traceback.print_exc()
Example #7
0
 def do_type(self, str_arg):
     """
     type the given string in the screen
     e.g. type I'm OK
     @param str_arg: the text to type (string)
     @return: result (boolean)
     """
     try:
         self.adbc.type(validateString(str_arg))
     except Exception, e:
         printLog(self.threadName + 'TYPE FAILED: %s' % e.message)
         self.resultFlag = False
Example #8
0
 def do_start(self, str_arg):
     """
     start an activity (openActivity() in C{Android} can do the same thing)
     e.g. start com.android.dial
     @param str_arg: activity (string)
     """
     try:
         # self.adbc.startActivity(validateString(str_arg))
         # the above approach failed in unittest complaining device is offline, weird...
         return self.runAdbCmd('shell am start -n', validateString(str_arg))
     except RuntimeError:
         self.resultFlag = False
         if DEBUG:
             traceback.print_exc()
Example #9
0
    def do_clickchild(self, str_arg):
        """
        [obsoleted]
        This method is merged with 'click'. Kept here for backward compatibility.
        click a certain child for one unique ID
        use it while there are multiple same name ID, but there is one unique root parent

        format: clickchild <root node ID> <child branch id list>
        e.g. clickchild id/root (0,1)

        2015-08-27: merged into click method, kept here for backward compatibility
        2015-08-11: using AVC will no longer require including the offset parameter
        ---------------------------------------------------------------------------------
        Below instruction is for Monkeyrunner which is DEPRECATED.
        2015-05-06: updated to include the offset parameter so that the tool can
        click on the right view center position

        format: clickchild <root node ID> <child branch id list> <root node relative position offset to screen>
        e.g. clickchild id/root (0,1) (18,338)
        """
        # printLog(self.threadName + "[running 'clickchild %s']" % str_arg)
        # arg validation
        arg = validateString(str_arg)
        if iDevice.dump_view:
            self.__dumpview()
        try:
            # to avoid '  ' two spaces case
            # suppose string like: id/button1 (5,2,3,3,3) (0,50)
            # i = arg.index(' ')
            # ids = arg[0:i]
            # arg = arg[i + 1:].strip()
            # seqs = arg[1:-1].split(',')
            arg_list = arg.split(' ')

            if len(arg_list) == 2:
                printLog(self.threadName + 'do_clickChild: using default offset.')
                node_id, seqs = arg_list
                self.__clickChildView(node_id, seqs[1:-1].split(','))
            elif len(arg_list) == 3:
                # node_id, seqs, offset = arg_list
                # self.__clickChildView(node_id, seqs[1:-1].split(','), self.__getPointXY(offset.strip()))
                raise ValueError("using AVC will NO LONGER require including the offset parameter.")
            else:
                raise ValueError('missing argument.')
        except ValueError:
            printLog(self.threadName + 'do_clickChild: click failed', logging.ERROR)
            traceback.print_exc()
            self.resultFlag = False
            time.sleep(1)
Example #10
0
    def do_click(self, str_arg):
        """
        click by a view id(or parent id with child path), a point in (x, y) coordinates,
        or the text in a view (text box, button etc.).

        2015-05-14: modified to include the way to click by text
        http://www.softteco.com/blog/android-decoding-click-low-level-event/
        2015-08-27: merged the clickchild method

        format: click <view_id>|<view_id>(child path id sequence)|text/<target text>|(x,y)
        e.g. click id/button
        e.g. click id/card_holder_id(2,0,0,0,0,1)
        e.g. click text/Show me
        e.g. click (100,200)

        """
        arg = validateString(str_arg)
        for tmp in range(REPEAT_TIMES_ON_ERROR):
            try:
                if arg.startswith('('):
                    point = self.__getPointXY(arg)
                    printLog(self.threadName + '[clicking point %s...]' % arg, logging.DEBUG)
                    self.adbc.touch(point[0], point[1], "DOWN_AND_UP")
                else:
                    if "/" not in arg:
                        raise ValueError('bad argument of do_click().')
                    # get the target view
                    tv = self.__getView(arg)
                    if tv:
                        if DEBUG:
                            printLog('Found view %s.' % arg, logging.DEBUG)
                            printLog(self.threadName + 'tinyStr: %s' % tv.__tinyStr__(), logging.DEBUG)
                            # printLog(self.threadName + 'position and size: {}'.format(tv.getPositionAndSize()),
                            #          logging.DEBUG)
                        printLog(self.threadName + '[clicking id %s...]' % arg, logging.DEBUG)
                        tv.touch()
                    else:
                        printLog('Target view %s not found.' % arg, logging.ERROR)
                        self.resultFlag = False
                return
            except Exception, e:
                printLog(self.threadName + 'the %dst try failed due to %s, will retry.' % (tmp, e.message),
                         logging.ERROR)
                # self.reconnect()
                time.sleep(1)
                continue
Example #11
0
    def do_keypress(self, str_arg):
        """
        press a key
        e.g. keypress KEYCODE_HOME

        check http://developer.android.com/reference/android/view/KeyEvent.html for the full list
        KEYCODE_DPAD_LEFT 21
        KEYCODE_DPAD_RIGHT 22
        KEYCODE_DPAD_UP 19
        KEYCODE_DPAD_DOWN 20
        KEYCODE_TAB 61
        KEYCODE_ENTER 66
        ...
        @param str_arg: the keycode

        """
        arg = validateString(str_arg)
        self.adbc.press(arg, "DOWN_AND_UP")
Example #12
0
    def do_checkchild(self, str_arg):
        """
        [obsoleted] This method is merged with 'check'. Kept here for backward compatibility.
        This is an extension to method 'check' to handle child elements whose id is not unique within the layout.

        @param str_arg: the unique parent ID, the path from parent to target child view, the target text
        @return: none, but resultFlag indicate the result, yes or not

        e.g.  checkChild id/parent (4,3,2,2) my text is text
        note:  the final text string is optinal. If not specified,  will check if the child exists
        """
        arg = validateString(str_arg).strip()
        try:
            # to avoid '  ' two spaces case
            # suppose string like: id/text1 (5,4,2,3,3,3) textfield
            i = arg.index(' ')
            ids = arg[0:i]
            arg = arg[i + 1:].strip()
            if iDevice.dump_view:
                self.__dumpview()
            if ' ' in arg:
                i = arg.index(' ')
                seqs = arg[1:i - 1].split(',')
                arg = arg[i + 1:].strip()
                texts = arg
                target_text = self.__getChildViewText(ids, seqs)
                printLog(self.threadName + '[text on screen: %s]' % target_text)
                self.resultFlag = True
                if texts != '':
                    if texts == target_text:
                        self.resultFlag = True
                    else:
                        self.resultFlag = False
            else:
                seqs = arg[1:-1].split(',')
                if self.__getChildView(ids, seqs):
                    self.resultFlag = True
                else:
                    self.resultFlag = False
        except Exception, e:
            # gbk problem
            self.resultFlag = False
            traceback.print_exc()
            printLog(self.threadName + 'Exception in do_checkchild: %s' % e.message, logging.ERROR)
Example #13
0
 def do_assert(self, str_arg):
     """
     do assertion to the result of previous step to determine if the step passed or failed.
     e.g. if you expect the result of previous text check match, then write "assert true" following "check id/xx xxx"
     @param str_arg: true of false
     @return: none
     """
     arg = validateString(str_arg)
     if arg not in ('true', 'false'):
         self.resultFlag = False
         raise ValueError('Bad parameter.')
     if (arg == 'true' and self.resultFlag) or (arg == 'false' and not self.resultFlag):
         printLog(self.threadName + '[ASSERT PASS]', logging.DEBUG)
         self.resultFlag = True
     else:
         # printLog(self.threadName+'[status=%s]' % self.resultFlag)
         printLog(self.threadName + '[ASSERT FAIL!]', logging.DEBUG)
         self.resultFlag = False
         raise AssertionError()
Example #14
0
    def do_takesnapshotx(self, str_arg):
        """
        take a snapshot of the given area and save it to the file with the given filename

        format: takesnapshotx (x1,y1) (x2,y2) [filename]
        e.g. takesnapshotx (0,0) (400,400) a2.png
        @param str_arg: arguments and filename (string)
        """
        # img = None
        fname = ""
        args = validateString(str_arg)
        # print args
        try:
            pa = re.compile('^(\(\d*,\d*\))\D*(\(\d*,\d*\))(.+)$')
            matches = pa.search(args.strip()).groups()
            # print matches
            point1 = self.__getPointXY(matches[0])
            point2 = self.__getPointXY(matches[1])
            fname = matches[2].strip()
        except AttributeError, e:
            printLog(self.threadName + "AttributeError: %s" % e.message, logging.ERROR)
            raise ValueError('do_takesnapshotx: Bad parameter.')
Example #15
0
    def do_longpress(self, str_arg):
        """
        long press a UI element by view id, a point or text
        format: 1. longpress <view id> [seconds]
                2. longpress <parent view id>(child path) [seconds]
                3. longpress text/<target text> [seconds]
                4. longpress (100,200) [seconds]

        2015-08-27: add format2 support
        2014-02-17: initial version
        @param str_arg: auguments
        """
        arg = validateString(str_arg)
        # if arg.startswith(r'('):
        # raise ValueError('Bad argument, You may want to use longpress2 with coordinates as auguments.')
        x = 0
        y = 0
        seconds = 2000
        try:
            if arg.startswith(r'('):
                point, sec = arg.split(')')
                if len(sec) > 0:
                    seconds = int(validateDigit(sec))
                x, y = self.__getPointXY(point + ')')
                if not isinstance(x, int):
                    raise ValueError('bad x type: not int.')
            elif arg.startswith('id') or arg.startswith('text'):
                if ' ' in arg:
                    view_id, sec = arg.split(' ')
                    if len(sec) > 0:
                        seconds = int(validateDigit(sec.strip()))
                else:
                    view_id = arg
                # get the target view
                tv = self.__getView(view_id)
                if tv:
                    if DEBUG:
                        printLog('Found view %s.' % arg, logging.DEBUG)
                        print tv.__tinyStr__()
                        print tv.getPositionAndSize()
                    x, y = tv.getCenter()
                    if not isinstance(x, int):
                        raise ValueError('Bad center coordinate: not int.')
                else:
                    printLog('Target view %s not found.' % arg, logging.ERROR)
                    self.resultFlag = False
                    return
            else:
                raise ValueError('bad argument in longpress().')
            # perform long press
            if self.adbc.getSdkVersion() >= 19:
                printLog(self.threadName + "[running longTouch %s, %s...]" % (x, y))
                self.adbc.longTouch(x, y, seconds)

            # solution for API level > 17:
            # http://stackoverflow.com/questions/11142843/how-can-i-use-adb-to-send-a-longpress-key-event
            elif self.adbc.getSdkVersion() > 17:
                cmd = 'adb shell input touchscreen swipe %s %s %s %s %d' % (x, y, x, y, seconds)
                printLog(self.threadName + "[running cmd %s...]" % cmd)
                if call(cmd, shell=True) != 0:
                    printLog("LONGPRESS FAILED: Failed to execute command '%s'." % cmd, logging.ERROR)
                    self.resultFlag = False
            else:
                printLog("LONGPRESS FAILED: API < 18 is not supported yet.", logging.ERROR)
                self.resultFlag = False

        except Exception, e:
            printLog(self.threadName + 'LONGPRESS FAILED:%s' % e.message, logging.WARNING)
            traceback.print_exc()
            self.resultFlag = False