Pitfall
flushSync를 사용하는 것은 흔하지 않으며 앱 성능을 저하시킬 수 있음.
flushSync를 사용하면 제공된 콜백 내부의 모든 업데이트를 동기적으로 flush하도록 React를 강제할 수 있음. 이렇게 하면 DOM이 즉시 업데이트됨.
flushSync(callback)
flushSync를 호출하면 React가 보류 중인 작업을 flush하고 DOM을 동기적으로 업데이트하도록 강제함.
import { flushSync } from 'react-dom';
flushSync(() => {
setSomething(123);
});
대부분의 경우 flushSync는 피할 수 있으므로 최후의 수단으로만 flushSync를 사용할 것.
callback: 함수. React는 즉시 이 callback을 호출하고 포함된 모든 업데이트를 동기적으로 flush함. 또한 보류 중인 모든 업데이트, Effect 또는 Effect 내부의 업데이트를 flush할 수도 있음. ?이 flushSync 호출의 결과로 업데이트가 일시 중단되면 fallback이 다시 표시될 수 있음.?undefined를 반환함.
flushSync는 성능을 크게 저하시킬 수 있으므로 신중히 사용해야함.flushSync는 보류 중인 Suspense 경계에 강제로 fallback 상태를 표시할 수 있음.?flushSync는 보류 중인 Effect를 실행하고, 반환하기 전에 포함된 모든 업데이트를 동기적으로 적용할 수 있음.flushSync는 콜백 내부의 업데이트를 flush하기 위해 필요한 경우 콜백 외부의 업데이트를 flush할 수 있음. 예를 들어, 클릭으로 인해 보류 중인 업데이트가 있는 경우 React는 콜백 내부의 업데이트를 flush하기 전에 해당 업데이트를 flush할 수 있음.브라우저 API나 UI 라이브러리와 같은 서드파티 코드와 통합할 때, React가 업데이트를 flush하도록 강제해야 할 수도 있음. flushSync를 사용하면 React가 콜백 내부의 모든 state 업데이트를 동기적으로 flush하도록 강제할 수 있음:
flushSync(() => {
setSomething(123);
});
// By this line, the DOM is updated.
이렇게 하면 다음 줄의 코드가 실행될 때 React가 이미 DOM을 업데이트했음을 보장함.
flushSync를 사용하는 것은 흔하지 않으며, 자주 사용하면 앱의 성능이 크게 저하될 수 있음. 앱이 React API만 사용하고 서드파티 라이브러리와 통합하지 않는 경우 flushSync는 필요하지 않음.
하지만 브라우저 API와 같은 서드파티 코드와 통합하는 데는 유용할 수 있음.
일부 브라우저 API는 콜백이 끝날 때까지 콜백 내부의 결과가 DOM에 동기적으로 기록되어 브라우저가 렌더링된 DOM으로 무언가를 할 수 있기를 기대함. 대부분의 경우 React는 이를 자동으로 처리함. 하지만 어떤 경우에는 동기식 업데이트를 강제해야 할 수도 있음.
예를 들어, 브라우저의 onbeforeprint API를 사용하면 인쇄 대화 상자가 열리기 직전에 페이지를 변경할 수 있음. 이 기능은 문서를 인쇄할 때 더 보기 좋게 표시할 수 있는 사용자 지정 인쇄 스타일을 적용하는 데 유용함. 아래 예시에서는 onbeforeprint 콜백 내부에서 flushSync를 사용하여 React state를 DOM에 즉시 'flush'함. 그러면 인쇄 대화 상자가 열릴 때 isPrinting이 "yes"로 표시됨:
import { useState, useEffect } from 'react';
import { flushSync } from 'react-dom';
export default function PrintApp() {
const [isPrinting, setIsPrinting] = useState(false);
useEffect(() => {
function handleBeforePrint() {
flushSync(() => {
setIsPrinting(true);
})
}
function handleAfterPrint() {
setIsPrinting(false);
}
window.addEventListener('beforeprint', handleBeforePrint);
window.addEventListener('afterprint', handleAfterPrint);
return () => {
window.removeEventListener('beforeprint', handleBeforePrint);
window.removeEventListener('afterprint', handleAfterPrint);
}
}, []);
return (
<>
<h1>isPrinting: {isPrinting ? 'yes' : 'no'}</h1>
<button onClick={() => window.print()}>
Print
</button>
</>
);
}
flushSync가 없으면 인쇄 대화 상자에 isPrinting이 "no"로 표시됨. 이는 React가 업데이트를 비동기적으로 일괄 처리하고, state가 업데이트되기 전에 인쇄 대화 상자가 표시되기 때문.
Pitfall
flushSync는 성능을 크게 저하시킬 수 있으며, 보류 중인 Suspense 경계가 예기치 않게 fallback state를 표시하도록 강제할 수 있음.대부분의 경우 flushSync는 피할 수 있으므로 최후의 수단으로 사용할 것.