diff --git a/packages/ra-ui-materialui/src/input/NumberInput.spec.tsx b/packages/ra-ui-materialui/src/input/NumberInput.spec.tsx index 2fe51c2a26c..815540424f5 100644 --- a/packages/ra-ui-materialui/src/input/NumberInput.spec.tsx +++ b/packages/ra-ui-materialui/src/input/NumberInput.spec.tsx @@ -292,6 +292,50 @@ describe('', () => { expect(onSubmit.mock.calls[0][0].views).toBeNull(); }); + it('should cast value to a numeric with a custom parse function', async () => { + const onSubmit = jest.fn(); + + render( + + } onSubmit={onSubmit}> + value} /> + + + ); + const input = screen.getByLabelText('resources.posts.fields.views'); + fireEvent.change(input, { target: { value: '12' } }); + fireEvent.click(screen.getByText('ra.action.save')); + await waitFor(() => { + expect(onSubmit).toHaveBeenCalledWith( + { views: 12 }, + expect.anything() + ); + }); + expect(typeof onSubmit.mock.calls[0][0].views).toEqual('number'); + }); + + it('should cast 0 to a numeric with a custom parse function', async () => { + const onSubmit = jest.fn(); + + render( + + } onSubmit={onSubmit}> + value} /> + + + ); + const input = screen.getByLabelText('resources.posts.fields.views'); + fireEvent.change(input, { target: { value: '0' } }); + fireEvent.click(screen.getByText('ra.action.save')); + await waitFor(() => { + expect(onSubmit).toHaveBeenCalledWith( + { views: 0 }, + expect.anything() + ); + }); + expect(typeof onSubmit.mock.calls[0][0].views).toEqual('number'); + }); + it('should reformat if format function gets changed', async () => { const AngleInput = props => { const unit = useWatch({ name: 'unit' }); diff --git a/packages/ra-ui-materialui/src/input/NumberInput.tsx b/packages/ra-ui-materialui/src/input/NumberInput.tsx index 9e402199049..98f94f194e2 100644 --- a/packages/ra-ui-materialui/src/input/NumberInput.tsx +++ b/packages/ra-ui-materialui/src/input/NumberInput.tsx @@ -83,13 +83,16 @@ export const NumberInput = ({ } const target = event.target; setValue(target.value); - const newValue = target.valueAsNumber - ? parse - ? parse(target.valueAsNumber) - : target.valueAsNumber - : parse - ? parse(target.value) - : convertStringToNumber(target.value); + const newValue = + target.valueAsNumber !== undefined && + target.valueAsNumber !== null && + !isNaN(target.valueAsNumber) + ? parse + ? parse(target.valueAsNumber) + : target.valueAsNumber + : parse + ? parse(target.value) + : convertStringToNumber(target.value); field.onChange(newValue); };