Skip to content

Commit

Permalink
fix(Field): show error state without error object if parent FieldBloc…
Browse files Browse the repository at this point in the history
…k has error (#3225)

Fixes #2958

Inputs in FieldBlock with errors now show that they have error

---------

Co-authored-by: Tobias Høegh <tobias@tujo.no>
  • Loading branch information
snorrekim and tujoworker authored Jan 17, 2024
1 parent 7c79a54 commit 35fe238
Show file tree
Hide file tree
Showing 13 changed files with 414 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { render, fireEvent, screen } from '@testing-library/react'
import ArraySelection from '../ArraySelection'
import Option from '../../Option'
import { FormError } from '../../../types'
import { FieldBlock } from '../../..'

describe('ArraySelection', () => {
it('renders correctly', () => {
Expand Down Expand Up @@ -199,4 +200,108 @@ describe('ArraySelection', () => {
expect(option2).toBeDisabled()
})
})

describe('checkbox', () => {
it('renders error', () => {
render(
<ArraySelection error={new FormError('Error message')}>
<Option value="A" title="Fooo!" />
<Option value="B" title="Baar!" />
<Option value="C" title="Bazz!" />
<Option value="D" title="Quxx!" />
</ArraySelection>
)

const element = document.querySelector('.dnb-form-status')
expect(element).toHaveTextContent('Error message')

const [optionA, optionB, optionC, optionD]: Array<HTMLElement> =
Array.from(document.querySelectorAll('.dnb-checkbox'))
expect(optionA).toHaveClass('dnb-checkbox__status--error')
expect(optionB).toHaveClass('dnb-checkbox__status--error')
expect(optionC).toHaveClass('dnb-checkbox__status--error')
expect(optionD).toHaveClass('dnb-checkbox__status--error')
})

it('shows error style in FieldBlock', () => {
render(
<FieldBlock>
<ArraySelection error={new FormError('Error message')}>
<Option value="A" title="Fooo!" />
<Option value="B" title="Baar!" />
<Option value="C" title="Bazz!" />
<Option value="D" title="Quxx!" />
</ArraySelection>
</FieldBlock>
)

const [optionA, optionB, optionC, optionD]: Array<HTMLElement> =
Array.from(document.querySelectorAll('.dnb-checkbox'))
expect(optionA).toHaveClass('dnb-checkbox__status--error')
expect(optionB).toHaveClass('dnb-checkbox__status--error')
expect(optionC).toHaveClass('dnb-checkbox__status--error')
expect(optionD).toHaveClass('dnb-checkbox__status--error')
})
})

describe('button', () => {
it('renders error', () => {
render(
<ArraySelection
variant="button"
error={new FormError('Error message')}
>
<Option value="A" title="Fooo!" />
<Option value="B" title="Baar!" />
<Option value="C" title="Bazz!" />
<Option value="D" title="Quxx!" />
</ArraySelection>
)

const element = document.querySelector('.dnb-form-status')
expect(element).toHaveTextContent('Error message')

const [
optionA,
optionB,
optionC,
optionD,
]: Array<HTMLButtonElement> = Array.from(
document.querySelectorAll('.dnb-toggle-button')
)
expect(optionA).toHaveClass('dnb-toggle-button__status--error')
expect(optionB).toHaveClass('dnb-toggle-button__status--error')
expect(optionC).toHaveClass('dnb-toggle-button__status--error')
expect(optionD).toHaveClass('dnb-toggle-button__status--error')
})

it('shows error style in FieldBlock', () => {
render(
<FieldBlock>
<ArraySelection
variant="button"
error={new FormError('Error message')}
>
<Option value="A" title="Fooo!" />
<Option value="B" title="Baar!" />
<Option value="C" title="Bazz!" />
<Option value="D" title="Quxx!" />
</ArraySelection>
</FieldBlock>
)

const [
optionA,
optionB,
optionC,
optionD,
]: Array<HTMLButtonElement> = Array.from(
document.querySelectorAll('.dnb-toggle-button')
)
expect(optionA).toHaveClass('dnb-toggle-button__status--error')
expect(optionB).toHaveClass('dnb-toggle-button__status--error')
expect(optionC).toHaveClass('dnb-toggle-button__status--error')
expect(optionD).toHaveClass('dnb-toggle-button__status--error')
})
})
})
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { render, waitFor, screen, fireEvent } from '@testing-library/react'
import Date from '..'
import userEvent from '@testing-library/user-event'
import { axeComponent } from '../../../../../core/jest/jestSetup'
import { FormError, FieldBlock } from '../../..'

describe('Field.Date', () => {
it('should render with props', () => {
Expand Down Expand Up @@ -89,4 +90,25 @@ describe('Field.Date', () => {
expect(await axeComponent(result)).toHaveNoViolations()
})
})

it('renders error', () => {
render(<Date error={new FormError('Error message')} />)

const element = document.querySelector('.dnb-form-status')
expect(element).toHaveTextContent('Error message')

const input = document.querySelector('.dnb-date-picker')
expect(input).toHaveClass('dnb-date-picker__status--error')
})

it('shows error style in FieldBlock', () => {
render(
<FieldBlock>
<Date error={new FormError('Error message')} />
</FieldBlock>
)

const input = document.querySelector('.dnb-date-picker')
expect(input).toHaveClass('dnb-date-picker__status--error')
})
})
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ function Expiry(props: ExpiryProps) {
className,
label = translations.expiryLabel,
error,
hasError,
info,
warning,
help,
Expand All @@ -68,7 +69,13 @@ function Expiry(props: ExpiryProps) {

const idRef = useRef(propsId || makeUniqueId()).current

const status = error ? 'error' : warning ? 'warn' : info ? 'info' : null
const status = hasError
? 'error'
: warning
? 'warn'
: info
? 'info'
: null

return (
<FieldBlock
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { axeComponent } from '../../../../../core/jest/jestSetup'
import { act, render } from '@testing-library/react'
import userEvent from '@testing-library/user-event'
import * as Field from '../..'
import { FormError, FieldBlock } from '../../..'

describe('Field.Expiry', () => {
beforeEach(() => {
Expand Down Expand Up @@ -311,4 +312,25 @@ describe('Field.Expiry', () => {

expect(await axeComponent(result)).toHaveNoViolations()
})

it('renders error', () => {
render(<Field.Expiry error={new FormError('Error message')} />)

const element = document.querySelector('.dnb-form-status')
expect(element).toHaveTextContent('Error message')

const input = document.querySelector('.dnb-input')
expect(input).toHaveClass('dnb-input__status--error')
})

it('shows error style in FieldBlock', () => {
render(
<FieldBlock>
<Field.Expiry error={new FormError('Error message')} />
</FieldBlock>
)

const input = document.querySelector('.dnb-input')
expect(input).toHaveClass('dnb-input__status--error')
})
})
Original file line number Diff line number Diff line change
Expand Up @@ -187,6 +187,7 @@ function NumberComponent(props: Props) {
info,
warning,
error,
hasError,
help,
size,
width,
Expand Down Expand Up @@ -228,7 +229,7 @@ function NumberComponent(props: Props) {
'dnb-forms-field-number__contents',
showStepControls && 'dnb-forms-field-number__contents--has-controls',
disabled && 'dnb-forms-field-number__contents--is-disabled',
error && 'dnb-forms-field-number__contents--has-error'
hasError && 'dnb-forms-field-number__contents--has-error'
),
forId: id,
layout,
Expand Down Expand Up @@ -305,7 +306,7 @@ function NumberComponent(props: Props) {
onBlur: handleBlur,
onChange: handleChange,
disabled,
status: error ? 'error' : undefined,
status: hasError ? 'error' : undefined,
stretch: width !== undefined,
suffix:
help && !showStepControls ? (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { axeComponent, wait } from '../../../../../core/jest/jestSetup'
import { screen, render, fireEvent, act } from '@testing-library/react'
import userEvent from '@testing-library/user-event'
import * as Field from '../../'
import { FormError, FieldBlock } from '../../..'

describe('Field.Number', () => {
describe('props', () => {
Expand Down Expand Up @@ -111,6 +112,20 @@ describe('Field.Number', () => {
expect(element.className).toContain('dnb-input__status--error')
})

it('shows error style in FieldBlock', () => {
const errorMessage = new FormError('Error message')
render(
<FieldBlock>
<Field.Number error={errorMessage} />
</FieldBlock>
)

const input = document.querySelector(
'.dnb-forms-field-number__input'
)
expect(input).toHaveClass('dnb-input__status--error')
})

it('formats with given thousandSeparator', () => {
const { rerender } = render(
<Field.Number value={12345} thousandSeparator=" " />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,7 @@ function PhoneNumber(props: Props) {
info,
warning,
error,
hasError,
disabled,
width = 'large',
help,
Expand Down Expand Up @@ -306,7 +307,7 @@ function PhoneNumber(props: Props) {
}
data={dataRef.current}
value={countryCodeRef.current}
status={error ? 'error' : undefined}
status={hasError ? 'error' : undefined}
disabled={disabled}
on_focus={onFocusHandler}
on_blur={handleBlur}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,7 @@ function SelectCountry(props: Props) {
info,
warning,
error,
hasError,
disabled,
value,
width = 'large',
Expand Down Expand Up @@ -189,6 +190,7 @@ function SelectCountry(props: Props) {
on_change={handleCountryChange}
on_type={onTypeHandler}
stretch
status={hasError ? 'error' : undefined}
show_submit_button
suffix={
help ? (
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ import { axeComponent } from '../../../../../core/jest/jestSetup'
import { fireEvent, render, waitFor } from '@testing-library/react'
import SelectCountry, { Props } from '..'
import { Provider } from '../../../../../shared'
import { Form } from '../../..'
import { Form, FormError, FieldBlock } from '../../..'

describe('Field.SelectCountry', () => {
it('should render with props', () => {
Expand Down Expand Up @@ -267,6 +267,29 @@ describe('Field.SelectCountry', () => {
expect(selectedItemElement().textContent).toBe('Danmark')
})

it('renders error', () => {
const errorMessage = new FormError('Error message')
render(<SelectCountry error={errorMessage} />)

const element = document.querySelector('.dnb-form-status')
expect(element).toHaveTextContent('Error message')

const input = document.querySelector('.dnb-autocomplete__input')
expect(input).toHaveClass('dnb-input__status--error')
})

it('shows error style in FieldBlock', () => {
const errorMessage = new FormError('Error message')
render(
<FieldBlock>
<SelectCountry error={errorMessage} />
</FieldBlock>
)

const input = document.querySelector('.dnb-autocomplete__input')
expect(input).toHaveClass('dnb-input__status--error')
})

it('should validate with ARIA rules', async () => {
const result = render(<SelectCountry value="DK" />)

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,7 @@ function Selection(props: Props) {
info,
warning,
error,
hasError,
disabled,
help,
emptyValue,
Expand Down Expand Up @@ -237,7 +238,7 @@ function Selection(props: Props) {
portal_class="dnb-forms-field-selection__portal"
title={placeholder}
value={String(value ?? '')}
status={status && 'error'}
status={(hasError || status) && 'error'}
disabled={disabled}
data={data}
suffix={
Expand Down
Loading

0 comments on commit 35fe238

Please sign in to comment.