React with SWR에서 패턴을 가져올 때 렌더링
추출 및 렌더링은 데이터 렌더링 어셈블리를 사용하기 시작하면서 필요한 데이터를 추출하는 모드입니다.이렇게 하면 렌더링을 시작하기 위해 로드 상태에서 렌더링을 기다릴 필요(렌더링 시 캡처라고도 함), 렌더링을 시작하기 위해 캡처가 완료될 때까지 기다릴 필요(선캡처 후 렌더링이라고도 함)가 없습니다.
이 모든 모델을 사용하여 예시 프로그램을 만들어서 어떻게 작동하는지 알 수 있습니다.
렌더링 시 추출
이것은 세 가지 모델 중 가장 흔히 볼 수 있는 모델로, 우선 불러오는 상태로 구성 요소를 보여준 다음에 데이터를 얻기 시작한다는 생각이다.
// fetcher.js
const sleep = ms => new Promise(r => setTimeout(r, ms));
export default function fetcher(url) {
return sleep(1000).then(() => ({ url }));
}
우선 간단한 캡처 함수를 만듭니다. 이 함수는 1초 동안 휴면한 다음 받은 URL을 포함하는 대상을 되돌려줍니다.import React from "react";
export default function Loading() {
return <p>Loading...</p>;
}
그리고 간단한 Loading
구성 요소를 메시지로 만듭니다.그것은 데이터 가져오기와 불러오기 지연을 위한 예비 방안으로 사용될 것이다.// resource.js
import React from "react";
import useSWR from "swr";
import fetcher from "./fetcher";
import Loading from "./loading";
export default function Resource({ id }) {
const { data } = useSWR(`/api/resource/${id}`, fetcher);
if (!data) {
return <Loading />;
}
return <p>{data.url}</p>;
}
이제 구성 요소 Resource
를 구축합니다. 이 구성 요소는 SWR을 호출하고 URL은 props.id
를 추가하여 가져오는 프로그램을 사용합니다. 내부에서 data
정의되지 않았는지 확인하고 Loading
구성 요소를 보여 줍니다. 정의되면 URL을 보여 줍니다.여기서 SWR은 우리의
fetcher
함수를 호출하고, 구성 요소가 한 번 나타나면 URL을 전달하며, 효과로 우리의 함수를 호출합니다.// app.js
import React from "react";
const sleep = ms => new Promise(r => setTimeout(r, ms));
const LazyResource = React.lazy(() =>
sleep(1000).then(() => import("./resource"))
);
export default function App() {
const [id, setID] = React.useState(null);
function handleChange(event) {
setID(event.target.value);
}
return (
<>
<label htmlFor="id">Resource ID:</label>{" "}
<input id="id" type="text" onChange={handleChange} value={id} />
{id && (
<React.Suspense fallback={<p>Loading...</p>}>
<LazyResource id={id} />
</React.Suspense>
)}
</>
);
}
현재, 저희 App
구성 요소는 간단한 입력을 보일 것입니다. ID를 기록한 다음에 ID를 저장하기 위해 상태를 업데이트할 것입니다. 만약 ID가falsy가 아니라면, 저희 Resource
구성 요소를 보여 드리겠습니다. 그러나, 저희 구성 요소를 가져오고 있습니다. React.lazy
를 사용하면 ID를 변경하지 않으면, 이 구성 요소의 코드를 영원히 불러오지 않을 것입니다.그러나 이것은 우리가 먼저 구성 요소를 불러와야 한다는 것을 의미한다. 예를 들어 우리의sleep 함수 때문에 최소한 1초가 걸리고fetcher 함수를 렌더링하고 터치해야 한다.이 예가 CodeSandbox에서 실행되는 것을 보여 줍니다.
만약 우리가 시험해 본다면, 우리 프로그램은 현재 처음으로 URL을 표시하는 데 2초가 걸리고, 이후에 매번 변경할 때마다 1초가 걸린다.
이것은 실행할 수 있지만 결코 이상적이지는 않다.
선취 후 렌더링
선수령 후 렌더링 방법의 방향이 다르기 때문에 우리는 데이터를 얻은 후에 렌더링을 시작하지 않고 데이터를 얻은 후에 렌더링을 시작할 것이다.비록 매우 비슷하게 들리지만, 그것은 다른 실현을 가지고 있다.
우리의 대부분의 코드는 변하지 않을 것이니, 이러한 변화에 관심을 가져라.
// resource.js
import React from "react";
export default function Resource({ data }) {
return <p>{data.url}</p>;
}
Resource
구성 요소에서 우리는 마운트 상태를 처리하지 않고 데이터를 추출하지 않고 부모 구성 요소에서 데이터를 받는다.// app.js
import React from "react";
import useSWR from "swr";
import Loading from "./loading";
import fetcher from "./fetcher";
const sleep = ms => new Promise(r => setTimeout(r, ms));
const LazyResource = React.lazy(() =>
sleep(1000).then(() => import("./resource"))
);
export default function App() {
const [id, setID] = React.useState(null);
const { data } = useSWR("/api/resource/" + id, fetcher);
async function handleChange(event) {
setID(event.target.value);
}
return (
<>
<label htmlFor="id">Resource ID:</label>{" "}
<input id="id" type="text" onChange={handleChange} value={id} />
{!id ? (
<p>Enter ID</p>
) : data ? (
<React.Suspense fallback={<Loading />}>
<LazyResource data={data} />
</React.Suspense>
) : (
<Loading />
)}
</>
);
}
우리 App
구성 요소에서, 우리는 현재 ID를 업데이트한 다음, SWR에 새fetcher 호출을 터치하고 있으며, 기본적으로, 우리는 데이터를 사용하여 구성 요소에서 얻은 데이터를 부모 구성 요소로 이동합니다.구성 요소 return
문장에서, 우리는 현재 유효한 ID가 있는지 확인한 다음, 데이터가 있는지 확인하여 Loading
구성 요소를 보여야 하는지 확인합니다.CodeSandbox에서 다시 작동하는 것을 보여 줍니다.
ID를 처음 작성할 때 렌더링
Resource
구성 요소는 2초가 걸립니다. 렌더링할 때 가져오는 모드에 비해 향상된 방법은 아닙니다. 다른 방법일 뿐입니다.추출과 렌더링
이제 우리가 더 흥미를 느끼는 모델을 살펴보자. 즉, 추출하면서 과장하는 것이다. 개발자로서 구성 요소가 어떤 데이터를 필요로 하는지, 혹은 그것을 알 수 있는 방법이 있다는 것이다.따라서, 우리는fetch가 렌더링을 완성하기를 기다릴 필요도, 렌더가fetch를 완성하기를 기다릴 필요도 없이, 렌더링과 가져오는 것을 동시에 기다릴 수 있다.
그것의 실현을 봅시다.우선, 우리는
Resource
구성 요소를 업데이트해야 한다.// resource.js
import React from "react";
import useSWR from "swr";
import fetcher from "./fetcher";
export default function Resource({ id }) {
const { data } = useSWR(`/api/resource/${id}`, fetcher, { suspense: true });
return <p>{data.url}</p>;
}
구성 요소에 데이터 리셋을 추가하지만 로드 상태를 처리하지 않고 데이터 리셋을 수행하기 전에 구성 요소를 일시 중지하도록 SWR을 구성합니다.// app.js
import React from "react";
import { mutate } from "swr";
import Loading from "./loading";
import fetcher from "./fetcher";
const sleep = ms => new Promise(r => setTimeout(r, ms));
const LazyResource = React.lazy(() =>
sleep(1000).then(() => import("./resource"))
);
export default function App() {
const [id, setID] = React.useState(null);
async function handleChange(event) {
const newID = event.target.value;
mutate(`/api/resource/${newID}`, fetcher(`/api/resource/${newID}`), false);
setID(newID);
}
return (
<>
<label htmlFor="id">Resource ID:</label>{" "}
<input id="id" type="text" onChange={handleChange} value={id} />
{!id ? (
<p>Enter ID</p>
) : (
<React.Suspense fallback={<Loading />}>
<LazyResource id={id} />
</React.Suspense>
)}
</>
);
}
만약 우리가 App
구성 요소를 검사한다면, 우리는 useSWR
의 사용법을 삭제할 것이다. 왜냐하면 우리는 그것을 다시 Resource
하기 때문이다. 그러나 우리는 SWR에서 mutate
라는 함수를 가져왔기 때문이다.이 작은 함수는 SWR 버퍼가 특정 키에 존재하는 데이터를 업데이트할 수 있도록 합니다.이를 위해서는 캐시 키, 이 예의 URL, 데이터를 전달하기 위해 호출해야 한다. 만약에 SWR이 우리의 API에 따라 다시 검증하기를 원한다면, 기본적으로 사용된 마지막 옵션은 낙관적인 UI 업데이트를 지원하는 데 매우 유용하다. 왜냐하면 우리는 API에서 데이터를 얻기만 하고 다시 검증할 필요가 없기 때문에 전달한다.
false
그러나 여기서 가장 중요한 부분은 두 번째 매개 변수이다. 나는 위에서 우리가 그곳에서 데이터를 전달해야 하지만 우리가 전달하는 것은 그것이 해결되기를 기다리는 것이 아니라 약속 대상이라고 썼다.mutate
우리가 내부에서 해결을 기다릴 것을 깨달았기 때문이다.그렇기 때문에 추출을 터치하고 입력 값을 즉시 업데이트할 수 있습니다.이제 CodeSandbox에서 이러한 변경 사항을 어떻게 하는지 살펴보겠습니다.
보시다시피 화면에 URL이 표시되는 시간은 1초입니다!이것은 우리가 구성 요소를 렌더링하는 데 필요한 코드와 데이터를 동시에 얻었다는 것을 의미하기 때문에 매우 신기하다.그리고 우리
Resource
구성 요소는 이전에 얻은 데이터를 다시 사용하고, 1초를 기다리지 않고 바로 렌더링을 할 것입니다.로드 지연과 데이터 가져오기에 가짜 지연을 사용해 보십시오. 둘의 조합이 아니라 가장 긴 지연만 기다리는 방법을 보실 수 있습니다.
Reference
이 문제에 관하여(React with SWR에서 패턴을 가져올 때 렌더링), 우리는 이곳에서 더 많은 자료를 발견하고 링크를 클릭하여 보았다 https://dev.to/sergiodxa/render-as-you-fetch-pattern-in-react-with-swr-3o9n텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
우수한 개발자 콘텐츠 발견에 전념 (Collection and Share based on the CC Protocol.)