// @flow
import React from 'react';
import { act } from 'react-dom/test-utils';
import moment from 'moment';
import { Datepicker } from '.';
import { mountWrappedComponent } from '../../../utils/tests';

describe('Datepicker', () => {
  beforeEach(() => {
    jest.clearAllMocks();
  });

  const DEFAULT_PROPS = {
    onChange: jest.fn(),
    label: 'Choose a date',
    value: new Date('2019-01-01 12:30:00'),
  };

  it('has the correct onChange functionality', () => {
    let component = mountWrappedComponent(<Datepicker {...DEFAULT_PROPS} />);

    act(() => {
      component.find('input').simulate('focus');
    });

    component = component.update();

    act(() => {
      component.find('.DayPicker-Day').at(19).simulate('click');
    });

    component = component.update();

    // we do a toContain just so we dont deal with timezones in testing environments
    expect(DEFAULT_PROPS.onChange.mock.calls[0][0].toISOString()).toContain(
      '2019-01-18T',
    );
  });

  describe('writing an invalid date', () => {
    it('calls onChange with undefined', () => {
      const component = mountWrappedComponent(
        <Datepicker {...DEFAULT_PROPS} />,
      );

      const input = component.find('input');

      act(() => {
        input.simulate('change', { target: { value: '2020-0' } });
      });

      component.update();

      expect(DEFAULT_PROPS.onChange).toHaveBeenCalledWith(undefined);
      expect(DEFAULT_PROPS.onChange).toHaveBeenCalledTimes(1);
    });
  });

  describe('writing a valid date', () => {
    it('calls onChange with a date', () => {
      const component = mountWrappedComponent(
        <Datepicker {...DEFAULT_PROPS} />,
      );

      const input = component.find('input');

      act(() => {
        input.simulate('change', { target: { value: '2020-10-10' } });
      });

      component.update();

      expect(
        moment(DEFAULT_PROPS.onChange.mock.calls[0][0]).isSame(
          moment(new Date('2020-10-10')),
        ),
      );
      expect(DEFAULT_PROPS.onChange).toHaveBeenCalledTimes(1);
    });
  });
});
