Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Features
Speaker Deck
PRO
Sign in
Sign up for free
Search
Search
Você usa APIs do jeito errado
Search
Hugo
July 16, 2022
Programming
0
66
Você usa APIs do jeito errado
Uma introdução ao React Query v3
Hugo
July 16, 2022
Tweet
Share
More Decks by Hugo
See All by Hugo
ReferenceError: talk is not defined
hugooliveirad
1
45
Três hábitos para escrever CSS escalável
hugooliveirad
0
620
Three habits to write scalable CSS
hugooliveirad
0
65
Mantendo webapps em produção, sem dor de cabeça
hugooliveirad
1
280
Minha webapp está em produção, e agora?
hugooliveirad
0
37
Other Decks in Programming
See All in Programming
XSLTで作るBrainfuck処理系
makki_d
0
190
Java on Azure で LangGraph!
kohei3110
0
110
TypeScript LSP の今までとこれから
quramy
1
500
Parallel::Pipesの紹介
skaji
2
910
無関心の谷
kanayannet
0
160
つよそうにふるまい、つよい成果を出すのなら、つよいのかもしれない
irof
1
280
Use Perl as Better Shell Script
karupanerura
0
690
GoのWebAssembly活用パターン紹介
syumai
3
10k
機械学習って何? 5分で解説頑張ってみる
kuroneko2828
0
200
コード書くの好きな人向けAIコーディング活用tips #orestudy
77web
3
300
Effect の双対、Coeffect
yukikurage
5
1.4k
WindowInsetsだってテストしたい
ryunen344
1
110
Featured
See All Featured
Fantastic passwords and where to find them - at NoRuKo
philnash
51
3.3k
Designing Experiences People Love
moore
142
24k
Responsive Adventures: Dirty Tricks From The Dark Corners of Front-End
smashingmag
252
21k
Sharpening the Axe: The Primacy of Toolmaking
bcantrill
43
2.4k
We Have a Design System, Now What?
morganepeng
52
7.6k
Side Projects
sachag
454
42k
The World Runs on Bad Software
bkeepers
PRO
68
11k
What’s in a name? Adding method to the madness
productmarketing
PRO
22
3.5k
Writing Fast Ruby
sferik
628
61k
4 Signs Your Business is Dying
shpigford
184
22k
A better future with KSS
kneath
239
17k
Building an army of robots
kneath
306
45k
Transcript
Você usa APIs do jeito errado Uma introdução ao React
Query
Oi, eu sou o Hugo E eu também já usei
APIs do jeito errado
Vamos começar um projeto novo
None
None
A API da timeline está pronta
A API da timeline está pronta Beleza, a gente vai
implementar
É só substituir os valores do JSON pela API const
[timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
É só substituir os valores do JSON pela API const
[timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
É só substituir os valores do JSON pela API const
[timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
É só substituir os valores do JSON pela API const
[timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
É só substituir os valores do JSON pela API const
[timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
function useTimelineData() { } É só substituir os valores do
JSON pela API const [timelineData, setTimelineData] = useState(); useEffect(() => { async function fetchData() { const response = await fetch('/timeline'); const data = await response.json(); setTimelineData(data); } fetchData(); }, [])
function TimelinePage() { const timelineData = useTimelineData(); if (!timelineData) {
return null; } return ( <Timeline> {timelineData.posts.map((post) => ( <Post key={post.id} post={post} /> ))} </Timeline> ) }
Tá pronto, chefe
Tá pronto, chefe Agora a API dos posts está pronta
Tá pronto, chefe Agora a API dos posts está pronta
Beleza, vamos lá. Tá fácil.
None
function usePostData(id) { const [postData, setPostData] = useState(); useEffect(() =>
{ async function fetchData() { const response = await fetch(`/posts/${id}`); const data = await response.json(); setPostData(data); } fetchData(); }, [id]) return postData; }
function usePostData(id) { const [postData, setPostData] = useState(); useEffect(() =>
{ async function fetchData() { const response = await fetch(`/posts/${id}`); const data = await response.json(); setPostData(data); } fetchData(); }, [id]) return postData; }
Tá pronto
Tá pronto Tá pronto?
Tá pronto Tá pronto? Alguém consegue me dizer quais são
os problemas da implementação atual?
Alguém consegue me dizer quais são os problemas da implementação
atual?
Erros e Exceções
Erros e Exceções
Error Erros e Exceções
Batching
1 4 3 2 useTimelineData Batching
1 4 3 2 useTimelineData Batching Batching
1 4 3 2 useTimelineData Batching Batching
Caching
Caching
Caching useTimelineData
Cache Invalidation New
Cache Invalidation New New
Race Condition
Race Condition Busca T T T T T T
Busca T Ty Type TypeSc TypeScri TypeScript T T T
T T T Race Condition
Busca T Ty Type TypeSc TypeScri TypeScript Requisições T Ty
Type TypeSc TypeScri TypeScript T T T T T T Race Condition
T Ty Type TypeSc TypeScri TypeScript Requisições T Ty Type
TypeSc TypeScri TypeScript Race Condition Latência T Ty Type TypeSc TypeScri TypeScript
Retries
Retries
1 4 3 2 Requisições Retries
1 4 3 2 Requisições 1 4 3 2 Retries
1 4 3 2 Requisições 1 4 3 2 3
Retry Retry Retry Sucesso Retries Retries
Erros e Exceções Batching Caching Cache Invalidation Race Condition Retries
Erros e Exceções Batching Caching Cache Invalidation Race Condition Retries
Cancelamento Prefetching In fi nite Pagination Polling Optimistic Updates Refetching E muito mais
Ninguém implementa tudo isso
Você não quer ter que implementar tudo isso
React Query
function usePostData(id) { const [postData, setPostData] = useState(); useEffect(() =>
{ async function fetchData() { const response = await fetch(`/posts/${id}`); const data = await response.json(); setPostData(data); } fetchData(); }, [id]) return postData; }
async function fetchData() { const response = await fetch(`/posts/${id}`); const
data = await response.json(); setPostData(data); }
async function fetchData() { const response = await fetch(`/posts/${id}`); const
data = await response.json(); setPostData(data); }
async function fetchData() { const response = await fetch(`/posts/${id}`); return
response.json(); setPostData(data); }
function usePostData(id) { return useQuery(['posts', id], () => fetchPost(id)); }
function usePostData(id) { return useQuery(['posts', id], () => fetchPost(id)); }
function usePostData(id) { return useQuery(['posts', id], () => fetchPost(id)); }
function usePostData(id) { return useQuery(['posts', id], () => fetchPost(id)); }
function PostPage({params: {id}}) { const {data, isLoading} = usePostData(id); if
(isLoading) { return null; } return ( <Post post={data.post} /> ) }
function PostPage({params: {id}}) { const {data, isLoading} = usePostData(id); if
(isLoading) { return null; } return ( <Post post={data.post} /> ) }
function PostPage({params: {id}}) { const {data, isLoading} = usePostData(id); if
(isLoading) { return null; } return ( <Post post={data.post} /> ) }
const { data, isLoading, isSuccess, error, isError, refetch, /* ...
*/ } = usePostData(id);
Erros e Exceções Batching Caching Cache Invalidation Race Condition Retries
Cancelamento Prefetching In fi nite Pagination Polling Optimistic Updates Refetching Sites Robustos
Con fi gurável
staleTime: 0
staleTime: 0 ... 0 ms
cacheTime: 1000 * 60 * 5
retry: 3
refetchOnWindowFocus: true
refetchOnWindowFocus: true ... ...
function usePostData(id) { return useQuery(['posts', id], () => fetchPost(id), {
staleTime: 1000 * 20, cacheTime: 1000, refetchOnWindowsFocus: false, }); }
Mutations
New
New New u
New New useMutation
async function createPost(post) { const response = await fetch('/posts', {
method: 'POST', headers: { 'Accept': 'application/json', 'Content-Type': 'application/json' }, body: JSON.stringify(post) }); return response.json(); }
function CreatePostPage() { const mutation = useMutation(createPost); const handleSubmit =
useCallback((event) => { event.preventDefault(); const data = new FormData(event.target); const post = Object.fromEntries(data.entries()); mutation.mutate(post); }, [mutation]); return mutation.isLoading ? (<Spinner />) : ( <form onSubmit={handleSubmit}> {/* ... */} </form> ) }
function CreatePostPage() { const mutation = useMutation(createPost); const handleSubmit =
useCallback((event) => { event.preventDefault(); const data = new FormData(event.target); const post = Object.fromEntries(data.entries()); mutation.mutate(post); }, [mutation]); return mutation.isLoading ? (<Spinner />) : ( <form onSubmit={handleSubmit}> {/* ... */} </form> ) }
function CreatePostPage() { const mutation = useMutation(createPost); const handleSubmit =
useCallback((event) => { event.preventDefault(); const data = new FormData(event.target); const post = Object.fromEntries(data.entries()); mutation.mutate(post); }, [mutation]); return mutation.isLoading ? (<Spinner />) : ( <form onSubmit={handleSubmit}> {/* ... */} </form> ) }
function CreatePostPage() { const mutation = useMutation(createPost); const queryClient =
useQueryClient(); const handleSubmit = useCallback((event) => { event.preventDefault(); const data = new FormData(event.target); const post = Object.fromEntries(data.entries()); mutation.mutate(post, { onSuccess: () => { queryClient.invalidateQueries('timeline'); } }); }, [mutation]); return mutation.isLoading ? (<Spinner />) : ( <form onSubmit={handleSubmit}> {/* ... */} </form> )
queryClient.invalidateQueries(['posts', id]);
DevTools
DevTools
Hugo, eu parei de prestar atenção Já uso o getServerProps
Não preciso do React Query
Hugo, eu parei de prestar atenção Já uso o getServerProps
Não preciso do React Query E se eu te falar que...
E se eu te falar que... React Query trabalha com
dados assíncronos
E se eu te falar que... React Query trabalha com
dados assíncronos Qualquer dado assíncrono
const [stream, setStream] = useState(); useEffect(() => { async function
getMedia() { const newStream = await navigator.mediaDevices.getUserMedia({video: true}); setStream(newStream); } getMedia(); }, [])
function useUserMedia() { return useQuery( ['userMedia'], () => navigator.mediaDevices.getUserMedia({video: true})
); }
function useUserMedia() { return useQuery( ['userMedia'], () => navigator.mediaDevices.getUserMedia({video: true}),
{ staleTime: Infinity } ); }
"The best part is no part"
None
De nada!
None
None
None