Redukserët shtesë në Redux
Le të hapim aplikacionin tonë të produkteve,
dhe në të skedarin productsSlice.js. Ndoshta e keni
vënë re, ne krijuam thunk fetchProducts
si një funksion të veçantë? E bëmë kështu, sepse
createSlice nuk mbështet përcaktimin
e thunks. Si mund ta bëjmë në këtë rast që
reducer i slice products të përgjigjet ndaj aksioneve,
të cilat janë përcaktuar jashtë products?
Në fund të fundit, ne kemi nevojë të përpunojmë aksionet,
që dërgon thunk fetchProducts.
Për raste të tilla, createSlice ka
vetinë extraReducers, e cila lejon
shtimin e redukserëve shtesë, të cilët
nga ana tjetër do të përpunojnë aksionet,
të përcaktuara jo në këtë slice.
Tani le të shtojmë në trupin e funksionit createSlice
pas vetisë reducers me të gjithë redukserët
edhe një metodë tjetër extraReducers:
extraReducers() {},
Kësaj metode duhet t'i kalojmë një objekt
builder, i cili ka metoda, me
ndihmën e të cilave mund të shtohen
redukserë shtesë:
extraReducers(builder) {},
Ne do të përdorim një nga metodat e builder -
addCase, i cili si parametër të parë pranon
një krijues aksioni, dhe si të dytë një reducer. Një nga
aksionet, që do të na dërgojë
fetchProducts gjatë kërkesës është
fetchProducts.pending, që na tregon
se kërkesa është dërguar. Le të ndryshojmë në këtë
rast statusin në 'in progress'
(para kësaj ai ishte 'idle'):
extraReducers(builder) {
builder.addCase(fetchProducts.pending, (state) => {
state.status = 'in progress'
})
},
Tani le të përpunojmë aksionin, i cili do të dërgohet
në rast të kërkesës me sukses. Këtu do të
ndryshojmë jo vetëm statusin në state në
'success', por edhe do të marrim produktet në
slice products nga payload i aksionit.
Për të mbledhur të gjitha produktet do të na duhet
metoda concat:
extraReducers(builder) {
builder
.addCase(fetchProducts.pending, (state) => {
state.status = 'in progress'
})
.addCase(fetchProducts.fulfilled, (state, action) => {
state.status = 'success'
state.products = state.products.concat(action.payload)
})
},
Në rast të kërkesës të pasuksesshme do të ndryshojmë
statusin në 'fail' dhe do të shkruajmë në state
mesazhin e gabimit:
.addCase(fetchProducts.rejected, (state, action) => {
state.status = 'fail'
state.error = action.error.message
})
Nëse e nisim tani aplikacionin tonë
dhe në menu klikojmë te 'Products', atëherë
pas disa sekondash (mbani mend për vonesën,
që kemi vendosur në server?) do të shohim
listën me produkte.
Po kështu do të shohim ndryshimet edhe në Redux
DevTools. Tani produktet tanë do të shfaqen edhe
në state (shikoni skedën 'State'),
nëse keni klikuar mbi aksionin
products/fetchProducts/fulfilled.
Atje do të shfaqet edhe statusi i ri 'success'.
Klikoni tani mbi aksionin
products/fetchProducts/pending dhe shikoni,
si ndryshon tani skeda 'State'.
Momenti i vetëm i pakëndshëm, i cili
mund t'ju ndodhë (unë fola për këtë
në mësimin e kaluar) - është dublimi i
kërkesës së të dhënave. Si rezultat, në listën tonë
do të ketë jo 8, por gjithsej
16 produkte dhe paralajmërime kritike
në konsolën e zhvilluesit. Le ta
shqyrtojmë këtë në mësimin vijues.
Hapni aplikacionin tuaj me studentët.
Hapni në të skedarin studentsSlice.js. Në
trupin e funksionit createSlice pas vetisë
reducers shtoni vetinë extraReducers.
Kalo metodës extraReducers builder.
Me ndihmën e metodës builder.addCase
shtoni përpunimin për aksionet pending,
fulfilled dhe rejected, të cilat
dërgon fetchStudents gjatë kërkesës
së të dhënave, siç tregohet në mësim.