1

Spectron是一个用于自动化Electron应用程序的node.js框架。我正在使用 Spectron 以及AVATypescript来进行自动化集成测试。我正在使用AVA 的建议方法来使测试的上下文类型安全,但我无法弄清楚如何在作为webdriverio客户端的 Spectron 客户端属性上获得类型安全。我只能看到 Spectron 打字稿定义文件提供的一些属性,这会导致打字稿转译错误。

这些是我得到的错误:

src/pages/drive-shell.ts(7,34): error TS2339: Property 'waitForVisible' does not exist on type 'SpectronClient'.
src/pages/login.ts(7,34): error TS2339: Property 'waitForVisible' does not exist on type 'SpectronClient'.
src/pages/login.ts(11,21): error TS2339: Property 'setValue' does not exist on type 'SpectronClient'.
src/pages/login.ts(12,21): error TS2339: Property 'setValue' does not exist on type 'SpectronClient'.
src/pages/login.ts(13,21): error TS2339: Property 'click' does not exist on type 'SpectronClient'.
4

3 回答 3

4

截至目前(2019 年 7 月),WebdriverIO 已移至 5.0 版,但 Spectron 仍使用 WebdriverIO 4。请确保在安装 WebdriverIO 类型时指定 Spectron 中使用的版本以解决此问题:

npm i -S @types/webdriverio@^4.8.0
于 2019-07-27T23:22:47.317 回答
2

实际上,我在输入问题时解决了这个问题,但由于我进行了一些搜索并且找不到任何解决方案,因此我认为我可以回答自己的问题以帮助他人。

我需要获取 webdriver io 的类型

npm i -S @types/webdriverio

然后我将该类型导入我的login.ts脚本并将其用作 SpectronClient

import * as WebdriverIO from 'webdriverio';
export class Login {
    constructor(private client: WebdriverIO.Client<void>) { }

    public async waitForPageToLoad() {
        return await this.client.waitForVisible('#username');
    }

    public login(username: string, password: string) {
        this.client.setValue('#username', username);
        this.client.setValue('#Password', password);
        this.client.click('#login');
    }
}

这是我的完整test.ts测试脚本

import * as ava from 'ava';
import { Application } from 'spectron';
import { Login } from './pages/login';
import { Settings } from './settings';

function contextualize<T>(getContext: () => Promise<T>): ava.RegisterContextual<T> {
    ava.test.beforeEach(async (t) => {
        Object.assign(t.context, await getContext());
    });
    return ava.test;
}
const test = contextualize(async () => {
    const app = new Application({
        path: '../electron.exe',
        args: ['../app/index.html'],
    });
    await app.start();
    return { app };
});

test.afterEach.always(async (t) => await t.context.app.stop());

test('can login', async (t) => {
    const login = new Login(t.context.app.client);
    await login.waitForPageToLoad();
    login.login(Settings.username, Settings.password);
});
于 2017-10-18T18:55:53.467 回答
0

在花了将近一整天的时间深入研究源代码后,我发现Spectron文档是错误的。

明明说,

Spectron 使用 WebdriverIO 并在创建的应用程序实例上公开托管客户端属性。客户端 API 是 WebdriverIO 的浏览器对象。

但从WebdriverIO 文档中可以看出,像click,setValue等函数不是browser对象的一部分。它们在element对象下可用。所以这就是我所做的,

const inputText = await app.client.$('user_name'); // get hold of the element
inputText.click(); // get access to the WebdriverIO functions
于 2021-05-28T00:08:04.303 回答