29de8f4f76
This continues #8455 by adding accessibility audits to component integration tests and fixing associated errors. It adds audits to existing tests rather than adding separate ones to facilitate auditing the various permutations a component’s rendering can go through. It also adds linting to ensure audits happen in component tests. This necessitated consolidating test files that were scattered.
222 lines
6.5 KiB
JavaScript
222 lines
6.5 KiB
JavaScript
import { find, render, settled, triggerEvent, waitUntil } from '@ember/test-helpers';
|
|
import { module, test } from 'qunit';
|
|
import { setupRenderingTest } from 'ember-qunit';
|
|
import hbs from 'htmlbars-inline-precompile';
|
|
import { componentA11yAudit } from 'nomad-ui/tests/helpers/a11y-audit';
|
|
import sinon from 'sinon';
|
|
import { create } from 'ember-cli-page-object';
|
|
import stepperInput from 'nomad-ui/tests/pages/components/stepper-input';
|
|
|
|
const StepperInput = create(stepperInput());
|
|
const valueChange = () => {
|
|
const initial = StepperInput.input.value;
|
|
return () => StepperInput.input.value !== initial;
|
|
};
|
|
|
|
module('Integration | Component | stepper input', function(hooks) {
|
|
setupRenderingTest(hooks);
|
|
|
|
const commonProperties = () => ({
|
|
min: 0,
|
|
max: 10,
|
|
value: 5,
|
|
label: 'Stepper',
|
|
classVariant: 'is-primary',
|
|
disabled: false,
|
|
onChange: sinon.spy(),
|
|
});
|
|
|
|
const commonTemplate = hbs`
|
|
<StepperInput
|
|
@debounce=50
|
|
@min={{min}}
|
|
@max={{max}}
|
|
@value={{value}}
|
|
@class={{classVariant}}
|
|
@disabled={{disabled}}
|
|
@onChange={{onChange}}>
|
|
{{label}}
|
|
</StepperInput>
|
|
`;
|
|
|
|
test('basic appearance includes a label, an input, and two buttons', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
|
|
await render(commonTemplate);
|
|
|
|
assert.equal(StepperInput.label, this.label);
|
|
assert.equal(StepperInput.input.value, this.value);
|
|
assert.ok(StepperInput.decrement.isPresent);
|
|
assert.ok(StepperInput.increment.isPresent);
|
|
assert.ok(StepperInput.decrement.classNames.split(' ').includes(this.classVariant));
|
|
assert.ok(StepperInput.increment.classNames.split(' ').includes(this.classVariant));
|
|
|
|
await componentA11yAudit(this.element, assert);
|
|
});
|
|
|
|
test('clicking the increment and decrement buttons immediately changes the shown value in the input but debounces the onUpdate call', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
|
|
const baseValue = this.value;
|
|
|
|
await render(commonTemplate);
|
|
|
|
StepperInput.increment.click();
|
|
await waitUntil(valueChange());
|
|
assert.equal(StepperInput.input.value, baseValue + 1);
|
|
assert.notOk(this.onChange.called);
|
|
|
|
StepperInput.decrement.click();
|
|
await waitUntil(valueChange());
|
|
assert.equal(StepperInput.input.value, baseValue);
|
|
assert.notOk(this.onChange.called);
|
|
|
|
StepperInput.decrement.click();
|
|
await waitUntil(valueChange());
|
|
assert.equal(StepperInput.input.value, baseValue - 1);
|
|
assert.notOk(this.onChange.called);
|
|
|
|
await settled();
|
|
assert.ok(this.onChange.calledWith(baseValue - 1));
|
|
});
|
|
|
|
test('the increment button is disabled when the internal value is the max value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
this.set('value', this.max);
|
|
|
|
await render(commonTemplate);
|
|
|
|
assert.ok(StepperInput.increment.isDisabled);
|
|
});
|
|
|
|
test('the decrement button is disabled when the internal value is the min value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
this.set('value', this.min);
|
|
|
|
await render(commonTemplate);
|
|
|
|
assert.ok(StepperInput.decrement.isDisabled);
|
|
});
|
|
|
|
test('the text input does not call the onUpdate function on oninput', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
const newValue = 8;
|
|
|
|
await render(commonTemplate);
|
|
|
|
const input = find('[data-test-stepper-input]');
|
|
|
|
input.value = newValue;
|
|
assert.equal(StepperInput.input.value, newValue);
|
|
assert.notOk(this.onChange.called);
|
|
|
|
await triggerEvent(input, 'input');
|
|
assert.equal(StepperInput.input.value, newValue);
|
|
assert.notOk(this.onChange.called);
|
|
|
|
await triggerEvent(input, 'change');
|
|
assert.equal(StepperInput.input.value, newValue);
|
|
assert.ok(this.onChange.calledWith(newValue));
|
|
});
|
|
|
|
test('the text input does call the onUpdate function on onchange', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
const newValue = 8;
|
|
|
|
await render(commonTemplate);
|
|
|
|
await StepperInput.input.fill(newValue);
|
|
|
|
await settled();
|
|
assert.equal(StepperInput.input.value, newValue);
|
|
assert.ok(this.onChange.calledWith(newValue));
|
|
});
|
|
|
|
test('text input limits input to the bounds of the min/max range', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
let newValue = this.max + 1;
|
|
|
|
await render(commonTemplate);
|
|
|
|
await StepperInput.input.fill(newValue);
|
|
await settled();
|
|
|
|
assert.equal(StepperInput.input.value, this.max);
|
|
assert.ok(this.onChange.calledWith(this.max));
|
|
|
|
newValue = this.min - 1;
|
|
|
|
await StepperInput.input.fill(newValue);
|
|
await settled();
|
|
|
|
assert.equal(StepperInput.input.value, this.min);
|
|
assert.ok(this.onChange.calledWith(this.min));
|
|
});
|
|
|
|
test('pressing ESC in the text input reverts the text value back to the current value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
const newValue = 8;
|
|
|
|
await render(commonTemplate);
|
|
|
|
const input = find('[data-test-stepper-input]');
|
|
|
|
input.value = newValue;
|
|
assert.equal(StepperInput.input.value, newValue);
|
|
|
|
await StepperInput.input.esc();
|
|
assert.equal(StepperInput.input.value, this.value);
|
|
});
|
|
|
|
test('clicking the label focuses in the input', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
|
|
await render(commonTemplate);
|
|
await StepperInput.clickLabel();
|
|
|
|
const input = find('[data-test-stepper-input]');
|
|
assert.equal(document.activeElement, input);
|
|
});
|
|
|
|
test('focusing the input selects the input value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
|
|
await render(commonTemplate);
|
|
await StepperInput.input.focus();
|
|
|
|
assert.equal(
|
|
window
|
|
.getSelection()
|
|
.toString()
|
|
.trim(),
|
|
this.value.toString()
|
|
);
|
|
});
|
|
|
|
test('entering a fractional value floors the value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
const newValue = 3.14159;
|
|
|
|
await render(commonTemplate);
|
|
|
|
await StepperInput.input.fill(newValue);
|
|
|
|
await settled();
|
|
assert.equal(StepperInput.input.value, Math.floor(newValue));
|
|
assert.ok(this.onChange.calledWith(Math.floor(newValue)));
|
|
});
|
|
|
|
test('entering an invalid value reverts the value', async function(assert) {
|
|
this.setProperties(commonProperties());
|
|
const newValue = 'NaN';
|
|
|
|
await render(commonTemplate);
|
|
|
|
await StepperInput.input.fill(newValue);
|
|
|
|
await settled();
|
|
assert.equal(StepperInput.input.value, this.value);
|
|
assert.notOk(this.onChange.called);
|
|
});
|
|
});
|