To run this:
- use
create-react-app
to spin up a project yarn install fast-check
- copy
Progress.tsx
andProgress.test.tsx
into thesrc
directory - run
yarn test
import { cleanup, render, screen, fireEvent, act } from '@testing-library/react'; | |
import Progress from './Progress'; | |
import * as fc from 'fast-check'; | |
test('renders learn react link', async () => { | |
await fc.assert( | |
fc.asyncProperty(fc.scheduler(), async (s) => { | |
let number = 0; | |
const mockGetProgress = s.scheduleFunction(async () => number += 10); | |
render(<Progress getProgress={mockGetProgress} />); | |
const button = screen.getByRole('button'); | |
fireEvent.click(button); | |
fireEvent.click(button); | |
fireEvent.click(button); | |
await act(async () => await s.waitAll()); | |
const progressValue = screen.getByText(/30/); | |
expect(progressValue).toBeInTheDocument(); | |
}).beforeEach(() => { | |
cleanup(); | |
}) | |
); | |
}); |
import { useState } from 'react'; | |
export default function Progress({ getProgress }: { getProgress: () => Promise<number> }) { | |
const [loading, setLoading] = useState(false); | |
const [value, setValue] = useState<number>(0); | |
const updateProgress = () => { | |
setLoading(true); | |
getProgress().then(newValue => { | |
setValue((oldValue) => Math.max(newValue, oldValue)); | |
setLoading(false); | |
}); | |
}; | |
return ( | |
<div> | |
<div> | |
<label htmlFor="p">File progress:</label> | |
<progress id="p" max="100" value={value}> {value}% </progress> | |
</div> | |
<div> | |
<button onClick={updateProgress}> | |
Update Progress | |
</button> | |
{loading && <p>updating...</p>} | |
</div> | |
</div> | |
); | |
} |