diff --git a/ui/lib/core/addon/components/form-field.hbs b/ui/lib/core/addon/components/form-field.hbs
index be08fd2365..2dbc31b997 100644
--- a/ui/lib/core/addon/components/form-field.hbs
+++ b/ui/lib/core/addon/components/form-field.hbs
@@ -219,6 +219,44 @@
{{this.validationError}}
{{/if}}
+ {{else}}
+
+ {{this.labelString}}
+ {{#if this.helpTextString}}
+ {{this.helpTextString}}
+ {{/if}}
+ {{#if @attr.options.subText}}
+
+ {{@attr.options.subText}}
+ {{#if @attr.options.docLink}}
+ See our documentation
+ for help.
+ {{/if}}
+
+ {{/if}}
+ {{#if @attr.options.characterLimit}}
+
+ {{/if}}
+ {{#if this.validationError}}
+ {{this.validationError}}
+ {{/if}}
+
{{/if}}
{{else if (or (eq @attr.type "boolean") (eq @attr.options.editType "boolean"))}}
{{/if}}
- {{else}}
- {{! Regular Text Input }}
-
{{/if}}
{{else if (eq @attr.type "object")}}
diff --git a/ui/lib/core/addon/components/form-field.js b/ui/lib/core/addon/components/form-field.js
index 0f10d92d57..9f018298fd 100644
--- a/ui/lib/core/addon/components/form-field.js
+++ b/ui/lib/core/addon/components/form-field.js
@@ -120,8 +120,10 @@ export default class FormFieldComponent extends Component {
} else if (type === 'number' || type === 'string') {
if (options?.editType === 'textarea' || options?.editType === 'password') {
return true;
- } else {
+ } else if (options?.editType === 'json') {
return false;
+ } else {
+ return true;
}
} else if (type === 'boolean' || options?.editType === 'boolean') {
return true;
diff --git a/ui/tests/acceptance/config-ui/messages/messages-test.js b/ui/tests/acceptance/config-ui/messages/messages-test.js
index f2ae4655f7..b7add218c8 100644
--- a/ui/tests/acceptance/config-ui/messages/messages-test.js
+++ b/ui/tests/acceptance/config-ui/messages/messages-test.js
@@ -245,7 +245,7 @@ module('Acceptance | Enterprise | config-ui/message', function (hooks) {
assert
.dom(CUSTOM_MESSAGES.modal('preview image'))
.doesNotExist('preview image does not show because you have a missing title');
- assert.dom(CUSTOM_MESSAGES.input('title')).hasClass('has-error-border', 'error around title shows');
+ assert.dom(GENERAL.validationErrorByAttr('title')).exists();
});
// unauthenticated messages
@@ -340,7 +340,7 @@ module('Acceptance | Enterprise | config-ui/message', function (hooks) {
await fillIn('[data-test-kv-value="0"]', 'www.learn.com');
await click(GENERAL.button('preview'));
assert.dom(CUSTOM_MESSAGES.modal('preview image')).doesNotExist('preview image does not show');
- assert.dom(CUSTOM_MESSAGES.input('title')).hasClass('has-error-border', 'error around title shows');
+ assert.dom(GENERAL.validationErrorByAttr('title')).exists();
});
test('cleanup message pollution', async function (assert) {
diff --git a/ui/tests/acceptance/mfa-method-test.js b/ui/tests/acceptance/mfa-method-test.js
index 1929cb57fc..64ba06cd8a 100644
--- a/ui/tests/acceptance/mfa-method-test.js
+++ b/ui/tests/acceptance/mfa-method-test.js
@@ -193,7 +193,7 @@ module('Acceptance | mfa-method', function (hooks) {
await click('[data-test-mleh-radio="skip"]');
await click('[data-test-mfa-create-save]');
assert
- .dom('[data-test-inline-error-message]')
+ .dom('[data-test-validation-error]')
.exists({ count: required.length }, `Required field validations display for ${type}`);
for (const field of required) {
diff --git a/ui/tests/acceptance/secrets/backend/kv/kv-v2-workflow-create-test.js b/ui/tests/acceptance/secrets/backend/kv/kv-v2-workflow-create-test.js
index 5f2ff9111f..e6685cd674 100644
--- a/ui/tests/acceptance/secrets/backend/kv/kv-v2-workflow-create-test.js
+++ b/ui/tests/acceptance/secrets/backend/kv/kv-v2-workflow-create-test.js
@@ -84,7 +84,7 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert
.dom(FORM.validationWarning)
@@ -167,9 +167,9 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret
await typeIn(FORM.inputByAttr('path'), 'my/');
- assert.dom(FORM.validation('path')).hasText("Path can't end in forward slash '/'.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't end in forward slash '/'.");
await typeIn(FORM.inputByAttr('path'), 'secret');
- assert.dom(FORM.validation('path')).doesNotExist('form validation goes away');
+ assert.dom(GENERAL.validationErrorByAttr('path')).doesNotExist('form validation goes away');
await fillIn(FORM.keyInput(), 'password');
await fillIn(FORM.maskedValueInput(), 'kittens1234');
@@ -182,10 +182,10 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// MaxVersions validation
await fillIn(FORM.inputByAttr('maxVersions'), 'seven');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('Maximum versions must be a number.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('Maximum versions must be a number.');
await fillIn(FORM.inputByAttr('maxVersions'), '99999999999999999');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('You cannot go over 16 characters.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('You cannot go over 16 characters.');
await fillIn(FORM.inputByAttr('maxVersions'), '7');
// Fill in other metadata
@@ -378,7 +378,7 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert
.dom(FORM.validationWarning)
@@ -425,9 +425,9 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret
await typeIn(FORM.inputByAttr('path'), 'my/');
- assert.dom(FORM.validation('path')).hasText("Path can't end in forward slash '/'.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't end in forward slash '/'.");
await typeIn(FORM.inputByAttr('path'), 'secret');
- assert.dom(FORM.validation('path')).doesNotExist('form validation goes away');
+ assert.dom(GENERAL.validationErrorByAttr('path')).doesNotExist('form validation goes away');
await fillIn(FORM.keyInput(), 'password');
await fillIn(FORM.maskedValueInput(), 'kittens1234');
@@ -440,10 +440,10 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// MaxVersions validation
await fillIn(FORM.inputByAttr('maxVersions'), 'seven');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('Maximum versions must be a number.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('Maximum versions must be a number.');
await fillIn(FORM.inputByAttr('maxVersions'), '99999999999999999');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('You cannot go over 16 characters.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('You cannot go over 16 characters.');
await fillIn(FORM.inputByAttr('maxVersions'), '7');
// Fill in other metadata
@@ -527,7 +527,7 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert
.dom(FORM.validationWarning)
@@ -574,9 +574,9 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret
await typeIn(FORM.inputByAttr('path'), 'my/');
- assert.dom(FORM.validation('path')).hasText("Path can't end in forward slash '/'.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't end in forward slash '/'.");
await typeIn(FORM.inputByAttr('path'), 'secret');
- assert.dom(FORM.validation('path')).doesNotExist('form validation goes away');
+ assert.dom(GENERAL.validationErrorByAttr('path')).doesNotExist('form validation goes away');
await fillIn(FORM.keyInput(), 'password');
await fillIn(FORM.maskedValueInput(), 'kittens1234');
@@ -589,10 +589,10 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// MaxVersions validation
await fillIn(FORM.inputByAttr('maxVersions'), 'seven');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('Maximum versions must be a number.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('Maximum versions must be a number.');
await fillIn(FORM.inputByAttr('maxVersions'), '99999999999999999');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('You cannot go over 16 characters.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('You cannot go over 16 characters.');
await fillIn(FORM.inputByAttr('maxVersions'), '7');
// Fill in other metadata
@@ -678,7 +678,7 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert
.dom(FORM.validationWarning)
@@ -743,9 +743,9 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret
await typeIn(FORM.inputByAttr('path'), 'my/');
- assert.dom(FORM.validation('path')).hasText("Path can't end in forward slash '/'.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't end in forward slash '/'.");
await typeIn(FORM.inputByAttr('path'), 'secret');
- assert.dom(FORM.validation('path')).doesNotExist('form validation goes away');
+ assert.dom(GENERAL.validationErrorByAttr('path')).doesNotExist('form validation goes away');
await fillIn(FORM.keyInput(), 'password');
await fillIn(FORM.maskedValueInput(), 'kittens1234');
@@ -758,10 +758,10 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// MaxVersions validation
await fillIn(FORM.inputByAttr('maxVersions'), 'seven');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('Maximum versions must be a number.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('Maximum versions must be a number.');
await fillIn(FORM.inputByAttr('maxVersions'), '99999999999999999');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('You cannot go over 16 characters.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('You cannot go over 16 characters.');
await fillIn(FORM.inputByAttr('maxVersions'), '7');
// Fill in other metadata
@@ -888,7 +888,7 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert
.dom(FORM.validationWarning)
@@ -971,9 +971,9 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// Create secret
await typeIn(FORM.inputByAttr('path'), 'my/');
- assert.dom(FORM.validation('path')).hasText("Path can't end in forward slash '/'.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't end in forward slash '/'.");
await typeIn(FORM.inputByAttr('path'), 'secret');
- assert.dom(FORM.validation('path')).doesNotExist('form validation goes away');
+ assert.dom(GENERAL.validationErrorByAttr('path')).doesNotExist('form validation goes away');
await fillIn(FORM.keyInput(), 'password');
await fillIn(FORM.maskedValueInput(), 'kittens1234');
@@ -986,10 +986,10 @@ module('Acceptance | kv-v2 workflow | secret and version create', function (hook
// MaxVersions validation
await fillIn(FORM.inputByAttr('maxVersions'), 'seven');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('Maximum versions must be a number.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('Maximum versions must be a number.');
await fillIn(FORM.inputByAttr('maxVersions'), '99999999999999999');
await click(FORM.saveBtn);
- assert.dom(FORM.validation('maxVersions')).hasText('You cannot go over 16 characters.');
+ assert.dom(GENERAL.validationErrorByAttr('maxVersions')).hasText('You cannot go over 16 characters.');
await fillIn(FORM.inputByAttr('maxVersions'), '7');
// Fill in other metadata
@@ -1104,7 +1104,7 @@ path "${this.backend}/metadata/*" {
// Create secret form -- validations
await click(FORM.saveBtn);
assert.dom(FORM.invalidFormAlert).hasText('There is an error with this form.');
- assert.dom(FORM.validation('path')).hasText("Path can't be blank.");
+ assert.dom(GENERAL.validationErrorByAttr('path')).hasText("Path can't be blank.");
await typeIn(FORM.inputByAttr('path'), secretPath);
assert.dom(PAGE.create.metadataSection).doesNotExist('Hides metadata section by default');
diff --git a/ui/tests/helpers/kv/kv-selectors.js b/ui/tests/helpers/kv/kv-selectors.js
index 6edaf6861e..a2ad41876d 100644
--- a/ui/tests/helpers/kv/kv-selectors.js
+++ b/ui/tests/helpers/kv/kv-selectors.js
@@ -117,6 +117,7 @@ export const FORM = {
inlineAlert: '[data-test-inline-alert]',
validation: (attr) => `[data-test-field="${attr}"] [data-test-inline-alert]`,
messageError: '[data-test-message-error]',
+ validationError: (attr) => `[data-test-validation-error="${attr}"]`,
validationWarning: '[data-test-validation-warning]',
invalidFormAlert: '[data-test-invalid-form-alert]',
versionAlert: '[data-test-secret-version-alert]',
diff --git a/ui/tests/integration/components/clients/config-test.js b/ui/tests/integration/components/clients/config-test.js
index c21e6c1c50..9d3971decd 100644
--- a/ui/tests/integration/components/clients/config-test.js
+++ b/ui/tests/integration/components/clients/config-test.js
@@ -78,7 +78,7 @@ module('Integration | Component | client count config', function (hooks) {
await fillIn('[data-test-input="retentionMonths"]', 20);
await click(GENERAL.submitButton);
assert
- .dom('[data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('retentionMonths'))
.hasText(
'Retention period must be greater than or equal to 48.',
'Validation error shows for min retention period'
@@ -86,7 +86,7 @@ module('Integration | Component | client count config', function (hooks) {
await fillIn('[data-test-input="retentionMonths"]', 90);
await click(GENERAL.submitButton);
assert
- .dom('[data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('retentionMonths'))
.hasText(
'Retention period must be less than or equal to 60.',
'Validation error shows for max retention period'
@@ -142,7 +142,7 @@ module('Integration | Component | client count config', function (hooks) {
await fillIn('[data-test-input="retentionMonths"]', 5);
await click(GENERAL.submitButton);
assert
- .dom('[data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('retentionMonths'))
.hasText(
'Retention period must be greater than or equal to 24.',
'Validation error shows for incorrect retention period'
diff --git a/ui/tests/integration/components/config-ui/messages/page/create-and-edit-test.js b/ui/tests/integration/components/config-ui/messages/page/create-and-edit-test.js
index 590b2d6f7d..ffc9eb3746 100644
--- a/ui/tests/integration/components/config-ui/messages/page/create-and-edit-test.js
+++ b/ui/tests/integration/components/config-ui/messages/page/create-and-edit-test.js
@@ -125,15 +125,12 @@ module('Integration | Component | messages/page/create-and-edit', function (hook
});
test('it should have form vaildations', async function (assert) {
+ assert.expect(2);
+
await this.renderComponent();
await click(GENERAL.submitButton);
- assert
- .dom(CUSTOM_MESSAGES.input('title'))
- .hasClass('has-error-border', 'show error border for title field');
- assert
- .dom(`${CUSTOM_MESSAGES.fieldValidation('title')} ${CUSTOM_MESSAGES.inlineErrorMessage}`)
- .hasText('Title is required.');
+ assert.dom(`${GENERAL.validationErrorByAttr('title')}`).hasText('Title is required.');
assert.dom(`${GENERAL.validationErrorByAttr('message')}`).hasText('Message is required.');
});
diff --git a/ui/tests/integration/components/form-field-test.js b/ui/tests/integration/components/form-field-test.js
index 5e5d6b44e3..f8a3c6d66a 100644
--- a/ui/tests/integration/components/form-field-test.js
+++ b/ui/tests/integration/components/form-field-test.js
@@ -107,28 +107,6 @@ module('Integration | Component | form field', function (hooks) {
// LEGACY FORM FIELDS
// ------------------
- test('it renders: string', async function (assert) {
- const [model, spy] = await setup.call(this, createAttr('foo', 'string', { defaultValue: 'default' }));
- assert.strictEqual(component.fields.objectAt(0).labelValue, 'Foo', 'renders a label');
- assert.strictEqual(component.fields.objectAt(0).inputValue, 'default', 'renders default value');
- assert.ok(component.hasInput, 'renders input for string');
- await component.fields.objectAt(0).input('bar').change();
-
- assert.strictEqual(model.get('foo'), 'bar');
- assert.ok(spy.calledWith('foo', 'bar'), 'onChange called with correct args');
- });
-
- test('it renders: number', async function (assert) {
- const [model, spy] = await setup.call(this, createAttr('foo', 'number', { defaultValue: 5 }));
- assert.strictEqual(component.fields.objectAt(0).labelValue, 'Foo', 'renders a label');
- assert.strictEqual(component.fields.objectAt(0).inputValue, '5', 'renders default value');
- assert.ok(component.hasInput, 'renders input for number');
- await component.fields.objectAt(0).input(8).change();
-
- assert.strictEqual(model.get('foo'), '8');
- assert.ok(spy.calledWith('foo', '8'), 'onChange called with correct args');
- });
-
test('it renders: object', async function (assert) {
await setup.call(this, createAttr('foo', 'object'));
assert.dom('[data-test-component="json-editor-title"]').hasText('Foo', 'renders a label');
@@ -283,14 +261,13 @@ module('Integration | Component | form field', function (hooks) {
assert.strictEqual(component.fields.objectAt(0).labelValue, 'Not Foo', 'renders the label from options');
});
- test('it renders a help tooltip and placeholder', async function (assert) {
+ test('it renders a help tooltip', async function (assert) {
await setup.call(
this,
- createAttr('foo', 'string', { helpText: 'Here is some help text', placeholder: 'example::value' })
+ createAttr('foo', 'string', { editType: 'stringArray', helpText: 'Here is some help text' })
);
await component.tooltipTrigger();
assert.ok(component.hasTooltip, 'renders the tooltip component');
- assert.dom(GENERAL.inputByAttr('foo')).hasAttribute('placeholder', 'example::value');
});
test('it should not expand and toggle ttl when default 0s value is present', async function (assert) {
@@ -1207,4 +1184,131 @@ module('Integration | Component | form field', function (hooks) {
.exists('Validation warning renders')
.hasText('Warning message #1 Warning message #2', 'Validation warnings are combined');
});
+
+ // ––––– editType === undefined && (type === 'string' || type === 'number') –––––
+
+ test('it renders: editType=undefined type=string - as Hds::Form::TextInput', async function (assert) {
+ const [model, spy] = await setup.call(this, createAttr('myfield', 'string', { defaultValue: 'default' }));
+ assert
+ .dom('.field [class^="hds-form-field"] input[type="text"].hds-form-text-input')
+ .exists('renders as Hds::Form::TextInput::Field');
+ assert
+ .dom(`input[type=text]`)
+ .exists('renders input[type="text"]')
+ .hasAttribute(
+ 'data-test-input',
+ 'myfield',
+ 'input[type="text"] has correct `data-test-input` attribute'
+ )
+ .hasAttribute('name', 'myfield', 'input[type="text"] has correct `name` attribute')
+ .hasAttribute('id', 'myfield', 'input[type="text"] has correct `id` attribute');
+ assert.dom(GENERAL.fieldLabel()).hasText('Myfield', 'renders the input[type="text"] label');
+ assert.dom(GENERAL.inputByAttr('myfield')).hasValue('default', 'renders default value');
+ await fillIn(GENERAL.inputByAttr('myfield'), 'bar');
+ assert.strictEqual(model.get('myfield'), 'bar');
+ assert.true(spy.calledWith('myfield', 'bar'), 'onChange called with correct args');
+ });
+
+ test('it renders: editType=undefined type=number - as Hds::Form::TextInput', async function (assert) {
+ const [model, spy] = await setup.call(this, createAttr('myfield', 'number', { defaultValue: 123 }));
+ assert
+ .dom('.field [class^="hds-form-field"] input[type="text"].hds-form-text-input')
+ .exists('renders as Hds::Form::TextInput::Field');
+ assert
+ .dom(`input[type=text]`)
+ .exists('renders input[type="text"]')
+ .hasAttribute(
+ 'data-test-input',
+ 'myfield',
+ 'input[type="text"] has correct `data-test-input` attribute'
+ )
+ .hasAttribute('name', 'myfield', 'input[type="text"] has correct `name` attribute')
+ .hasAttribute('id', 'myfield', 'input[type="text"] has correct `id` attribute');
+ assert.dom(GENERAL.fieldLabel()).hasText('Myfield', 'renders the input[type="text"] label');
+ assert.dom(GENERAL.inputByAttr('myfield')).hasValue('123', 'renders default value');
+ await fillIn(GENERAL.inputByAttr('myfield'), 1234);
+ assert.strictEqual(model.get('myfield'), '1234');
+ assert.true(spy.calledWith('myfield', '1234'), 'onChange called with correct args');
+ });
+
+ test('it renders: editType=undefined - with passed characterLimit, docLink, editDisabled, helpText, label, placeholder, subText', async function (assert) {
+ await setup.call(
+ this,
+ createAttr('myfield', 'string', {
+ characterLimit: 10,
+ docLink: '/docs',
+ editDisabled: true,
+ helpText: 'Some helpText',
+ label: 'Custom label',
+ placeholder: 'Custom placeholder',
+ subText: 'Some subText',
+ })
+ );
+ assert.dom(GENERAL.fieldLabel()).hasText('Custom label', 'renders the custom label from options');
+ assert
+ .dom('.hds-form-field__character-count')
+ .containsText('10', 'renders the characterLimit helper text from options');
+ assert
+ .dom(GENERAL.inputByAttr('myfield'))
+ .hasAttribute('placeholder', 'Custom placeholder', 'renders the placeholder from options')
+ .hasAttribute('disabled', '', 'renders the disabled attribute from options')
+ .hasAttribute('maxlength', '10', 'renders the characterLimit from options');
+ assert
+ .dom(GENERAL.helpTextByAttr('Some subText'))
+ .exists('renders `subText` option as HelperText')
+ .hasText(
+ 'Some subText See our documentation for help.',
+ 'renders the right subText string from options'
+ );
+ assert
+ .dom(`${GENERAL.helpTextByAttr('Some subText')} ${GENERAL.docLinkByAttr('/docs')}`)
+ .exists('renders `docLink` option as as link inside the subText');
+ assert
+ .dom(GENERAL.helpTextByAttr('Some helpText'))
+ .exists('renders `helpText` option as HelperText')
+ .hasText('Some helpText', 'renders the right helpText string from options');
+ });
+
+ test('it renders: editType=undefined - with readOnly when mode=edit', async function (assert) {
+ this.setProperties({
+ attr: createAttr('myfield', 'string', { readOnly: true }),
+ mode: 'edit',
+ model: { myfield: false },
+ onChange: () => {},
+ });
+
+ await render(
+ hbs``
+ );
+ assert
+ .dom(GENERAL.inputByAttr('myfield'))
+ .hasAttribute('readonly', '', 'renders the readOnly attribute from options');
+ });
+
+ test('it renders: editType=undefined - with validation errors and warnings', async function (assert) {
+ this.setProperties({
+ attr: createAttr('myfield', 'string'),
+ model: { myfield: false },
+ modelValidations: {
+ myfield: {
+ isValid: false,
+ errors: ['Error message #1', 'Error message #2'],
+ warnings: ['Warning message #1', 'Warning message #2'],
+ },
+ },
+ onChange: () => {},
+ });
+
+ await render(
+ hbs``
+ );
+ assert
+ .dom(GENERAL.validationErrorByAttr('myfield'))
+ .exists('Validation error renders')
+ .hasText('Error message #1 Error message #2', 'Validation errors are combined');
+ assert
+ .dom(GENERAL.validationWarningByAttr('myfield'))
+ .exists('Validation warning renders')
+ .hasText('Warning message #1 Warning message #2', 'Validation warnings are combined');
+ });
});
diff --git a/ui/tests/integration/components/keymgmt/provider-edit-test.js b/ui/tests/integration/components/keymgmt/provider-edit-test.js
index 9aa3fef963..5da7173020 100644
--- a/ui/tests/integration/components/keymgmt/provider-edit-test.js
+++ b/ui/tests/integration/components/keymgmt/provider-edit-test.js
@@ -199,7 +199,7 @@ module('Integration | Component | keymgmt/provider-edit', function (hooks) {
assert.dom(`[${ts}-creds-title]`).doesNotExist('New credentials header hidden in create mode');
await click(`[${ts}-submit]`);
- assert.dom('[data-test-inline-error-message]').exists('Validation error messages shown');
+ assert.dom('[data-test-validation-error]').exists('Validation error messages shown');
await fillIn('[data-test-input="provider"]', 'azurekeyvault');
['client_id', 'client_secret', 'tenant_id'].forEach((prop) => {
diff --git a/ui/tests/integration/components/kubernetes/page/configure-test.js b/ui/tests/integration/components/kubernetes/page/configure-test.js
index 1877ccfb6a..0979db68fa 100644
--- a/ui/tests/integration/components/kubernetes/page/configure-test.js
+++ b/ui/tests/integration/components/kubernetes/page/configure-test.js
@@ -231,7 +231,7 @@ module('Integration | Component | kubernetes | Page::Configure', function (hooks
await click('[data-test-config-save]');
assert
- .dom(`${GENERAL.validationErrorByAttr('kubernetesHost')} [data-test-inline-error-message]`)
+ .dom(GENERAL.validationErrorByAttr('kubernetesHost'))
.hasText('Kubernetes host is required', 'Error renders for required field');
assert.dom('[data-test-alert]').hasText('There is an error with this form.', 'Alert renders');
});
diff --git a/ui/tests/integration/components/kubernetes/page/role/create-and-edit-test.js b/ui/tests/integration/components/kubernetes/page/role/create-and-edit-test.js
index 3981ad397b..5db6ee649f 100644
--- a/ui/tests/integration/components/kubernetes/page/role/create-and-edit-test.js
+++ b/ui/tests/integration/components/kubernetes/page/role/create-and-edit-test.js
@@ -163,7 +163,7 @@ module('Integration | Component | kubernetes | Page::Role::CreateAndEdit', funct
);
await click('[data-test-radio-card="basic"]');
await click('[data-test-submit]');
- assert.dom('[data-test-inline-error-message]').hasText('Name is required', 'Validation error renders');
+ assert.dom(GENERAL.validationErrorByAttr('name')).hasText('Name is required', 'Validation error renders');
await fillIn('[data-test-input="name"]', 'role-1');
await fillIn('[data-test-input="serviceAccountName"]', 'default');
await click('[data-test-submit]');
@@ -327,10 +327,7 @@ module('Integration | Component | kubernetes | Page::Role::CreateAndEdit', funct
);
await click('[data-test-radio-card="basic"]');
await click('[data-test-submit]');
- assert
- .dom('[data-test-input="name"]')
- .hasClass('has-error-border', 'shows border error on input with error');
- assert.dom('[data-test-inline-error-message]').hasText('Name is required');
+ assert.dom(GENERAL.validationErrorByAttr('name')).hasText('Name is required');
assert
.dom('[data-test-invalid-form-alert] [data-test-inline-error-message]')
.hasText('There is an error with this form.');
diff --git a/ui/tests/integration/components/kv/page/kv-page-metadata-edit-test.js b/ui/tests/integration/components/kv/page/kv-page-metadata-edit-test.js
index 6cef2ea9f3..871d67e5c0 100644
--- a/ui/tests/integration/components/kv/page/kv-page-metadata-edit-test.js
+++ b/ui/tests/integration/components/kv/page/kv-page-metadata-edit-test.js
@@ -148,7 +148,7 @@ module('Integration | Component | kv | Page::Secret::Metadata::Edit', function (
await fillIn(FORM.inputByAttr('maxVersions'), 'a');
await click(FORM.saveBtn);
assert
- .dom(FORM.inlineAlert)
+ .dom(FORM.validationError('maxVersions'))
.hasText('Maximum versions must be a number.', 'Validation message is shown for max_versions');
await click(FORM.cancelBtn);
diff --git a/ui/tests/integration/components/kv/page/kv-page-secrets-create-test.js b/ui/tests/integration/components/kv/page/kv-page-secrets-create-test.js
index 59049ff26e..06fdd036bc 100644
--- a/ui/tests/integration/components/kv/page/kv-page-secrets-create-test.js
+++ b/ui/tests/integration/components/kv/page/kv-page-secrets-create-test.js
@@ -9,7 +9,7 @@ import { setupEngine } from 'ember-engines/test-support';
import { setupMirage } from 'ember-cli-mirage/test-support';
import { Response } from 'miragejs';
import { hbs } from 'ember-cli-htmlbars';
-import { click, fillIn, findAll, render, typeIn } from '@ember/test-helpers';
+import { click, fillIn, render, typeIn } from '@ember/test-helpers';
import codemirror from 'vault/tests/helpers/codemirror';
import { FORM } from 'vault/tests/helpers/kv/kv-selectors';
import sinon from 'sinon';
@@ -242,11 +242,11 @@ module('Integration | Component | kv-v2 | Page::Secrets::Create', function (hook
await fillIn(FORM.inputByAttr('path'), ''); // clear input
await typeIn(FORM.inputByAttr('path'), 'slash/');
- assert.dom(FORM.validation('path')).hasText(`Path can't end in forward slash '/'.`);
+ assert.dom(FORM.validationError('path')).hasText(`Path can't end in forward slash '/'.`);
await typeIn(FORM.inputByAttr('path'), 'secret');
assert
- .dom(FORM.validation('path'))
+ .dom(FORM.validationError('path'))
.doesNotExist('it removes validation on key up when secret contains slash but does not end in one');
await click(GENERAL.toggleInput('json'));
@@ -258,9 +258,8 @@ module('Integration | Component | kv-v2 | Page::Secrets::Create', function (hook
codemirror().setValue('{}'); // clear linting error
await fillIn(FORM.inputByAttr('path'), '');
await click(FORM.saveBtn);
- const [pathValidation, formAlert] = findAll(FORM.inlineAlert);
- assert.dom(pathValidation).hasText(`Path can't be blank.`);
- assert.dom(formAlert).hasText('There is an error with this form.');
+ assert.dom(FORM.validationError('path')).hasText(`Path can't be blank.`);
+ assert.dom(FORM.inlineAlert).hasText('There is an error with this form.');
});
test('it toggles JSON view and saves modified data', async function (assert) {
diff --git a/ui/tests/integration/components/ldap/page/configure-test.js b/ui/tests/integration/components/ldap/page/configure-test.js
index 681f43048e..bdc270360f 100644
--- a/ui/tests/integration/components/ldap/page/configure-test.js
+++ b/ui/tests/integration/components/ldap/page/configure-test.js
@@ -81,10 +81,10 @@ module('Integration | Component | ldap | Page::Configure', function (hooks) {
await click(selectors.save);
assert
- .dom('[data-test-field="binddn"] [data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('binddn'))
.hasText('Administrator distinguished name is required.', 'Validation message renders for binddn');
assert
- .dom('[data-test-field="bindpass"] [data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('bindpass'))
.hasText('Administrator password is required.', 'Validation message renders for bindpass');
assert
.dom('[data-test-invalid-form-message]')
diff --git a/ui/tests/integration/components/ldap/page/role/create-and-edit-test.js b/ui/tests/integration/components/ldap/page/role/create-and-edit-test.js
index 9a6f10c99a..566c1474f7 100644
--- a/ui/tests/integration/components/ldap/page/role/create-and-edit-test.js
+++ b/ui/tests/integration/components/ldap/page/role/create-and-edit-test.js
@@ -11,6 +11,7 @@ import { render, click, fillIn } from '@ember/test-helpers';
import hbs from 'htmlbars-inline-precompile';
import sinon from 'sinon';
import { ldapRoleID } from 'vault/adapters/ldap/role';
+import { GENERAL } from 'vault/tests/helpers/general-selectors';
module('Integration | Component | ldap | Page::Role::CreateAndEdit', function (hooks) {
setupRenderingTest(hooks);
@@ -135,9 +136,7 @@ module('Integration | Component | ldap | Page::Role::CreateAndEdit', function (h
await click('[data-test-submit]');
fields.forEach((field) => {
- assert
- .dom(`[data-test-field="${field}"] [data-test-inline-error-message]`)
- .exists('Validation message renders');
+ assert.dom(GENERAL.validationErrorByAttr(field)).exists('Validation message renders');
});
assert
diff --git a/ui/tests/integration/components/oidc/client-form-test.js b/ui/tests/integration/components/oidc/client-form-test.js
index b144b80a0d..17636b1289 100644
--- a/ui/tests/integration/components/oidc/client-form-test.js
+++ b/ui/tests/integration/components/oidc/client-form-test.js
@@ -102,10 +102,12 @@ module('Integration | Component | oidc/client-form', function (hooks) {
const validationErrors = findAll(SELECTORS.inlineAlert);
assert
- .dom(validationErrors[0])
+ .dom(GENERAL.validationErrorByAttr('name'))
.hasText('Name is required. Name cannot contain whitespace.', 'Validation messages are shown for name');
- assert.dom(validationErrors[1]).hasText('Key is required.', 'Validation message is shown for key');
- assert.dom(validationErrors[2]).hasText('There are 3 errors with this form.', 'Renders form error count');
+ assert
+ .dom(GENERAL.validationErrorByAttr('key'))
+ .hasText('Key is required.', 'Validation message is shown for key');
+ assert.dom(validationErrors[1]).hasText('There are 3 errors with this form.', 'Renders form error count');
// fill out form with valid inputs
await clickTrigger();
diff --git a/ui/tests/integration/components/oidc/key-form-test.js b/ui/tests/integration/components/oidc/key-form-test.js
index 55b5c297d8..3b3859ced7 100644
--- a/ui/tests/integration/components/oidc/key-form-test.js
+++ b/ui/tests/integration/components/oidc/key-form-test.js
@@ -12,6 +12,7 @@ import oidcConfigHandlers from 'vault/mirage/handlers/oidc-config';
import { OIDC_BASE_URL, CLIENT_LIST_RESPONSE, SELECTORS } from 'vault/tests/helpers/oidc-config';
import { setRunOptions } from 'ember-a11y-testing/test-support';
import { capabilitiesStub, overrideResponse } from 'vault/tests/helpers/stubs';
+import { GENERAL } from 'vault/tests/helpers/general-selectors';
module('Integration | Component | oidc/key-form', function (hooks) {
setupRenderingTest(hooks);
@@ -57,11 +58,12 @@ module('Integration | Component | oidc/key-form', function (hooks) {
await fillIn('[data-test-input="name"]', ' ');
await click(SELECTORS.keySaveButton);
- const validationErrors = findAll(SELECTORS.inlineAlert);
assert
- .dom(validationErrors[0])
+ .dom(GENERAL.validationErrorByAttr('name'))
.hasText('Name is required. Name cannot contain whitespace.', 'Validation messages are shown for name');
- assert.dom(validationErrors[1]).hasText('There are 2 errors with this form.', 'Renders form error count');
+ assert
+ .dom(SELECTORS.inlineAlert)
+ .hasText('There are 2 errors with this form.', 'Renders form error count');
assert.dom('[data-test-oidc-radio="limited"] input').isDisabled('limit radio button disabled on create');
await fillIn('[data-test-input="name"]', 'test-key');
diff --git a/ui/tests/integration/components/oidc/provider-form-test.js b/ui/tests/integration/components/oidc/provider-form-test.js
index 538d75abf9..ee7cdb44a3 100644
--- a/ui/tests/integration/components/oidc/provider-form-test.js
+++ b/ui/tests/integration/components/oidc/provider-form-test.js
@@ -13,6 +13,7 @@ import { SELECTORS, OIDC_BASE_URL, CLIENT_LIST_RESPONSE } from 'vault/tests/help
import parseURL from 'core/utils/parse-url';
import { setRunOptions } from 'ember-a11y-testing/test-support';
import { capabilitiesStub, overrideResponse } from 'vault/tests/helpers/stubs';
+import { GENERAL } from 'vault/tests/helpers/general-selectors';
const ISSUER_URL = 'http://127.0.0.1:8200/v1/identity/oidc/provider/test-provider';
@@ -81,11 +82,12 @@ module('Integration | Component | oidc/provider-form', function (hooks) {
await fillIn('[data-test-input="name"]', ' ');
await click(SELECTORS.providerSaveButton);
- const validationErrors = findAll(SELECTORS.inlineAlert);
assert
- .dom(validationErrors[0])
+ .dom(GENERAL.validationErrorByAttr('name'))
.hasText('Name is required. Name cannot contain whitespace.', 'Validation messages are shown for name');
- assert.dom(validationErrors[1]).hasText('There are 2 errors with this form.', 'Renders form error count');
+ assert
+ .dom(SELECTORS.inlineAlert)
+ .hasText('There are 2 errors with this form.', 'Renders form error count');
await click('[data-test-oidc-radio="limited"]');
assert
diff --git a/ui/tests/integration/components/oidc/scope-form-test.js b/ui/tests/integration/components/oidc/scope-form-test.js
index a2454434d1..987673904f 100644
--- a/ui/tests/integration/components/oidc/scope-form-test.js
+++ b/ui/tests/integration/components/oidc/scope-form-test.js
@@ -5,11 +5,12 @@
import { module, test } from 'qunit';
import { setupRenderingTest } from 'ember-qunit';
-import { render, fillIn, click, findAll } from '@ember/test-helpers';
+import { render, fillIn, click } from '@ember/test-helpers';
import { hbs } from 'ember-cli-htmlbars';
import { setupMirage } from 'ember-cli-mirage/test-support';
import { SELECTORS, OIDC_BASE_URL } from 'vault/tests/helpers/oidc-config';
import { capabilitiesStub } from 'vault/tests/helpers/stubs';
+import { GENERAL } from 'vault/tests/helpers/general-selectors';
module('Integration | Component | oidc/scope-form', function (hooks) {
setupRenderingTest(hooks);
@@ -20,7 +21,7 @@ module('Integration | Component | oidc/scope-form', function (hooks) {
});
test('it should save new scope', async function (assert) {
- assert.expect(9);
+ assert.expect(8);
this.server.post('/identity/oidc/scope/test', (schema, req) => {
assert.ok(true, 'Request made to save scope');
@@ -45,13 +46,13 @@ module('Integration | Component | oidc/scope-form', function (hooks) {
// check validation errors
await click(SELECTORS.scopeSaveButton);
- const validationErrors = findAll(SELECTORS.inlineAlert);
- assert.dom(validationErrors[0]).hasText('Name is required.', 'Validation messages are shown for name');
- assert.dom(validationErrors[1]).hasText('There is an error with this form.', 'Renders form error count');
-
assert
- .dom('[data-test-inline-error-message]')
- .hasText('Name is required.', 'Validation message is shown for name');
+ .dom(GENERAL.validationErrorByAttr('name'))
+ .hasText('Name is required.', 'Validation messages are shown for name');
+ assert
+ .dom(SELECTORS.inlineAlert)
+ .hasText('There is an error with this form.', 'Renders form error count');
+
// json editor has test coverage so let's just confirm that it renders
assert
.dom('[data-test-input="template"] [data-test-component="json-editor-toolbar"]')
diff --git a/ui/tests/integration/components/pki/page/pki-issuer-rotate-root-test.js b/ui/tests/integration/components/pki/page/pki-issuer-rotate-root-test.js
index 47d68d5733..9ca7869869 100644
--- a/ui/tests/integration/components/pki/page/pki-issuer-rotate-root-test.js
+++ b/ui/tests/integration/components/pki/page/pki-issuer-rotate-root-test.js
@@ -126,12 +126,8 @@ module('Integration | Component | page/pki-issuer-rotate-root', function (hooks)
await fillIn(GENERAL.inputByAttr('issuerName'), 'default');
await click(GENERAL.submitButton);
assert.dom(SELECTORS.validationError).hasText('There are 2 errors with this form.');
- assert
- .dom(GENERAL.inputByAttr('commonName'))
- .hasClass('has-error-border', 'common name has error border');
- assert
- .dom(GENERAL.inputByAttr('issuerName'))
- .hasClass('has-error-border', 'issuer name has error border');
+ assert.dom(GENERAL.validationErrorByAttr('commonName')).exists();
+ assert.dom(GENERAL.validationErrorByAttr('issuerName')).exists();
});
test('it sends request to rotate/internal on save when using old root settings', async function (assert) {
diff --git a/ui/tests/integration/components/pki/pki-generate-csr-test.js b/ui/tests/integration/components/pki/pki-generate-csr-test.js
index 2898ebfa6f..79b7280e59 100644
--- a/ui/tests/integration/components/pki/pki-generate-csr-test.js
+++ b/ui/tests/integration/components/pki/pki-generate-csr-test.js
@@ -105,7 +105,7 @@ module('Integration | Component | pki-generate-csr', function (hooks) {
.dom(GENERAL.validationErrorByAttr('type'))
.hasText('Type is required.', 'Type validation error renders');
assert
- .dom('[data-test-field="commonName"] [data-test-inline-alert]')
+ .dom(GENERAL.validationErrorByAttr('commonName'))
.hasText('Common name is required.', 'Common name validation error renders');
assert.dom('[data-test-alert]').hasText('There are 2 errors with this form.', 'Alert renders');
diff --git a/ui/tests/integration/components/pki/pki-role-form-test.js b/ui/tests/integration/components/pki/pki-role-form-test.js
index 1796e62b3a..4973ad9332 100644
--- a/ui/tests/integration/components/pki/pki-role-form-test.js
+++ b/ui/tests/integration/components/pki/pki-role-form-test.js
@@ -86,7 +86,7 @@ module('Integration | Component | pki-role-form', function (hooks) {
test('it should save a new pki role with various options selected', async function (assert) {
// Key usage, Key params and Not valid after options are tested in their respective component tests
- assert.expect(8);
+ assert.expect(7);
this.server.post(`/${this.role.backend}/roles/test-role`, (schema, req) => {
assert.ok(true, 'Request made to save role');
const request = JSON.parse(req.requestBody);
@@ -123,10 +123,7 @@ module('Integration | Component | pki-role-form', function (hooks) {
await click(GENERAL.submitButton);
assert
- .dom(GENERAL.inputByAttr('name'))
- .hasClass('has-error-border', 'shows border error on role name field when no role name is submitted');
- assert
- .dom('[data-test-inline-error-message]')
+ .dom(GENERAL.validationErrorByAttr('name'))
.includesText('Name is required.', 'show correct error message');
await fillIn(GENERAL.inputByAttr('name'), 'test-role');
diff --git a/ui/tests/integration/components/secret-engine/configure-ssh-test.js b/ui/tests/integration/components/secret-engine/configure-ssh-test.js
index 407ebeb56c..6b74d9068e 100644
--- a/ui/tests/integration/components/secret-engine/configure-ssh-test.js
+++ b/ui/tests/integration/components/secret-engine/configure-ssh-test.js
@@ -65,7 +65,7 @@ module('Integration | Component | SecretEngine/configure-ssh', function (hooks)
await fillIn(GENERAL.inputByAttr('publicKey'), 'hello');
await click(GENERAL.submitButton);
assert
- .dom(GENERAL.inlineError)
+ .dom(GENERAL.validationErrorByAttr('publicKey'))
.hasText(
'You must provide a Public and Private keys or leave both unset.',
'Public key validation error renders.'
@@ -74,9 +74,9 @@ module('Integration | Component | SecretEngine/configure-ssh', function (hooks)
await click(GENERAL.inputByAttr('generateSigningKey'));
await click(GENERAL.submitButton);
assert
- .dom(GENERAL.inlineError)
+ .dom(GENERAL.validationErrorByAttr('generateSigningKey'))
.hasText(
- 'You must provide a Public and Private keys or leave both unset.',
+ 'Provide a Public and Private key or set "Generate Signing Key" to true.',
'Generate signing key validation message shows.'
);
});
diff --git a/ui/tests/integration/components/totp/key-form-test.js b/ui/tests/integration/components/totp/key-form-test.js
index 7a00ef01c7..261ff353e2 100644
--- a/ui/tests/integration/components/totp/key-form-test.js
+++ b/ui/tests/integration/components/totp/key-form-test.js
@@ -5,7 +5,7 @@
import { module, test } from 'qunit';
import { setupRenderingTest } from 'ember-qunit';
-import { render, fillIn, click, findAll } from '@ember/test-helpers';
+import { render, fillIn, click } from '@ember/test-helpers';
import { hbs } from 'ember-cli-htmlbars';
import { setupMirage } from 'ember-cli-mirage/test-support';
import { GENERAL } from 'vault/tests/helpers/general-selectors';
@@ -57,21 +57,22 @@ module('Integration | Component | totp/key-form', function (hooks) {
// check validation errors
await click(GENERAL.submitButton);
- const validationErrors = findAll(GENERAL.inlineAlert);
- assert.dom(validationErrors[0]).hasText(`Name can't be blank.`, 'Validation messages are shown for name');
assert
- .dom(validationErrors[1])
+ .dom(GENERAL.validationErrorByAttr('name'))
+ .hasText(`Name can't be blank.`, 'Validation messages are shown for name');
+ assert
+ .dom(GENERAL.validationErrorByAttr('issuer'))
.hasText(
`Issuer can't be blank when when the key is generated by Vault.`,
'Validation messages are shown for issuer'
);
assert
- .dom(validationErrors[2])
+ .dom(GENERAL.validationErrorByAttr('accountName'))
.hasText(
`Account name can't be blank when the key is generated by Vault.`,
'Validation messages are shown for account name'
);
- assert.dom(validationErrors[3]).hasText('There are 3 errors with this form.', 'Renders form error count');
+ assert.dom(GENERAL.inlineAlert).hasText('There are 3 errors with this form.', 'Renders form error count');
await fillIn('[data-test-input="name"]', 'test-key');
await fillIn('[data-test-input="issuer"]', 'test-issuer');
@@ -117,15 +118,16 @@ module('Integration | Component | totp/key-form', function (hooks) {
// check validation errors
await click(GENERAL.submitButton);
- const validationErrors = findAll(GENERAL.inlineAlert);
- assert.dom(validationErrors[0]).hasText(`Name can't be blank.`, 'Validation messages are shown for name');
assert
- .dom(validationErrors[1])
+ .dom(GENERAL.validationErrorByAttr('name'))
+ .hasText(`Name can't be blank.`, 'Validation messages are shown for name');
+ assert
+ .dom(GENERAL.validationErrorByAttr('key'))
.hasText(
`Key can't be blank if key is being passed from another service and the URL is empty.`,
'Validation messages are shown for issuer'
);
- assert.dom(validationErrors[2]).hasText('There are 2 errors with this form.', 'Renders form error count');
+ assert.dom(GENERAL.inlineAlert).hasText('There are 2 errors with this form.', 'Renders form error count');
await fillIn('[data-test-input="name"]', 'test-key');
await fillIn('[data-test-input="key"]', 'test-root-key');
diff --git a/ui/tests/integration/helpers/transition-to-test.js b/ui/tests/integration/helpers/transition-to-test.js
index 32b7e35ac6..57e9926f09 100644
--- a/ui/tests/integration/helpers/transition-to-test.js
+++ b/ui/tests/integration/helpers/transition-to-test.js
@@ -25,7 +25,9 @@ module('Integration | Helper | transition-to', function (hooks) {
});
test('it does not call transition on render', async function (assert) {
- await render(hbs``);
+ await render(
+ hbs``
+ );
assert.true(this.router.transitionTo.notCalled, 'transitionTo not called on render');
assert.true(this.router.transitionToExternal.notCalled, 'transitionToExternal not called on render');
@@ -33,7 +35,7 @@ module('Integration | Helper | transition-to', function (hooks) {
test('it calls transitionTo correctly', async function (assert) {
await render(
- hbs``
+ hbs``
);
await click('[data-test-btn]');
@@ -48,7 +50,7 @@ module('Integration | Helper | transition-to', function (hooks) {
test('it calls transitionToExternal correctly', async function (assert) {
await render(
- hbs``
+ hbs``
);
await click('[data-test-btn]');
@@ -68,7 +70,7 @@ module('Integration | Helper | transition-to', function (hooks) {
// This test passing, indirectly means the helper works as expected. Failures might be something like "global failure: TypeError: this.router is undefined"
test('it uses service:app-router when base router undefined', async function (assert) {
await render(
- hbs``,
+ hbs``,
{ owner: this.engine }
);
await click('[data-test-btn]');