Не вызывается обратный вызов события нажатия кнопки - шутка / энзим - PullRequest
0 голосов
/ 26 сентября 2018

У меня есть следующий тест, который проверяет вызов метода обратного вызова при нажатии кнопки с аргументом, переданным в качестве значения текстового ввода моего компонента Estimate.

Test:

let obj
let fn
describe('Estimate tests', () => {
  beforeAll(() => {
    fn = jest.fn()
    obj = mount(<Estimate onPress={fn} />)
  })

  afterAll(() => {
    obj.unmount()
  })

  test('Button click returns text input value', () => {
    obj.find('TextInput').first().simulate('change', { target: { value: 61606 } })
    obj.find('Button').first().simulate('click')
    expect(fn).toHaveBeenCalledWith(61606)
  })
})

Estimate.jsx:

export class Estimate extends PureComponent {
  render () {
    const { onPress } = this.props

    // @todo remove the excess margin and spacing above this component
    return (
      <Form
        name="estimateForm"
        ref={(ref) => {
          this.estimateForm = ref
        }}
      >
        <Actions style={{ alignItems: 'flex-end' }}>
          <Button
            type="text"
            style={{ marginBottom: -em(0.5) }}
            onPress={() => onPress(this.estimateForm.values)}
            title={t('estimateShippingAndTax')}
          />
          <TextInput
            placeholder={t('postalCode')}
            name="estimate"
            style={{ width: 100 }}
            validate="postalCode"
          />
        </Actions>
      </Form>
    )
  }
}

Возвращает:

expect(jest.fn()).toHaveBeenCalledWith(expected)

Expected mock function to have been called with:
  [61606]
But it was not called.

  31 |     obj.find('TextInput').first().simulate('change', { target: { value: 61606 } })
  32 |     obj.find('Button').first().simulate('click')
> 33 |     expect(fn).toHaveBeenCalledWith(61606)
     |                ^
  34 |   })
  35 | })
  36 | 

Что происходит?onPress ассоциируется с кнопками на прессе.И все же это даже не называется.

1 Ответ

0 голосов
/ 26 сентября 2018

Поскольку вы работаете с неконтролируемым компонентом , имитирующее изменение (то же самое, что вызов target.props.onChange(...)) не будет работать.

Для веб-приложения это можно сделать с помощью мутации .value вместо simulate('change', ...), но поскольку он является React Native, его TextInput в контролируемом компоненте должен быть снабжен явным обработчиком onChange / onChangeText.Тогда вы сможете использовать simulate('change') так же, как и вы.

Последнее, что я хочу выделить: для управляемого компонента будет необходимо вызвать .update() на оболочке фермента, какчто:

test('Button click returns text input value', () => {
    obj.find('TextInput').first().simulate('change', { target: { value: 61606 } });
    obj.update();
    obj.find('Button').first().simulate('click');
    expect(fn).toHaveBeenCalledWith([61606]); // also here you will retrieve array with values not single one
})

[UPD] на самом деле значение TextInput можно установить неконтролируемым образом через ref (но я считаю, что его использование контролируемым образом лучше):

obj.instance()._textInputRefYouShouldBound.setNativeProps({text: '61606'});
obj.find('Button').first().simulate('click')
expect(fn).toHaveBeenCalledWith(['61606'])
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...