Fix password UI auth test
By adding a way to wait a short time for a component to appear in the DOM, so we don't get flakey failures like this when we change something to returning a promise that needs to resolve before the component actually appears.
This commit is contained in:
parent
c413de4452
commit
375ae8fb04
2 changed files with 83 additions and 42 deletions
|
@ -68,50 +68,51 @@ describe('InteractiveAuthDialog', function () {
|
|||
onFinished={onFinished}
|
||||
/>, parentDiv);
|
||||
|
||||
// at this point there should be a password box and a submit button
|
||||
const formNode = ReactTestUtils.findRenderedDOMComponentWithTag(dlg, "form");
|
||||
const inputNodes = ReactTestUtils.scryRenderedDOMComponentsWithTag(
|
||||
dlg, "input"
|
||||
);
|
||||
let passwordNode;
|
||||
let submitNode;
|
||||
for (const node of inputNodes) {
|
||||
if (node.type == 'password') {
|
||||
passwordNode = node;
|
||||
} else if (node.type == 'submit') {
|
||||
submitNode = node;
|
||||
// wait for a password box and a submit button
|
||||
test_utils.waitForRenderedDOMComponentWithTag(dlg, "form").then((formNode) => {
|
||||
const inputNodes = ReactTestUtils.scryRenderedDOMComponentsWithTag(
|
||||
dlg, "input"
|
||||
);
|
||||
let passwordNode;
|
||||
let submitNode;
|
||||
for (const node of inputNodes) {
|
||||
if (node.type == 'password') {
|
||||
passwordNode = node;
|
||||
} else if (node.type == 'submit') {
|
||||
submitNode = node;
|
||||
}
|
||||
}
|
||||
}
|
||||
expect(passwordNode).toExist();
|
||||
expect(submitNode).toExist();
|
||||
expect(passwordNode).toExist();
|
||||
expect(submitNode).toExist();
|
||||
|
||||
// submit should be disabled
|
||||
expect(submitNode.disabled).toBe(true);
|
||||
// submit should be disabled
|
||||
expect(submitNode.disabled).toBe(true);
|
||||
|
||||
// put something in the password box, and hit enter; that should
|
||||
// trigger a request
|
||||
passwordNode.value = "s3kr3t";
|
||||
ReactTestUtils.Simulate.change(passwordNode);
|
||||
expect(submitNode.disabled).toBe(false);
|
||||
ReactTestUtils.Simulate.submit(formNode, {});
|
||||
// put something in the password box, and hit enter; that should
|
||||
// trigger a request
|
||||
passwordNode.value = "s3kr3t";
|
||||
ReactTestUtils.Simulate.change(passwordNode);
|
||||
expect(submitNode.disabled).toBe(false);
|
||||
ReactTestUtils.Simulate.submit(formNode, {});
|
||||
|
||||
expect(doRequest.callCount).toEqual(1);
|
||||
expect(doRequest.calledWithExactly({
|
||||
session: "sess",
|
||||
type: "m.login.password",
|
||||
password: "s3kr3t",
|
||||
user: "@user:id",
|
||||
})).toBe(true);
|
||||
expect(doRequest.callCount).toEqual(1);
|
||||
expect(doRequest.calledWithExactly({
|
||||
session: "sess",
|
||||
type: "m.login.password",
|
||||
password: "s3kr3t",
|
||||
user: "@user:id",
|
||||
})).toBe(true);
|
||||
|
||||
// there should now be a spinner
|
||||
ReactTestUtils.findRenderedComponentWithType(
|
||||
dlg, sdk.getComponent('elements.Spinner'),
|
||||
);
|
||||
// there should now be a spinner
|
||||
ReactTestUtils.findRenderedComponentWithType(
|
||||
dlg, sdk.getComponent('elements.Spinner'),
|
||||
);
|
||||
|
||||
// let the request complete
|
||||
q.delay(1).then(() => {
|
||||
// let the request complete
|
||||
return q.delay(1);
|
||||
}).then(() => {
|
||||
expect(onFinished.callCount).toEqual(1);
|
||||
expect(onFinished.calledWithExactly(true, {a:1})).toBe(true);
|
||||
}).done(done, done);
|
||||
}).done(done);
|
||||
});
|
||||
});
|
||||
|
|
|
@ -1,11 +1,51 @@
|
|||
"use strict";
|
||||
|
||||
var sinon = require('sinon');
|
||||
var q = require('q');
|
||||
import sinon from 'sinon';
|
||||
import q from 'q';
|
||||
import ReactTestUtils from 'react-addons-test-utils';
|
||||
|
||||
var peg = require('../src/MatrixClientPeg.js');
|
||||
var jssdk = require('matrix-js-sdk');
|
||||
var MatrixEvent = jssdk.MatrixEvent;
|
||||
import peg from '../src/MatrixClientPeg.js';
|
||||
import jssdk from 'matrix-js-sdk';
|
||||
const MatrixEvent = jssdk.MatrixEvent;
|
||||
|
||||
/**
|
||||
* Wrapper around window.requestAnimationFrame that returns a promise
|
||||
* @private
|
||||
*/
|
||||
function _waitForFrame() {
|
||||
const def = q.defer();
|
||||
window.requestAnimationFrame(() => {
|
||||
def.resolve();
|
||||
});
|
||||
return def.promise;
|
||||
}
|
||||
|
||||
/**
|
||||
* Waits a small number of animation frames for a component to appear
|
||||
* in the DOM. Like findRenderedDOMComponentWithTag(), but allows
|
||||
* for the element to appear a short time later, eg. if a promise needs
|
||||
* to resolve first.
|
||||
* @return a promise that resolves once the component appears, or rejects
|
||||
* if it doesn't appear after a nominal number of animation frames.
|
||||
*/
|
||||
export function waitForRenderedDOMComponentWithTag(tree, tag, attempts) {
|
||||
if (attempts === undefined) {
|
||||
// Let's start by assuming we'll only need to wait a single frame, and
|
||||
// we can try increasing this if necessary.
|
||||
attempts = 1;
|
||||
} else if (attempts == 0) {
|
||||
return q.reject("Gave up waiting for component with tag: " + tag);
|
||||
}
|
||||
|
||||
return _waitForFrame().then(() => {
|
||||
const result = ReactTestUtils.scryRenderedDOMComponentsWithTag(tree, tag);
|
||||
if (result.length > 0) {
|
||||
return result[0];
|
||||
} else {
|
||||
return waitForRenderedDOMComponentWithTag(tree, tag, attempts - 1);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Perform common actions before each test case, e.g. printing the test case
|
||||
|
|
Loading…
Reference in a new issue