使用自定义 util 时神秘的量角器测试失败

Mysterious protractor test failure when using custom util

我希望我的测试能够正常工作,无论它们在 运行 中的顺序如何。因此,我创建了一个实用程序,如果尚未登录,则登录测试用户。但似乎当我使用量角器行为不端的实用程序。请继续阅读。该实用程序如下所示:

export class E2EUtils {
  loginAndGoTo(url: string) {
    return browser.get(url).then(() => {
      return browser.driver.getCurrentUrl().then(
        (currentUrl) => {
          if (currentUrl.indexOf('/login') !== -1) {
            element(by.css('[name=email]')).sendKeys('user@email.com');
            element(by.css('[name=password]')).sendKeys('secret');
            element(by.css('login form button')).click();
          }
          expect(browser.driver.getCurrentUrl()).toMatch('.*' + url + '$');
        }, (error) => {
          console.error('error in E2EUtil.loginAndGoTo', error);
        });
    });
  };
}

使用util的测试

import { E2EUtils } from '../e2e-utils.e2e-spec';
let utils = new E2EUtils();

describe('Home', () => {
  it('should show right profile', (done) => {
    utils.loginAndGoTo('home/user').then(() => {
      expect(element(by.css('home p')).getText()).toContain('user');
      done();
    }, (e) => { console.error('error in home.component.e2e-spec.ts', e); });
  });
});

而且它不起作用。它挂起并最终给出错误:

Failed: Timed out waiting for Protractor to synchronize with the page after 11 seconds. Please see https://github.com/angular/protractor/blob/master/docs/faq.md
While waiting for element with locator - Locator: By(css selector, home p)

不过。这个'identical test works'。唯一的区别是我没有使用 util.

  it('should show right profile-OLD', () => {
    browser.get('/home/user');
    element(by.css('[name=email]')).sendKeys('user@email.com');
    element(by.css('[name=password]')).sendKeys('secret');
    element(by.css('login form button')).click();
    expect(browser.getCurrentUrl()).toMatch('.*home/user$');
    expect(element(by.css('home p')).getText()).toContain('user');
  });

我也使用过 Element Explorer 并亲自尝试了元素定位器,它仅在不使用 util 时有效。即使正确的页面可见。因此,该实用程序似乎将量角器设置为一种奇怪的状态。附带说明一下,我无法在 util 方法中使用 browser.getCurrentUrl(),而是必须使用 browser.driver.getCurrentUrl()。但是,browser.getCurrentUrl() 在不使用实用程序的测试中工作。

好的。所以我找到了解决方法。如果我添加 ignoreSynchronizationsleep 一段时间,我可以通过测试。像这样:

it('should show right profile', (done) => {
  browser.ignoreSynchronization = true;                                 <--
  utils.loginAndGoTo('home/user').then(() => {
    sleep(1000);                                                        <--
    expect(element(by.css('home p')).getText()).toContain('user');
    done();
  }, (e) => { console.error('error in home.component.e2e-spec.ts', e); });
});

我不明白为什么这让它起作用。不知何故,我的 util 方法(异步的)让量角器相信它必须等待 angular?此外,我现在可以使用 browser.getCurrentUrl 而不是 browser.driver.getCurrentUrl。这是 ignoreSynchronization 的文档所说

/**
   * If true, Protractor will not attempt to synchronize with the page before
   * performing actions. This can be harmful because Protractor will not wait
   * until $timeouts and $http calls have been processed, which can cause
   * tests to become flaky. This should be used only when necessary, such as
   * when a page continuously polls an API using $timeout.
   *
   * @type {boolean}
   */