Appium框架中的非法参数异常

Illegal Argument Exception in Appium framework

在(愚蠢地)升级 Appium Server 以及各种项目库之后,我无法判断是哪个(如果有的话)导致了问题,我之前的 运行 Appium 框架在尝试定位任何元素时突然开始失败.

服务器启动(通过桌面手动或通过 java 代码)并启动我的模拟器(如果尚未加载),建立连接,打开应用程序(在案例中显示,只需设置) 并在尝试通过检查 "Settings" 文本的存在来验证设置主页显示时失败:

Given the settings app is displayed (FAILED) (java.lang.IllegalArgumentException: Can not set io.appium.java_client.android.AndroidElement field com.mindtree.pageobjects.SettingsMainPage.header to org.openqa.selenium.remote.RemoteWebElement$$EnhancerByCGLIB$$d27c0df4)

桌面和 nodeJS 的 Appium 服务器版本目前都是 1.7.2 我相信问题是在我最初是 1.7.1 或 1.7.2 时开始的,它成功地在桌面版本上进行了自动更新1.8.1.

Selenium 版本为 3.11.0(尝试了从 3.9.0 到 3.13.0 的各种版本)

Appium Java 客户端是 6.0.0-BETA5(试过 6.0.0-BETA4、6.0.0、6.1.0)

Java 是 1.8

报错的JBehave测试步骤:

@Given("the settings app is displayed")
public void givenTheSettingsAppIsDisplayed() {
    main = new SettingsMainPage(driver);
    if (main.pageLoaded())
        test.logGivenPass("the settings app is displayed");
    else {
        test.logGivenFail("the settings app is displayed");
        fail();
    }
}

对应的页面对象片段:

public class SettingsMainPage extends MobilePageObject {

    public SettingsMainPage(AndroidDriver<AndroidElement> driver) {
        super(driver);
        System.out.println("Settings Main page class has been initialized");
    }

    @AndroidFindBy(xpath = "//android.widget.TextView[@text='Settings']")
    AndroidElement header;
    @AndroidFindBy(id= "android:id/title")
    List<AndroidElement> titles;
    @AndroidFindBy(id= "android:id/summary")
    List<AndroidElement> summaries;

    public Boolean pageLoaded() {
        return helper.isDisplayed(header);
    }

}

Google 搜索这个特定错误 returns 几次,但没有提供解决方案。

感谢任何指导。

编辑:我应该补充一点,失败似乎发生在通过页面工厂初始化页面对象时,因为文本 "initialized" 从未显示,它在尝试初始化所有页面元素时失败,具体第一个,至少根据错误信息。

我的基页对象如下:

import java.time.Duration;

import org.openqa.selenium.support.PageFactory;

import com.mindtree.helpers.AppiumUtils;

import io.appium.java_client.android.AndroidDriver;
import io.appium.java_client.android.AndroidElement;
import io.appium.java_client.pagefactory.AppiumFieldDecorator;

public class MobilePageObject {

    AndroidDriver<AndroidElement> driver;
    AppiumUtils helper;

    public MobilePageObject(AndroidDriver<AndroidElement> driver) {

        this.driver = driver;
        PageFactory.initElements(new AppiumFieldDecorator(driver, Duration.ofSeconds(15)), this);
        helper = new AppiumUtils();

    }

}

Edit Update: Downgraded the Appium Server through NodeJS from 1.7.2 to 1.7.1. Result: no change, same error reported.

我正在使用 Appium 服务器 1.8.1selenium 3.13.0java 客户端6.1.0。我使用如下页面对象模型,它工作正常。

public class SettingsMainPage{

    public SettingsMainPage(AndroidDriver<AndroidElement> driver) {
        PageFactory.initElements(new AppiumFieldDecorator(driver), this);
        System.out.println("Settings Main page class has been initialized");
    }

    @AndroidFindBy(xpath = "//android.widget.TextView[@text='Settings']")
    AndroidElement header;
    @AndroidFindBy(id= "android:id/title")
    List<AndroidElement> titles;
    @AndroidFindBy(id= "android:id/summary")
    List<AndroidElement> summaries;

    public boolean pageLoaded() {
       try{

           (new WebDriverWait(driver, 20)).until(ExpectedConditions.visibilityOfElementLocated(header));
           return header.isDisplayed();
       }
       catch(Exception e){
           return false;
       }
    }

}

并且您必须像下面这样定义您的 desiredCapabilities:

public static AppiumDriver<MobileElement> driver;
public static AppiumDriver<MobileElement> setupDesiredCapabilities(String appPackage, String appActivity,
                                                                       String udid, String platformVersion, boolean noReset) {

        DesiredCapabilities caps = new DesiredCapabilities();

        caps.setCapability("deviceName", "Android phone");  //any name
        caps.setCapability("udid", udid);   
        caps.setCapability("platformName", "Android");
        caps.setCapability("platformVersion", platformVersion);
        caps.setCapability("appPackage", appPackage);
        caps.setCapability("appActivity", appActivity);
        caps.setCapability("noReset", noReset);    //optional


        try {
            driver = new AndroidDriver<MobileElement>(new URL(
                    "http://127.0.0.1:4723/wd/hub"), caps);

        } catch (MalformedURLException e) {
            //
        } catch (Exception ex) {
            //
        }

        return driver;
    }

Make sure you have define static AppiumDriver and use the same driver object to call constructor of each page.