[web] Add a delay before showing loading spinner while lazy-loading React components (#6262)

GitOrigin-RevId: a77d11e980103de31a5bf1a19391874bea70cfec
This commit is contained in:
Alf Eaton 2022-01-11 09:17:56 +00:00 committed by Copybot
parent ce45098530
commit d1e3ce8225
2 changed files with 46 additions and 3 deletions

View file

@ -1,14 +1,38 @@
import { useTranslation } from 'react-i18next'
import Icon from './icon'
import { useEffect, useState } from 'react'
import PropTypes from 'prop-types'
function LoadingSpinner() {
function LoadingSpinner({ delay = 500 }) {
const { t } = useTranslation()
const [show, setShow] = useState(false)
useEffect(() => {
const timer = window.setTimeout(() => {
setShow(true)
}, delay)
return () => {
window.clearTimeout(timer)
}
}, [delay])
if (!show) {
return null
}
return (
<div className="loading">
<Icon type="fw" modifier="refresh" spin />
{` ${t('loading')}`}
&nbsp;
{t('loading')}
</div>
)
}
LoadingSpinner.propTypes = {
delay: PropTypes.number,
}
export default LoadingSpinner

View file

@ -12,8 +12,21 @@ import {
cleanUpContext,
} from '../../../helpers/render-with-context'
import { stubMathJax, tearDownMathJaxStubs } from './stubs'
import sinon from 'sinon'
describe('<ChatPane />', function () {
beforeEach(function () {
this.clock = sinon.useFakeTimers({
toFake: ['setTimeout', 'clearTimeout', 'setInterval', 'clearInterval'],
})
})
afterEach(function () {
this.clock.runAll()
this.clock.restore()
fetchMock.reset()
})
const user = {
id: 'fake_user',
first_name: 'fake_user_first_name',
@ -78,10 +91,16 @@ describe('<ChatPane />', function () {
})
it('a loading spinner is rendered while the messages are loading, then disappears', async function () {
fetchMock.get(/messages/, [])
fetchMock.get(/messages/, [], { delay: 1000 })
renderWithChatContext(<ChatPane />, { user })
this.clock.tick(600) // wait for spinner to be displayed
await screen.findByText('Loading…')
this.clock.tick(1000) // wait for response to be received
await waitForElementToBeRemoved(() => screen.getByText('Loading…'))
})