Skip to content

Commit b264807

Browse files
committed
react query v4
1 parent a968762 commit b264807

File tree

4 files changed

+54
-44
lines changed

4 files changed

+54
-44
lines changed

src/content/6/en/part6.md

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,9 @@ So far, we have placed the application's state and state logic directly inside R
1010

1111
We'll learn about the lightweight version of Redux directly supported by React, namely the React context and useRedux hook, as well as the React Query library that simplifies the server state management.
1212

13-
<i>Part updated 30th Jan 2023</i>
14-
- <i>A new section on React Query, useReducer and React context replaced the section on Redux connect</i>
13+
14+
<i>Part updated 23rd August 2023</i>
15+
- <i>Create React App replaced with Vite</i>
16+
- <i>React Query updated to version 4</i>
1517

1618
</div>

src/content/6/en/part6d.md

Lines changed: 21 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -50,20 +50,20 @@ The initial code is on GitHub in the repository [https://github.com/fullstack-hy
5050

5151
### Managing data on the server with the React Query library
5252

53-
We shall now use the [React Query](https://react-query-v3.tanstack.com/) library to store and manage data retrieved from the server.
53+
We shall now use the [React Query](https://tanstack.com/query/latest) library to store and manage data retrieved from the server. The latest version of the library is also called TanStack Query, but we stick to the familiar name.
5454

5555
Install the library with the command
5656

5757
```bash
58-
npm install react-query
58+
npm install @tanstack/react-query
5959
```
6060

61-
A few additions to the file <i>index.js</i> are needed to pass the library functions to the entire application:
61+
A few additions to the file <i>main.jsx</i> are needed to pass the library functions to the entire application:
6262

6363
```js
6464
import React from 'react'
6565
import ReactDOM from 'react-dom/client'
66-
import { QueryClient, QueryClientProvider } from 'react-query' // highlight-line
66+
import { QueryClient, QueryClientProvider } from '@tanstack/react-query' // highlight-line
6767

6868
import App from './App'
6969

@@ -79,19 +79,19 @@ ReactDOM.createRoot(document.getElementById('root')).render(
7979
We can now retrieve the notes in the <i>App</i> component. The code expands as follows:
8080

8181
```js
82-
import { useQuery } from 'react-query' // highlight-line
82+
import { useQuery } from '@tanstack/react-query' // highlight-line
8383
import axios from 'axios' // highlight-line
8484

8585
const App = () => {
8686
// ...
8787

8888
// highlight-start
89-
const result = useQuery(
90-
'notes',
91-
() => axios.get('http://localhost:3001/notes').then(res => res.data)
92-
)
89+
const result = useQuery({
90+
queryKey: ['notes'],
91+
queryFn: () => axios.get('http://localhost:3001/notes').then(res => res.data)
92+
})
9393

94-
console.log(result)
94+
console.log(JSON.parse(JSON.stringify(result)))
9595
// highlight-end
9696

9797
// highlight-start
@@ -142,7 +142,10 @@ import { getNotes } from './requests' // highlight-line
142142
const App = () => {
143143
// ...
144144

145-
const result = useQuery('notes', getNotes) // highlight-line
145+
const result = useQuery({
146+
queryKey: ['notes'],
147+
queryFn: () => getNotes // highlight-line
148+
})
146149

147150
// ...
148151
}
@@ -175,7 +178,7 @@ import { useQuery, useMutation } from 'react-query' // highlight-line
175178
import { getNotes, createNote } from './requests' // highlight-line
176179

177180
const App = () => {
178-
const newNoteMutation = useMutation(createNote) // highlight-line
181+
const newNoteMutation = useMutation({ mutationFn: createNote }) // highlight-line
179182

180183
const addNote = async (event) => {
181184
event.preventDefault()
@@ -192,7 +195,7 @@ const App = () => {
192195
To create a new note, a [mutation](https://tanstack.com/query/latest/docs/react/guides/mutations) is defined using the function [useMutation](https://tanstack.com/query/latest/docs/react/reference/useMutation):
193196

194197
```js
195-
const newNoteMutation = useMutation(createNote)
198+
const newNoteMutation = useMutation({ mutationFn: createNote })
196199
```
197200

198201
The parameter is the function we added to the file <i>requests.js</i>, which uses Axios to send a new note to the server.
@@ -218,7 +221,7 @@ const App = () => {
218221

219222
const newNoteMutation = useMutation(createNote, {
220223
onSuccess: () => { // highlight-line
221-
queryClient.invalidateQueries('notes') // highlight-line
224+
queryClient.invalidateQueries({ queryKey: ['notes'] }) // highlight-line
222225
},
223226
})
224227

@@ -252,7 +255,7 @@ const App = () => {
252255

253256
const updateNoteMutation = useMutation(updateNote, {
254257
onSuccess: () => {
255-
queryClient.invalidateQueries('notes')
258+
queryClient.invalidateQueries({ queryKey: ['notes'] })
256259
},
257260
})
258261

@@ -532,7 +535,7 @@ React's built-in [Context API](https://beta.reactjs.org/learn/passing-data-deepl
532535

533536
Let us now create a context in the application that stores the state management of the counter.
534537

535-
The context is created with React's hook [createContext](https://beta.reactjs.org/reference/react/createContext). Let's create a context in the file <i>CounterContext.js</i>:
538+
The context is created with React's hook [createContext](https://beta.reactjs.org/reference/react/createContext). Let's create a context in the file <i>CounterContext.jsx</i>:
536539

537540
```js
538541
import { createContext } from 'react'
@@ -594,7 +597,7 @@ The current code for the application is in [GitHub](https://github.com/fullstack
594597

595598
### Defining the counter context in a separate file
596599

597-
Our application has an annoying feature, that the functionality of the counter state management is partly defined in the <i>App</i> component. Now let's move everything related to the counter to <i>CounterContext.js</i>:
600+
Our application has an annoying feature, that the functionality of the counter state management is partly defined in the <i>App</i> component. Now let's move everything related to the counter to <i>CounterContext.jsx</i>:
598601

599602
```js
600603
import { createContext, useReducer } from 'react'
@@ -629,7 +632,7 @@ export default CounterContext
629632

630633
The file now exports, in addition to the <i>CounterContext</i> object corresponding to the context, the <i>CounterContextProvider</i> component, which is practically a context provider whose value is a counter and a dispatcher used for its state management.
631634

632-
Let's enable the context provider by making a change in <i>index.js</i>:
635+
Let's enable the context provider by making a change in <i>main.jsx</i>:
633636

634637
```js
635638
import ReactDOM from 'react-dom/client'

src/content/6/fi/osa6.md

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,8 @@ Olemme toistaiseksi sijoittaneet ohjelman tilan ja siitä huolehtivan logiikan s
1010

1111
Tututustumme Reactin suoraan tukemaan Reduxin kevytversioon, eli Reactin kontekstiin ja useRedux-hookiin sekä palvelimen tilan hallintaa helpottavaan React Query ‑kirjastoon.
1212

13-
<i>Osa päivitetty 1.2.2023</i>
14-
- <i>Uusi luku, aiheenaan React Query, useReducer ja React context korvasi Redux connect ‑luvun</i>
13+
<i>Osa päivitetty 23.8.2023</i>
14+
- <i>Create React App korvattu Vitellä</i>
15+
- <i>React Query päivitetty versioon 4</i>
1516

1617
</div>

src/content/6/fi/osa6d.md

Lines changed: 26 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -50,18 +50,19 @@ Alkuvaiheen koodi on GitHubissa repositorion [https://github.com/fullstack-hy202
5050

5151
### Palvelimella olevan datan hallinta React Query ‑kirjaston avulla
5252

53-
Hyödynnämme nyt [React Query](https://react-query-v3.tanstack.com/) ‑kirjastoa palvelimelta haettavan datan säilyttämiseen ja hallinnointiin. Asennetaan kirjasto komennolla
53+
Hyödynnämme nyt [React Query](https://tanstack.com/query/latest) ‑kirjastoa palvelimelta haettavan datan säilyttämiseen ja hallinnointiin. Kirjaston uusimmasta versiosta käytetään myös nimitystä TanStack Query mutta pitäydymme vanhassa tutussa nimessä.
54+
55+
Asennetaan kirjasto komennolla
5456

5557
```bash
56-
npm install react-query
58+
npm install @tanstack/react-query
5759
```
5860

59-
Tiedostoon <i>index.js</i> tarvitaan muutama lisäys, jotta kirjaston funktiot saadaan välitettyä koko sovelluksen käyttöön:
61+
Tiedostoon <i>main.jsx</i> tarvitaan muutama lisäys, jotta kirjaston funktiot saadaan välitettyä koko sovelluksen käyttöön:
6062

6163
```js
62-
import React from 'react'
6364
import ReactDOM from 'react-dom/client'
64-
import { QueryClient, QueryClientProvider } from 'react-query' // highlight-line
65+
import { QueryClient, QueryClientProvider } from '@tanstack/react-query' // highlight-line
6566

6667
import App from './App'
6768

@@ -77,19 +78,19 @@ ReactDOM.createRoot(document.getElementById('root')).render(
7778
Voimme nyt hakea muistiinpanot komponentissa <i>App</i>. Koodi laajenee seuraavasti:
7879

7980
```js
80-
import { useQuery } from 'react-query' // highlight-line
81+
import { useQuery } from '@tanstack/react-query' // highlight-line
8182
import axios from 'axios' // highlight-line
8283

8384
const App = () => {
8485
// ...
8586

8687
// highlight-start
87-
const result = useQuery(
88-
'notes',
89-
() => axios.get('http://localhost:3001/notes').then(res => res.data)
90-
)
88+
const result = useQuery({
89+
queryKey: ['notes'],
90+
queryFn: () => axios.get('http://localhost:3001/notes').then(res => res.data)
91+
})
9192

92-
console.log(result)
93+
console.log(JSON.parse(JSON.stringify(result)))
9394
// highlight-end
9495

9596
// highlight-start
@@ -106,7 +107,7 @@ const App = () => {
106107
}
107108
```
108109

109-
Datan hakeminen palvelimelta tapahtuu edelleen tuttuun tapaan Axiosin <i>get</i>-metodilla. Axiosin metodikutsu on kuitenkin nyt kääritty [useQuery](https://react-query-v3.tanstack.com/reference/useQuery)-funktiolla muodostetuksi [kyselyksi](https://react-query-v3.tanstack.com/guides/queries). Funktiokutsun ensimmäisenä parametrina on merkkijono <i>notes</i> joka toimii [avaimena](https://react-query-v3.tanstack.com/guides/query-keys) määriteltyyn kyselyyn, eli muistiinpanojen listaan.
110+
Datan hakeminen palvelimelta tapahtuu edelleen tuttuun tapaan Axiosin <i>get</i>-metodilla. Axiosin metodikutsu on kuitenkin nyt kääritty [useQuery](https://tanstack.com/query/latest/docs/react/reference/useQuery)-funktiolla muodostetuksi [kyselyksi](https://tanstack.com/query/latest/docs/react/guides/queries). Funktiokutsun ensimmäisenä parametrina on merkkijono <i>notes</i> joka toimii [avaimena](https://tanstack.com/query/latest/docs/react/guides/query-keys) määriteltyyn kyselyyn, eli muistiinpanojen listaan.
110111

111112
Funktion <i>useQuery</i> paluuarvo on olio, joka kertoo kyselyn tilan. Konsoliin tehty tulostus havainnollistaa tilannetta:
112113

@@ -140,7 +141,10 @@ import { getNotes } from './requests' // highlight-line
140141
const App = () => {
141142
// ...
142143

143-
const result = useQuery('notes', getNotes) // highlight-line
144+
const result = useQuery({
145+
queryKey: ['notes'],
146+
queryFn: () => getNotes // highlight-line
147+
})
144148

145149
// ...
146150
}
@@ -173,7 +177,7 @@ import { useQuery, useMutation } from 'react-query' // highlight-line
173177
import { getNotes, createNote } from './requests' // highlight-line
174178

175179
const App = () => {
176-
const newNoteMutation = useMutation(createNote) // highlight-line
180+
const newNoteMutation = useMutation({ mutationFn: createNote }) // highlight-line
177181

178182
const addNote = async (event) => {
179183
event.preventDefault()
@@ -187,10 +191,10 @@ const App = () => {
187191
}
188192
```
189193

190-
Uuden muistiinpanon luomista varten määritellään [mutaatio](https://react-query-v3.tanstack.com/guides/mutations) funktion [useMutation](https://react-query-v3.tanstack.com/reference/useMutation) avulla:
194+
Uuden muistiinpanon luomista varten määritellään [mutaatio](https://tanstack.com/query/latest/docs/react/guides/mutations) funktion [useMutation](https://tanstack.com/query/latest/docs/react/reference/useMutatio) avulla:
191195

192196
```js
193-
const newNoteMutation = useMutation(createNote)
197+
const newNoteMutation = useMutation({ mutationFn: createNote })
194198
```
195199

196200
Parametrina on tiedostoon <i>requests.js</i> lisäämämme funktio, joka lähettää Axiosin avulla uuden muistiinpanon palvelille.
@@ -204,7 +208,7 @@ newNoteMutation.mutate({ content, important: true })
204208
Ratkaisumme on hyvä. Paitsi se ei toimi. Uusi muistiinpano kyllä tallettuu palvelimelle, mutta se ei päivity näytölle.
205209

206210
Jotta saamme renderöityä myös uuden muistiinpanon, meidän on kerrottava React Querylle, että kyselyn, jonka avaimena on merkkijono <i>notes</i> vanha tulos tulee mitätöidä eli
207-
[invalidoida](https://react-query-v3.tanstack.com/guides/invalidations-from-mutations).
211+
[invalidoida](https://tanstack.com/query/latest/docs/react/guides/invalidations-from-mutations).
208212

209213
Invalidointi on onneksi helppoa, se voidaan tehdä kytkemällä mutaatioon sopiva <i>onSuccess</i>-takaisinkutsufunktio:
210214

@@ -217,7 +221,7 @@ const App = () => {
217221

218222
const newNoteMutation = useMutation(createNote, {
219223
onSuccess: () => { // highlight-line
220-
queryClient.invalidateQueries('notes') // highlight-line
224+
queryClient.invalidateQueries({ queryKey: ['notes'] }) // highlight-line
221225
},
222226
})
223227

@@ -251,7 +255,7 @@ const App = () => {
251255

252256
const updateNoteMutation = useMutation(updateNote, {
253257
onSuccess: () => {
254-
queryClient.invalidateQueries('notes')
258+
queryClient.invalidateQueries({ queryKey: ['notes'] })
255259
},
256260
})
257261

@@ -532,7 +536,7 @@ Reactin sisäänrakennettu [Context API](https://beta.reactjs.org/learn/passing-
532536

533537
Luodaan sovellukseen nyt konteksti, joka tallettaa laskurin tilanhallinnan.
534538

535-
Konteksti luodaan Reactin hookilla [createContext](https://beta.reactjs.org/reference/react/createContext). Luodaan konteksti tiedostoon <i>CounterContext.js</i>:
539+
Konteksti luodaan Reactin hookilla [createContext](https://beta.reactjs.org/reference/react/createContext). Luodaan konteksti tiedostoon <i>CounterContext.jsx</i>:
536540

537541
```js
538542
import { createContext } from 'react'
@@ -596,7 +600,7 @@ Sovelluksen tämänhetkinen koodi on GitHubissa repositorion [https://github.com
596600

597601
### Laskurikontekstin määrittely omassa tiedostossa
598602

599-
Sovelluksessamme on vielä sellainen ikävä piirre, että laskurin tilanhallinnan toiminnallisuus on määritelty osin komponentissa <i>App</i>. Siirretään nyt kaikki laskuriin liittyvä tiedostoon <i>CounterContext.js</i>:
603+
Sovelluksessamme on vielä sellainen ikävä piirre, että laskurin tilanhallinnan toiminnallisuus on määritelty osin komponentissa <i>App</i>. Siirretään nyt kaikki laskuriin liittyvä tiedostoon <i>CounterContext.jsx</i>:
600604

601605
```js
602606
import { createContext, useReducer } from 'react'
@@ -631,7 +635,7 @@ export default CounterContext
631635

632636
Tiedosto exporttaa nyt kontekstia vastaavan olion <i>CounterContext</i> lisäksi komponentin <i>CounterContextProvider</i> joka on käytännössä kontekstin tarjoaja (context provider), jonka arvona on laskuri ja sen tilanhallintaan käytettävä dispatcheri.
633637

634-
Otetaan kontekstin tarjoaja käyttöön tiedostossa <i>index.js</i>
638+
Otetaan kontekstin tarjoaja käyttöön tiedostossa <i>main.jsx</i>
635639

636640
```js
637641
import ReactDOM from 'react-dom/client'

0 commit comments

Comments
 (0)