提问者:小点点

机器人框架-将Appium驱动程序传递给python脚本


我正在使用Python将机器人框架与Appium集成。然而,我不知道如何将在机器人框架中创建的Appium驱动程序传递给自定义的python脚本。

我的环境:

  • MacOS-Mavericks
  • Appium 1.2(通过home brew安装)
  • 最新的机器人框架(通过pip安装)
  • 最新的机器人框架Appium库(通过pip安装)

我在Python有一个工作的Appium脚本,但我想开始使用机器人框架来处理实际测试。

工作python脚本的部分代码:

wd = webdriver.Remote('http://127.0.0.1:4723/wd/hub', desired_caps)
wd.find_element_by_name("Start").click()
wd.find_element_by_xpath("//UIAApplication[1]/UIAWindow[1]/UIATableView[1]/UIATableCell[1]").click()
wd.execute_script("var vKeyboard = target.frontMostApp().keyboard(); vKeyboard.typeString(\"Test Text\");")
wd.execute_script("var vKeyboard = target.frontMostApp().keyboard(); vKeyboard.buttons()['Return'].tap();")

如您所见,由于应用程序的工作方式,我决定使用execute_script作为脚本的一部分。

机器人框架的Appium库不公开execute_script,所以我需要在python库中编写自己的。

这是我的机器人测试脚本的开始,直到我需要execute_script:

TestStart
    Open Application   ${REMOTE_URL}    ${PLATFORM_NAME}    ${PLATFORM_VERSION}    ${DEVICE_NAME}    ${APP}
    Click Element    name=Start
    Click Element    xpath=//UIAApplication[1]/UIAWindow[1]/UIATableView[1]/UIATableCell[1]

我的问题是如何获得在Open Application中创建的驱动程序实例并将其传递给Python脚本?

我有一个python脚本,它具有以下内容:

def KeyboardType(driver):
    driver.execute_script("var vKeyboard = target.frontMostApp().keyboard(); vKeyboard.typeString(\"hi there\");")

但是,我似乎无法将驱动程序从Robot Framework脚本传递到这个python脚本。

我尝试通过以下方式将Open Application设置为变量:

${Driver}  Open Application   ${REMOTE_URL}    ${PLATFORM_NAME}    ${PLATFORM_VERSION}    ${DEVICE_NAME}    ${APP}
KeyboardType  ${Driver}

但是我收到了错误:

str对象没有属性execute_script

我还尝试将获取当前上下文的结果传递到python脚本中,但后来我得到:

unicode对象没有属性execute_script

如何将机器人框架创建的驱动程序传递到python脚本中?


共3个答案

匿名用户

我目前没有使用appium,所以我不能给出一个明确的答案。然而,关于selenium,有人提出了一个类似的问题,其中有人需要实际的web驱动程序对象。请参阅问题将现有的Web驱动程序对象传递给机器人框架的自定义Python库

简而言之,您可以尝试对appium库进行子类化,以便您的关键字可以访问所有appium内部结构,或者您可以通过调用BuiltIn()来获得库的句柄。get_library_instance('Selenium2Library

有关后一种技术的更多信息,请参阅机器人框架用户指南中的从机器人框架获取活动库实例。

匿名用户

这是您问题的解决方案:)

from robot.libraries.BuiltIn import BuiltIn

def get_current_driver():
    return BuiltIn().get_library_instance('AppiumLibrary')._current_application()

匿名用户

感谢Bryan Oakley的回应,他向我指出了解决方案,即对Appium库进行子类化。

我做了以下更改以使其工作

我的主要Robot Framework测试文件不再引用Appium框架,而是只引用我的自定义python文件。

我的自定义python文件现在是Appium库的子类,因此我可以访问_current_application()。

自定义python类现在如下所示:

from AppiumLibrary import AppiumLibrary

class Custom(AppiumLibrary):
    def get_driver_instance(self):
        return self._current_application()

    def KeyboardType(self, textToType):
        self._current_application().execute_script("var vKeyboard = target.frontMostApp().keyboard(); vKeyboard.typeString(\"" + textToType + "\");")

    def PressKeyboardButton(self, buttonToPress):
        self._current_application().execute_script("var vKeyboard = target.frontMostApp().keyboard(); vKeyboard.buttons()['" + buttonToPress + "'].tap();")

机器人框架文件现在如下所示:

TestStart
    Open Application   ${REMOTE_URL}    ${PLATFORM_NAME}    ${PLATFORM_VERSION}    ${DEVICE_NAME}    ${APP}
    Click Element    name=Start
    Click Element    xpath=//UIAApplication[1]/UIAWindow[1]/UIATableView[1]/UIATableCell[1]
    KeyboardType    Test 123
    PressKeyboardButton    Return

注意:此时,我不需要将Open Application设置为变量,因为子类会自动访问它。但是,如果需要,我现在可以稍后通过“获取驱动程序实例”轻松地将其设置为变量。

谢谢你的帮助布莱恩!