appuim+python常遇到的问题

appuim+python常遇到的问题

'''
appuim使用过程中常见的问题
'''
import time

一、内嵌H5定位
    1/在web自动化中我们会遇见frame的问题,在遇见这些内嵌的标签后我们需要做的就是切换窗口,
    那么在app自动化测试也有类似的情况就是我们经常看见的内嵌html,在我们原生的app中增加一个由html做成的页面;
    2/需要切换contexts那么就需要获取页面的所有contexts,代码实现:
        webview = driver.contexts
        driver.switch_to.context(webview[1])
        driver.find_element_by_link_text('PHP').click()

二、 滑动定位
    1/在app自动化中我们经常会遇见一个问题,我们需要查找的元素不在当前可展示的屏幕,至于在什么地方我们不知道
    ,如果这个时候我们一直使用在当前页面查找,那么系统就会报错,为了解决这个问题我们就需要使用滑动查找
    2/在appium中滑动我们所需要使用的方法就是swipe函数,至于往哪个方向滑动就是看我们里面的x,y的值,如果我们需要下往上滑动那么我们就应该是:
        driver.swipe(x1,y1,x2,y2,t)
        # 从x1,y1滑动屏幕到x2,y2,保持t时间
        # 备注:这里需要注意的是屏幕的x,y的值是从左上角开始取的,左上角为(0,0),右下角是最大
        优化方案:
            x = driver.get_window_size()['width']
            y = driver.get_window_size()['height']
            driver.swipe(x*0.1,y*0.1,x*0.6,y*0.7,t)

三、Toast提示信息(一闪而逝):
# https://www.cnblogs.com/du-hong/p/11175517.html
    1、要获取 Toast 信息要满足以下四个要求:
        Appium server 版本 1.6.3+才支持 Toast 获取。(而 Appium Server 1.6.3 没有可视化界面,解决方案:下载 Appium-desktop-Setup-1.4.1-ia32.exe)。
        代码中必须指定 automationName 为:UIAutomator2
        UIAutomator2 只支持安卓版本 5.0+
        因此,因为他们的最高支持安卓版本为 4.4.2,可以使用 genymotion 模拟器。
        要求安装 jdk1.8 64 位及以上。配置其环境变量 JAVA_HOME 和 path。
    2、实现:
    #获取toast内容是否出现
        def toast_exist(self, toastmessage):
            toast_loc = ("xpath", "//*[contains(@text,'%s')]" % toastmessage)
            try:
            WebDriverWait(self.driver,5,0.2).until(EC.presence_of_element_located(toast_loc))
              #获取文本内容
              driver.find_element_by_xpath(toast_loc).text
              return True
            except:

四、对屏幕的持续操作TouchAction()
    Touch Action包含一些列操作,比如按压、长按、点击、移动、暂停。由着些不同操作可以组成一套动作。使用TochAction需要先导入对应的模块
    from appium.webdriver.common.touch_action import TouchAction
    方法:
        按压:press() 开始按压一个元素或坐标点(x,y):TouchAction(driver).press(x=0,y=308)
        长按:longPress() 开始按压一个元素或坐标点(x,y)。 相比press()方法,longPress()多了一个入参,既然长按,得有按的时间吧。duration以毫秒为单位
            TouchAction(driver).long_press(x=0,y=0,duration=1000)
        点击:tap() 对一个元素或控件执行点击操作:TouchAction(driver).tap(x=0,y=0)
        移动:move_to() 将指针从上一个点移动到指定的元素或点:TouchAction(driver).move_to(x=0,y=0)
        暂停(等待):Wait()暂停脚本的执行,单位为毫秒
        释放:release() 结束的行动取消屏幕上的指针
        执行:perform() 执行的操作发送到服务器的命令操作:TouchAction(driver).press(x=0,y=308).release().perform()
        连续操作:
            TouchAction(driver).press(x=212, y=296).wait(100)\
                       .move_to(x=148, y=0).wait(100)\
                       .move_to(x=148,y=0).wait(100)\
                       .move_to(x=-148,y=148).wait(100)\
                       .move_to(x=-148,y=148).wait(100)\
                       .move_to(x=148,y=0).wait(100)\
                       .move_to(x=148,y=0).wait(100) \
                       .release().wait(200).perform()

//滑动验证码的实现


五、截图:
    1、save_screenshot() 该方法直接保存当前屏幕截图到当前脚本所在文件位置:
        driver.save_screenshot('login.png')
    2、get_screenshot_as_file(self, filename)将截图保留到指定文件路径:
        driver.get_screenshot_as_file('./images/login.png')

六、时间等待:
    1、强制等待:time.sleep()
    2、隐式等待:driver.implicitly_wait(20)::
        WebDriver提供的针对driver级别的适用整个生命周期的等待方法,
        该等待是全局设置,因而只需在实例化driver后设置一次即可。从等待作用上看,是可以满足需要的,但是考虑到实际应用场景,
        driver要等待的元素和脚本要操作的元素未必相同,也就是说,脚本要操作的元素已经出现,但因为设置了全局等待,driver也会继续等待
        页面上其他无关元素,直至整个页面加载完毕。因而,与显式等待相比,可能出现无效等待的情况。
    3、显式等待:WebDriverWait(driver, 3).until(lambda x: x.find_element_by_id())
        WebDriver提供的针对元素级别的、灵活、智能的等待方法,通过配合until()、until_not()、ExpectedCondition等条件的使用,
        默认每500ms检查一次条件状态,可以及时将脚本从等待中唤醒,避免无效等待,在实际应用中推荐使用该方法
    4、等待activity:获取当前页面的出现时间然后进行等待,设置最大时间
        # 获取当前界面activity
        ac = driver.current_activity
        # 等主页面activity出现,30秒内
        driver.wait_activity(".base.ui.MainActivity", 30)

七、Xpha定位的实现

    1、如果元素text是唯一的,可以通过text文本定位://*[@text=’text文本属性’]
        # 定位text
        driver.find_element_by_xpath("//*[@text='文本内容,此处用的是完全匹配']").click()
        
    2、如果元素id是唯一的,也可以id属性定位://*[@resource-id=id属性’]
        # 定位 resource-id
        driver.find_element_by_xpath("//*[@resource-id='com.taobao.taobao:id/tv_scan_text']").click()
        # 也可以联合@resource-id属性和@text文本属性来下定位
        driver.find_element_by_xpth("//*[@resource-id='com.taobao.taobao:id/tv_scan_text'][@text='文本内容,此处用的是完全匹配']").click()
        
    3class属性唯一的话,同样可以通过class属性定位,有两种方法:
        第一种: //class属性 :
        driver.find_element_by_xpath("//android.widget.EditText").click()
        第二种: //*[@class=class属性’] 
        driver.find_element_by_xpath("//*[@class='android.widget.EditText']").click()
        
    4、通过content-desc属性定位://*[@content-desc=’desc的文本’]
        #content-desc定位
        driver.find_element_by_xpath("//*[@content-desc='帮助']").click()
        
    5、contains模糊定位: //[contains(@text(), ‘这里是模糊匹配的文本’)]
        contains是模糊匹配的定位方法,对于一个元素的id或者text不是固定的,但有一部分是固定的,这种就可以模糊匹配
        contains也能模糊匹配idclass属性: //[contains(@resource-id,id属性’)]//[contains(@clsss,class属性’)]
        #定位class
        driver.find_element_by_xpath("//*[contains(@class, 'EditText')]").click()
        #定位id
        driver.find_element_by_xpath("//*[contains(@resource-id, 'id/home_searchedit')]").click()
        
    6、组合定位:如果一个元素有2个属性,通过xpath也可以同时匹配2个属性,text, resource-id,class ,index,content-desc这些属性都能任意组合定位
        # id和class属性   定位搜索框
        id_class = '//android.widget.EditText[@resource-id="com.taobao.taobao:id/home_searchedit"]'
        driver.find_element_by_xpath(id_class).click()

        # text和index属性  定位登录/注册
        desc_class = '//*[@text="注册/登录" and @index="1"]'
        driver.find_element_by_xpath(desc_class).click()

        # class和text属性  定位输入手机号
        class_text = '//android.widget.EditText[@text="请输入手机号码"]'
        driver.find_element_by_xpath(class_text).send_keys("")

        # class和desc  定位帮助
        id_desc = '//*[contains(@resource-id, "aliuser_menu_item_help") and @content-desc="帮助"]'
        driver.find_element_by_xpath(id_desc).click()
    
    7、层级定位
    
        #通过父亲定位儿子:在定位到父元素之后使用/子元素定位即可
        fa_sun = '//*[@resoure-id="com.taobao.taobao:id/home_searchbar"]/android.widget.EditText'
        t = driver.find_element_by_xpaths(fa_sun)[0].text
        
        # 通过子元素定位父元素:'..','parent::*','parent::android.widget.LinearLayout'
        # 方法一: ..
        sun_fa1 = '//*[@resource-id="com.taobao.taobao:id/tv_scan_text"]/..'
        c = driver.find_element_by_xpath(sun_fa1).tag_name
        # 方法二  parent::*
        sun_fa2 = '//*[@resource-id="com.taobao.taobao:id/tv_scan_text"]/parent::*'
        d = driver.find_element_by_xpath(sun_fa1).tag_name
        # 方法三 parent::android.widget.LinearLayout
        sun_fa3 = '//*[@resource-id="com.taobao.taobao:id/tv_scan_text"]/parent::android.widget.LinearLayout'
        e = driver.find_element_by_xpath(sun_fa1).tag_name

 八、使用uiautomator定位
 
    1、通过text文本定位语法:new UiSelector().text("text文本")
        loc_text = 'new UiSelector().text("图书")'
        driver.find_element_by_android_uiautomator(loc_text).click()
        
    2、如果文本比较长,可以用textContains模糊匹配:new UiSelector().textContains("包含text文本")
        loc_textContains = 'new UiSelector().textContains("图")'
        driver.find_element_by_android_uiautomator(loc_textContains).click()
        
    3、同样可以用textStartsWith是以某个文本开头来匹配:ew UiSelector().textStartsWith("以text文本开头")
        loc_textStart = 'new UiSelector().textStartsWith("图")'
        driver.find_element_by_android_uiautomator(loc_textStart).click()
        
    4、也可以用正则表达式textMatches匹配:new UiSelector().textMatches("正则表达式")
    
    5、resourceId定位:new UiSelector().resourceId("id")
        loc_id = 'new UiSelector().resourceId("com.baidu.yuedu:id/webbooktitle")'
        driver.find_element_by_android_uiautomator(loc_id).click()
        
    6、className定位:new UiSelector().className("className")
        loc_class = 'new UiSelector().className("android.widget.TextView")'
        driver.find_element_by_android_uiautomator(loc_class).click()
    
    7、description定位:new UiSelector().description("contenet-des属性")
    
    8、组合定位
        #id+text
        id_text = 'resourceId("com.baidu.yuedu:id/webbooktitle").text("小说")'
        #class+text
        class_text = 'className("android.widget.TextView").text("图书")'  
    
    9、关系定位
        父子定位childSelector
            son = 'resourceId("com.baidu.yuedu:id/rl_tabs").childSelector(text("小说"))'
            driver.find_element_by_android_uiautomator(son).click()
        兄弟定位fromParent
            brother = 'resourceId("com.baidu.yuedu:id/lefttitle").fromParent(text("图书"))'
            driver.find_element_by_android_uiautomator(brother).click()
    
常用的一些方法:
    from appium import webdriver
    from selenium.webdriver.common.touch_actions import TouchActions   #导入TouchActions类
    import time

    caps = {}
    caps["platformName"] = "Android"
    caps["platformVersion"] = "8.0.0"
    caps["deviceName"] = "Phone"
    caps["appPackage"] = "com.android.settings"
    caps["appActivity"] = ".Settings"

    driver = webdriver.Remote("http://localhost:4723/wd/hub", caps)

    time.sleep(1)
    driver.find_element_by_xpath("//android.widget.TextView[@text='Network & Internet']").click()
    print(driver.available_ime_engines)   #返回安卓设备可用的输入法
    driver.open_notifications()   #打系统通知栏
    time.sleep(2)
    driver.press_keycode(4)   #点击返回键关闭通知栏
    driver.save_screenshot("new.png")    #截取当前屏幕并命名new.png,然后保存到电脑脚本当前目录

    '''driver.find_element_by_xpath("//android.widget.TextView[@text='Display']").click()   #使用xpath方法定位
    m = driver.find_element_by_xpath("//android.widget.TextView[@text='Adaptive brightness']")
    print(m.get_attribute("className"))   #获取元素m的className值   '''
    '''
    e = driver.find_element_by_android_uiautomator('new UiSelector().className("android.widget.SeekBar")')      #使用uiautomator搭配class属性方法定位    控制条
    ex = e.location.get('x')       #获取元素初始横坐标
    ey = e.location.get('y')       #获取元素初始纵坐标
    #driver.tap([(ex,ey)],500)         #用tap方法点击拖动按钮的最左侧起始位置
    #driver.tap([(ex+400,ey)],500)      #用tap方法横向点击某按钮,ex+400,ey不变
    driver.swipe(ex,ey,ex+400,ey,500)   #用swipe方法横向拖动某按钮, ey纵坐标不变
    time.sleep(1)
    driver.press_keycode(4)       #按导航返回键'''

    #driver.find_element_by_xpath("//android.widget.TextView[@text='Network & Internet']")

    '''k = driver.find_element_by_xpath("//android.widget.TextView[@text='Network & Internet']")   #定位元素Network & Internet,通过xpath方式
    kx = k.location.get('x')   #获取元素的x坐标
    ky = k.location.get('y')   #获取元素的y坐标
    driver.tap([(kx,ky)],5000)    #长按元素坐标5s
    time.sleep(2)
    driver.install_app('F:\\soft\\weixin.apk')   #安装app,后接apk路径
    #driver.remove_app("com.tencent.mm")   #删除app(包名)
    driver.press_keycode('4')     #按返回键
    #driver.keyevent('3')     #按home键
    time.sleep(2)'''

    '''
    driver.find_element_by_accessibility_id("Search settings").click()   #定位并点击click()
    #driver.find_element_by_id("android:id/search_src_text").send_keys('wifi')    #定位到搜索输入栏,用.send_keys()方法模拟输入文本
    #driver.find_element_by_id("android:id/search_src_text")      #定位到搜索输入栏
    driver.press_keycode(42)     #模拟点击键盘上的n
    driver.press_keycode(34)     #模拟点击键盘上的f
    driver.press_keycode(31)     #模拟点击键盘上的c
    time.sleep(1)
    driver.find_element_by_accessibility_id("Clear query").click()    #清除文本,用.clear()方法来清除输入文本    通过id方式定位
    driver.find_element_by_accessibility_id("Navigate up").click()    #点击返回键'''
    '''
    k = driver.find_element_by_xpath("//android.widget.TextView[@text='Network & Internet']")     #定位元素并附值给k
    print(k.size)    #获取K元素的size,包括height, width
    print(driver.get_window_size())     #打印屏幕分辨率
    '''
    '''time.sleep(2)      #强制等待2s
    x = driver.get_window_size()['width']    #获取屏幕的宽度
    y = driver.get_window_size()['height']    #获取屏幕的高度
    driver.swipe(1/2*x, 5/7*y, 1/2*x, 2/7*y, 1000)    #从下往上滑动屏幕(5/7->2/7)

    time.sleep(2)

    driver.close_app()   #关闭app
    time.sleep(2)
    driver.launch_app()   #启动app
    time.sleep(2)
    driver.get_screenshot_as_file('G:\\Kemi\\pic.png')   #截取当前屏幕并命名pic.png,然后保存到电脑G:\Kemi下
    driver.save_screenshot("newContact.png")  #截取当前屏幕并命名pic.png,然后保存到电脑当前目录下'''

    time.sleep(2)

    #driver.is_app_installed("com.android.settings")   #检查app是否安装
    #driver.find_element_by_xpath("//android.widget.TextView[@text='Brightness level']").is_displayed()  # 定位元素并判断是否显示
    #driver.find_element_by_xpath("//android.widget.TextView[@text='Brightness level']").is_enabled()  #判断是否可用

    #self.driver.find_element_by_android_uiautomator('new UiSelector().text("Long")').click()   #使用uiautomator搭配text属性方法定位    弹框选项

    x = driver.get_window_size()['width']
    y = driver.get_window_size()['height']
    driver.swipe(1/2*x, 6/7*y, 1/2*x, 1/7*y, 1000)    #从下往上滑动屏幕
    time.sleep(1)
    driver.find_element_by_xpath("//android.widget.TextView[@text='Support']").click()
    try:                                                                           #使用try-except判断是否有弹窗,没有就pass跳过势将执行后面的操作
        driver.find_element_by_id("com.sonymobile.support:id/eula_agree").click()
    except Exception as e:
        pass
    try:
        driver.find_element_by_id("com.android.packageinstaller:id/permission_allow_button").click()
    except Exception as e:
        pass
    driver.find_element_by_xpath("//android.widget.ImageView[@resource-id='com.sonymobile.support:id/icon'][@instance='4']").click()  #使用xpath下class、resource-id、instance联合定位
    #driver.find_element_by_xpath("//android.widget.ImageView[@instance='4']").click()    #效果同上句,用xpath下class及instance联合定位
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值