腾讯Android自动化测试实战3.1.4 Robotium的控件获取、操作及断言

简介:

3.1.4 Robotium的控件获取、操作及断言

Robotium是一款在Android客户端中的自动化测试框架,它需要模拟用户操作手机屏幕。要完成对手机的模拟操作,应该包含以下几个基本操作:

(1)需要知道所要操作控件的坐标。

(2)对要操作的控件进行模拟操作。

(3)判断操作完成后的结果是否符合预期。

因此,本节将从控件获取、控件操作及操作后断言来介绍Robotium,此外,由于WebView在控件获取和控件操作上都与Native完全不同,将对其做单独介绍。

1. Native控件获取

从Robotium中获取Native控件主要有两大方式:一个是根据被测应用的控件ID来获取;另一个是先获取当前界面所有的控件,对这些控件进行过滤封装后再提供相应的获取控件的API。

1)根据被测应用的控件ID来获取

根据控件ID获取见表3-1。

根据String型ID获取控件:

ImageView mIcon = (ImageView) solo.getView("mypic");

在Android中,所有的控件都继承自View,因此,如果被测应用中的控件有唯一ID的话,就可以使用这种通过ID形式唯一获取所要操作的控件。

例如获取RelativeLayout或LinearLayout:

RelativeLayout rel = (RelativeLayout) solo.getView("example1");

LinearLayout lin = (LinearLayout) solo.getView("example2");

由于Android中所有的控件都继承自View类,而对于开发人员的自定义控件,这些自定义控件也基本是继承自Android的基础控件扩展而来的,因此通过这种方式几乎可以获得所有类型的控件,获取相应类型的控件时只要进行转义即可,因此当控件拥有唯一ID时,推荐使用该方式。

控件ID可以通过Android SDK中提供的工具来查看,例如%ANDROID_HOME%\tools\uiautomatorviewer.bat工具,在Android 4.3及以上系统版本的手机上,可直接查看到UI界面的ID。

2)根据控件类型的索引、文本来获取

根据文本获取见表3-2。

此方式是Robotium先将当前界面中的所有控件全部获取,然后按控件类型、索引进行过滤后再获取指定的控件View。

根据index索引获取控件:

//返回界面中第一个类型为Button的控件

Button loginBtn = (Button) solo.getButton(0);

其他的如getEditText(int index)、getText(int index)均同理。

根据文本text获取控件:

//返回界面中文本为‘登录’类型为Button的控件

Button loginBtn = (Button) solo.getButton("登录");

其他的如getText(String text)、getEditText(String text)均同理。

在Robotium中查找控件时,如果找不到相应ID或文本的控件,测试框架会throw出“View with id ××× is no found”或者“with text ××× no found”等Throwable异常,若我们并不希望因此而报错,则可以使用try catch Throwable来捕获。

3)根据控件类型进行过滤

根据类型过滤见表3-3。

表3-3 根据类型过滤

返回值  方法及说明

ArrayList<View>      getCurrentViews()

获取当前界面或弹框中所有的控件

ArrayList<T>     getCurrentViews(Class<T> classToFilterBy)

获取当前界面或弹框中所有控件类型为classToFilterBy的控件

ArrayList<T>     getCurrentViews(Class<T> classToFilterBy, View parent)

获取父控件parent下所有控件类型为classToFilterBy的控件

 

获取当前界面或弹框中所有控件类型为TextView的控件:

ArrayList<TextView> allTextViews = solo

              .getCurrentViews(TextView.class);

获取指定父控件下所有控件类型为TextView的控件:

RelativeLayout rel = (RelativeLayout) solo.getView("example1");

ArrayList<TextView> allTextViews = solo

              .getCurrentViews(TextView.class, rel);

同样是过滤出指定的控件类型,不过该方法是从父视图parent中开始过滤,当不指定parent,即solo.getCurrentViews(TextView.class,null)时,则和solo.getCurrentViews(TextView.class)一样,返回的是当前界面中所有的。

移动App一般节奏很快,UI布局结构也经常随着功能的变更而变动,例如“登录”按钮从最上面变到了最下面,因此通过索引或文本来获取控件是有很大隐患的。很多时候,通过巧妙地控件过滤可以更准确地找到相应的控件。

2. Native控件操作

对于Android端的自动化测试而言,当我们获取到期望的控件后,接下来就是对该控件进行点击、长按、文本输入、拖动等模拟操作。除此之外,UI自动化测试为了贴近用户的真实使用及自身健壮性,还需要时延等待、页面加载等待;为了判断界面是否符合预期,则还需要控件搜索、界面截图等操作。

1)点击、长按操作

点击长按见表3-4。

表3-4 点击长按

返回值  方法及说明

void      clickOnView(View view)/clickLongOnView(View view)

点击指定的View控件/长按指定的View控件

void      clickOnScreen(float x, float y)/clickLongOnScreen(float x, float y)

根据坐标x, y点击屏幕/根据坐标x, y长按屏幕

 

Robotium是基于控件的自动化测试框架,当获取到要操作的控件后,直接对控件进行点击、长按或文本输入等操作即可。

点击指定的View控件:

Button loginBtn = (Button) solo.getView("loginBtn");

solo.clickOnView(loginBtn)

Robotium还提供了点击文本、点击图片的API,例如clickOnText(String text)、click-OnButton(String text)等,这类API类似于前文所介绍的,先根据文本获取控件,再发送点击事件:

Button loginBtn = (Button) solo.getButton("登录");

solo.clickOnView(loginBtn)

类似于点击、长按指定的View控件:

Button loginBtn = (Button) solo.getButton("登录");

solo.clickLongOnView(loginBtn)

需要注意的是,Robotium的点击事件是通过Instrumentation发送的,因此该类点击方法不能点击非被测应用的区域,例如不能点击至通知栏所在的区域,否则会出现类似如下的异常:

java.lang.SecurityException: "Injecting to another application requires INJECT_EVENTS permission"

因此在使用Robotium编写测试用例时,需要注意其无法跨应用的缺点,从而尽量避免出现此场景,有些场景偶然性地无法规避,可以采用try catch Throwable的形式捕获异常,而对于需要跨应用的场景,则可以使用9.4.2节介绍的UI Automator结合Instrumentation模式进行处理。

try {

    } catch (Throwable e) {

}

在手机设置–开发者选项中,可以开启“指针位置”,开启“指针位置”后,再触摸屏幕时,可实时显示屏幕坐标。调试时为了更准确地知道对屏幕的什么地方进行了操作,也常常同时开启“显示触摸操作”开关。

2)操作输入框

操作输入框见表3-5。

表3-5 操作输入框

返回值  方法及说明

void      enterText(EditText editText, String text)

在指定的EditText中输入文本text

void      typeText(EditText editText, String text)

在指定的EditText中键入文本text

void      clearEditText(EditText editText)

清空指定的输入框

 

在自动化测试过程中,当我们可以准确获取控件,并能模拟点击、长按等基本操作后,就可以在被测应用中进行自由跳转,然后可能就需要进行一些输入操作。测试框架中主要提供了enterText(EditText editText, String text)和typeText(EditText editText, String text)两种方法,前者直接对EditText文本框进行赋值,不会有文本输入的展示过程,而后者则会一个文本一个文本地输入,更贴近真实用户的操作。

EditText userET = (EditText) solo.getView("example_et_id");

solo.enterText(userET, "my_user_name")      //直接对文本框赋值

solo.typeText(userET, "my_user_name")       //会展示输入的过程

3)滑动、滚动

滑动、滚动见表3-6。

表3-6 滑动、滚动

返回值  方法及说明

void      drag(float fromX, float toX, float fromY, float toY, int stepCount)

从起始x,y坐标滑至终点x,y坐标;通过stepCount参数指定滑动时的步长

void      scrollToTop() / scrollToBottom()

滚动至顶部 / 滚动至底部

void      scrollUp() / scrollDown()

向上滚动屏幕 / 向下滚动屏幕

void      scrollListToLine(AbsListView absListView, int line)

滚动列表至第line行

 

在Android中,常用的操作还有各种滑动手势,如上拉、下拉、左滑、右滑等。在滑动方面,测试框架主要提供了两类支持,一类是根据坐标进行滑动从而可以模拟各类手势操作,另一类则是根据控件来直接进行滚动操作。

根据坐标进行滑动的主要是drag(float fromX, float toX, float fromY, float toY, int step Count),这里的参数包括起始位置的x与y坐标、终点位置的x与y坐标,还有步长stepCount。其中步长stepCount的意思是,假如要从A点滑到B点,如果步长为1,那么将直接产生从A点到B点的手势操作,滑动速度很快;如果步长为100,则将从A到B分成100等份,例如A、A1、A2…B,然后依次从A滑到A1,再从A1滑到A2、A2滑到A3……这样滑动更慢但结果也更精确,例如当我们在手机上快速从下往上滑动时,列表滑动是有惯性的,会快速滚动,而这常常不是我们所需要的。

根据控件进行滚动主要有滚动至顶部、底部等方法。scrollToTop()方法可以将当前屏幕滑至顶部,如果当前是ListView则滑至列表的顶部,如果是WebView则滑至页面的顶部。同样地,scrollToBottom()可将界面滑至底部。类似的还有向下滑一屏的scrollDown()方法和向上滑一屏的scrollUp()方法。与前文介绍的drag方法不同的是,这类滚动调用的是相应控件自身的API,例如WebView的滚动调用的是控件自身的pageUp(boolean top)或pageDown(boolean bottom)方法。因此,这种方式与drag方式最大的区别在于,drag是实际地模拟手势操作,当上拉时,如果ListView有监听上拉加载更多,那么使用drag是可以触发上拉加载更多的,而scrollUp()则不能。

4)搜索与等待

搜索与等待见表3-7。

表3-7 搜索与等待

返回值  方法及说明

void      sleep(int time)

休眠指定的时间,单位毫秒

boolean searchText(String text)

从当前界面搜索指定文本

boolean waitForView(int id) / waitForText(String text)

等待指定控件出现 / 等待指定文本出现

boolean waitForActivity(String name)

等待指定的Activity出现

boolean waitForLogMessage(String logMessage)

等待指定的日志信息出现

boolean waitForDialogToOpen() / waitForDialogToClose()

等待弹框打开 / 等待弹框关闭

 

UI自动化测试常常被诟病运行不稳定,除了项目快速迭代导致界面经常变更这一不可控因素外,脚本常常运行出错就是由于没有合适的等待机制导致控件未找到、点击异常等问题,要想测试用例能够快速且稳定地运行,合理使用等待是关键要素之一。

Robotium中提供了诸多与等待相关的API,但是实际情况中需要等待的操作往往要复杂得多,因此测试框架中也提供了Condition模式,即waitForCondition(Condition condition, int timeout)方法,使用该方法时,实现Condition接口并重写isSatisfied()方法,isSatisfied()为true时将跳出等待。通过这种模式我们可以自定义实现更多类型的等待操作,如代码清单3-1所示。

代码清单3-1 使用waitForCondition模式实现等待

public void waitForAppInstalled(final String appName, int timeout) {

    waitForCondition(new Condition() {

        @Override

        public boolean isSatisfied() {

            sleeper.sleepMini();

            return checker.isAppInstalled(appName);

        }

    }, timeout);

}

当然了,我们也可以使用超时机制来实现,如代码清单3-2所示。

代码清单3-2 使用TimeOut模式实现等待

public void waitForAppInstalled(final String appName, int timeout) {

    long endTime = SystemClock.uptimeMillis() + timeout;

    while (SystemClock.uptimeMillis() < endTime) {

        if (checker.isAppInstalled(appName)) {

            break;

        }

        sleeper.sleep();

    }

}

需要注意的是,Robotium中查找控件、点击控件等API都默认使用了搜索与等待机制,当我们使用上文提到的获取控件、点击控件相关操作时,测试框架已经做好了等待操作,因此非特殊情况是不需要额外增加等待操作的步骤的。太多的等待将使用例执行变得缓慢低效,因此在用例编写调试过程中应该做好平衡。

5)截图及其他

截图及其他见表3-8所示。

表3-8 截图及其他

返回值  方法及说明

void      takeScreenshot(String name)

截图,图片名称为指定的name参数,图片默认路径为/sdcard/Robotium-Screenshots/

void      finishOpenedActivities()

关闭当前已打开的所有Activity

void      goBack() / goBackToActivity(String name)

点击返回键 / 不断地点击返回键直至返回到指定的Activity

void      hideSoftKeyboard()

收起键盘

void      setActivityOrientation(int orientation)

等待设置Activity转屏方向

 

自动化测试过程中,因为都是自动化执行的,当用例执行失败时,除了日志外,最方便解决定位问题的就是运行时的截图,有了截图定位问题往往事半功倍,Robotium中提供了单次截图及截取一系列图片的功能。takeScreenshot()方法可以直接截取当前屏幕,并将其默认地保存在/sdcard/Robotium-Screenshots/目录下,要更改图片名称则使用takeScreenshot(String name),要截取某时间段内一个序列的话则可以使用startScreenshotSequence(String name)。那么如何更好地在自动化中使用截图功能呢?一般情况下我们更希望的是在用例执行失败时进行截图,详情请见本书9.3.2节中介绍的结合Spoon出错重试与截图。

除了常规的操作外,Robotium测试框架还提供了发送模拟按键sendKey(int key)、设置屏幕是横屏还是竖屏setActivityOrientation(int orientation)、模拟点击返回键goBack()、跳转至指定Activity的方法goBackToActivity(String name)、收起输入法hideSoftKeyboard()、关闭所有已打开的Activity 的方法finishOpenedActivities()等。通过组合利用这些常用操作,基本就可以完成在Android端的UI自动化操作了。

3. WebView支持

在Android App中由于HTML可以更快地响应变化,而不像Native那样需要发布版本才能让用户使用上新特性,因此大多数App都是既有Native部分,也有HTML部分,也即俗称的Hybrid App。而Robotium在Robotium4.0版本中就开始全面支持WebView的自动化了。要了解如何使用Robotium测试框架来对App中的WebView部分进行自动化测试,首先需要了解HTML基础,然后了解Robotium是如何获取页面元素并进行操作的。

1)HTML基础

Robotium支持通过ID、className等方式来获取WebElement元素,因此,首先了解ID、className等的概念,模拟打开GitHub首页并查看网页源码如图3-12所示。

HTML元素:指的是从开始标签到结束标签的所有代码。如图3-12所示,Sign in按钮在开始标签<a href="/login" class="btn btn-block primary">与结束标签</a>内,因此整体属于一个HTML元素。

HTML属性:属性总是以名称/值对的形式出现的,比如:name="value"。属性总是在HTML元素的开始标签中规定的。核心属性有class(规定元素的类名)、ID(规定元素的唯一ID)。Sign in按钮中就有class属性,class="btn btn-block primary"。

 

 

图3-12 GitHub首页的HTML结构

2)WebElement相关API及操作

WebElement相关API见表3-9。

表3-9 WebElement相关API

返回值  方法及说明

ArrayList<WebElement> getCurrentWebElements()

获取当前WebView的所有WebElement元素

ArrayList<WebElement> getCurrentWebElements(By by)

通过By根据指定的元素属性获取当前WebView的所有WebElement元素

void      clickOnWebElement(By by)

通过By根据指定的元素属性点击WebElement

void      clickOnWebElement(WebElement webElement)

点击指定的WebElement

void      enterTextInWebElement(By by, String text)

根据by找到WebElement,并输入指定的文本text

boolean waitForWebElement(By by)

等待根据by获得的WebElement出现

 

在Robotium中对WebElement进行操作有两种方式,一种是先获取相应的WebElement,然后发送点击事件,另一种则是直接调用clickOnWebElement(By by)进行点击。

在获取WebElement元素前我们首先需要知道这个页面的HTML结构,需要知道URL链接才能方便地查看HTML元素、属性等。

获取WebView中的页面信息可以参考本书6.3.3节Appium 脚本常见问题及处理方法中如何获取WebView中的页面信息这一部分内容,通过Chrome浏览器中的DevTools工具可以快速方便地查看WebView中的信息。

我们也可以使用原始的如代码清单3-3所示的方式打印出所有的元素信息。

代码清单3-3 使用日志打印方式获取元素信息

ArrayList<WebElement> webElements = solo.getCurrentWebElements();

WebElement webElement = null;

for(int i=0;i< webElements.size();i++){

    webElement = webElements.get(i);

    Log.i("WebElement", "getId:" + webElement.getId());

    Log.i("WebElement","getClassName:"+webElement.getClassName());

    Log.i ("WebElement", "getText:" + webElement.getText());

}

当我们知道了相应页面的元素、属性后,就可以通过元素或属性等信息来获取指定的WebElement。

1)获取当前WebView所有WebElement

ArrayList<WebElement> webElements = solo.getCurrentWebElements();

2)通过className获取

ArrayList<WebElement> signIns = solo.getCurrentWebElements(By

             .className("btn btn-block primary"));

3)通过ID获取

ArrayList<WebElement> signIns = solo.getCurrentWebElements(By

             .id("example_id"));

4)通过textContent获取

ArrayList<WebElement> signIns = solo.getCurrentWebElements(By

             .textContent("Sign in"));

类似的还有通过cssSelector、name、tagName、xpath等方式获取。

5)通过WebElement点击

拿到WebElement后,如果在页面中该标识是唯一的,那么数组长度为1,可以通过clickOnWebElement(WebElement webElement)方法比较精确地点击。

solo.clickOnWebElement(signIns.get(0));

以上获取WebElement并点击也可以直接使用clickOnWebElement(By by)方法完成。

solo.clickOnWebElement(By.className("btn btn-block primary"));

6)WebElement输入

solo.enterTextInWebElement(By.name("userId"), "your username"); 

solo.enterTextInWebElement(By.name("passwd"), "your passwd"); 

同样地,WebElement也支持等待操作,可以通过waitForWebElement(By by)等待相应的元素出现,然后查找,这样可以使脚本更健壮。不过Robotium中的clickOnTx-WebElement(By by)也均默认已经使用了等待机制,因此非特殊情况,脚本中不需要额外增加等待操作。

Robotium中对WebView的支持由于是使用对系统WebView执行JS从而封装获取页面元素的方式,因此该测试框架只支持App中使用系统WebView的情况,如果App或浏览器使用的是非系统内核的WebView,例如腾讯手机QQ浏览器的X5内核,则无法使用,需要引用X5的SDK并对Robotium进行改造才可支持。

4. 断言

自动化测试中,我们获取控件、执行操作后,接下来就是要对操作后的场景进行断言了。Robotium是基于Instrumentation的测试框架,其测试用例编写的框架是基于Junit的,因此,本小节将先介绍Junit中的断言,然后介绍Robotium中适用于Android端自动化的断言。

1)Junit中的断言

Junit中的断言相关API见表3-10。

表3-10 Junit中的断言相关API

返回值  方法及说明

void      assertTrue(String message, boolean condition)

断言传入的condition参数应该为True,否则将抛出一个带有message提示的Throwable异常

void      assertFalse(String message, boolean condition)

断言传入的condition参数应该为False,否则将抛出一个带有message提示的Throwable异常

void      fail(String message)

直接使用例失败,并抛出一个带有message提示的Throawable异常

 

Junit中的断言可以查看Android SDK中junit.framework.Assert包下的Assert类,常用的有assertTrue(String message, boolean condition)方法,即断言方法中第二个参数condition的结果是否为True,如果为True则该语句执行通过,否则该语句将抛出Throwable的异常,而异常中的提示语将为第一个参数message。因此,使用断言时,应该准确明了地说明message参数,以便断言不符合预期时可以快速判断是什么原因导致的。例如断言某个控件应该要显示在界面中,代码如下:

Button loginBtn = (Button) solo.getView("loginBtn");

assertTrue("‘登录’按钮应该要显示在界面", loginBtn.isShown());

同样地,还有assertFalse(String message, boolean condition)方法,用于断言第二个条件中的结果应该为False。通过这两个方法,只要测试过程中的预期结果能转换成True或False的都可以进行判断,例如判断界面元素是否显示、数值大小比较、文本对比等。

在测试工程中,当出现某种场景时,有时我们希望直接使用例失败而不再往下执行,此时可以使用Assert类中的fail(String message)方法,例如:

if(isBadHappened()){

     fail("this should no happened");

}

而如果出现某种场景,我们希望直接使用例通过而不再执行,则此时在用例脚本中直接使用return即可。

2)Robotium中的断言

Robotium中的断言相关API见表3-11。

表3-11 Robotium中的断言相关API

返回值  方法及说明

void      assertCurrentActivity(String message, String name)

断言当前界面是否为name参数指定的Activity,若不是则抛出一个带有message提示的Throwable异常

void      assertMemoryNotLow()

断言当前是否处于低内存状态

 

Robotium基于Junit中的断言判断,也封装了几个方便在Android端自动化时使用的断言方法。例如assertCurrentActivity(String message, String name)方法可以判断当前界面是否是预期的Activity,我们知道Android中许多页面都对应于一个Activity,当App跳转到一个界面时,就可以使用该方法来判断是否已跳转到相应Activity了。

//获取当前的Activity名

String currentActivity =

              solo.getCurrentActivity().getClass().getSimpleName();

// expectedActivity为期望跳转的Activity

solo.assertCurrentActivity("expected xxxActivity" + " but was " + currentActivity, expectedActivity);

另外,测试框架中的assertMemoryNotLow()方法可以用来判断当前是否处于内存吃紧的情况。在Robotium封装的断言API并不多,因为如前文所说,大多数场景都可以使用True或False来进行判断。

3)Android中的断言

Android中的断言相关API见表3-12。

表3-12 Android中的断言相关API

返回值  方法及说明

void      assertOnScreen(View origin, View view)

断言view是否在屏幕中

void      assertBottomAligned(View first, View second)

断言两个view是否底端对齐,即它们的底端y坐标相等

 

在Android SDK中,android.test.ViewAsserts包下有个ViewAsserts类可以方便地进行与控件相关的断言。例如断言控件是否在窗口中assertOnScreen(View origin, View view),断言两个控件是否底部对齐assertBottomAligned(View first, View second),是否右对齐assertRightAligned(View first, View second),等等。而之所以能实现这些断言在于View控件本身就具有非常多的可以用于判断自身状态的属性,例如View可以判断自身是否显示isShown(),判断是否被选中isSelected(),还可以获取自身所在的坐标位置getLocationOnScreen(int[] location)和宽高getWidth()、getHeight(),等等。由于基于Robotium编写的测试用例是以App形式安装进手机的,且运行时是运行在被测应用所在的进程,因此我们使用断言时,可以借助Android SDK中丰富的类库来进行各种判断,例如判断当前网络状态、应用安装情况、当前应用是否处于前台等,可以很方便地对测试的预期结果进行判断。如代码清单3-4所示,调用Android中的API根据包名判断是否是系统应用。

代码清单3-4 根据包名判断是否是系统应用

/**

 * 根据packageName判断该应用是否是系统应用

 * @param packageName  应用的包名

 * @return  true,系统应用;false,非系统应用

 */

public boolean isSystemApp(String packageName){    

    PackageManager pm = getInstrumentation().getTargetContext().getApplicationContext().getPackageManager();

 

    ApplicationInfo applicationInfo = null;

 

    try {

        applicationInfo = pm.getApplicationInfo(packageName, PackageManager.GET_UNINSTALLED_PACKAGES);

        if(applicationInfo !=null &&  (applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM) ==1){

        LogUtils.logD(TAG, "applicationInfo flag:" + (applicationInfo.flags & ApplicationInfo.FLAG_SYSTEM));

            return true;

        }

 

    } catch (NameNotFoundException e) {

    }      

   

    return false;

}

相关文章
|
5月前
|
Android开发 iOS开发
android自动化编译
android自动化编译
|
4月前
|
安全 测试技术 网络安全
探索自动化测试:从理论到实践网络防御的盾牌与剑:漏洞解析与加密技术实战
【7月更文挑战第31天】在软件工程领域,自动化测试是确保产品质量和提升开发效率的关键工具。本文将深入探讨自动化测试的核心概念、优势以及面临的挑战,并通过一个具体的代码示例来展示如何在实际项目中实施自动化测试。我们将看到,通过采用恰当的策略和技术,自动化测试不仅能够提高测试覆盖率,还可以缩短反馈周期,从而加速迭代速度。 【7月更文挑战第31天】在数字世界的无垠战场上,网络安全和信息安全是守护数据宝藏的盾牌与剑。本文将深入探讨网络安全的脆弱点,揭示加密技术的奥秘,并唤醒每一位数字时代居民的安全意识。通过代码示例和案例分析,我们将一起穿梭在信息的海洋中,学习如何铸造坚不可摧的防御,以及如何运用高超
74 0
|
5月前
|
XML API 开发工具
Android Bitmap 加载与像素操作
Android Bitmap 加载与像素操作
48 2
|
4月前
|
Android开发
Android kernel 操作gpio
Android kernel 操作gpio
43 0
|
6月前
|
安全 物联网 测试技术
构建未来:Android与IoT设备的无缝交互深入探索软件自动化测试的未来趋势
【5月更文挑战第30天】在物联网(IoT)技术快速发展的当下,Android系统因其开放性和广泛的用户基础成为了连接智能设备的首选平台。本文将探讨如何通过现代Android开发技术实现智能手机与IoT设备的高效、稳定连接,并分析其中的挑战和解决方案。我们将深入挖掘Android系统的底层通信机制,提出创新的交互模式,并通过实例演示如何在Android应用中集成IoT控制功能,旨在为开发者提供一套可行的指导方案,促进IoT生态系统的进一步发展。
|
5月前
|
存储 算法 Java
Android 进阶——代码插桩必知必会&ASM7字节码操作
Android 进阶——代码插桩必知必会&ASM7字节码操作
241 0
|
6月前
|
JavaScript 前端开发 Java
《手把手教你》系列技巧篇(四十九)-java+ selenium自动化测试-隐藏元素定位与操作(详解教程)
【5月更文挑战第13天】本文主要讨论了在Selenium自动化测试中如何处理前端隐藏元素的问题。隐藏元素通常是通过`type="hidden"`或`style="display: none;"`属性实现的,它们在页面上不可见,但仍然存在于HTML代码中。Selenium可以定位到这些隐藏元素,但无法直接进行点击、输入等操作,会报错“ElementNotInteractableException”。
109 3
|
5月前
|
Java Android开发 Python
自动化编译错误 cocos2dx 3.0beta2 android
自动化编译错误 cocos2dx 3.0beta2 android
|
6月前
|
JavaScript 前端开发 测试技术
《手把手教你》系列技巧篇(四十八)-java+ selenium自动化测试-判断元素是否可操作(详解教程)
【5月更文挑战第12天】本文介绍了WebDriver中用于判断元素状态的三个方法:`isEnabled()`、`isSelected()`和`isDisplayed()`。`isSelected()`检查元素是否被选中,通常用于勾选框。`isDisplayed()`则用来判断元素是否在页面上可见。`isEnabled()`方法确定元素是否可操作,例如是否能点击或输入内容。
119 1
|
6月前
|
数据采集 Java 开发工具
一文2500字从0到1教你搭建Android自动化python+appium环境
一文2500字从0到1教你搭建Android自动化python+appium环境
一文2500字从0到1教你搭建Android自动化python+appium环境

热门文章

最新文章