Дополнителни редјусери во Redux
Да ја отвориме нашата апликација со производи,
а во неа датотеката productsSlice.js. Веројатно
забележавте дека креиравме thunk fetchProducts
како посебна функција? Направивме така, бидејќи
createSlice не поддржува дефинирање на
thunks. Како тогаш да натераме
reducer на слајсот products да одговара на акциите,
кои се дефинирани надвор од products?
Бидејќи ние треба да ги обработиме акциите,
кои ги испраќа thunk-от fetchProducts.
За вакви случаи, createSlice има
својство extraReducers, кое овозможува
додавање на дополнителни редјусери, кои
пак ќе ги обработат акциите,
дефинирани не во овој слајс.
Сега да во телото на функцијата createSlice
после својството reducers со сите редјусери
додадеме уште еден метод extraReducers:
extraReducers() {},
На овој метод мора да му пренесеме објект
builder, кој има методи, со
чија помош може да се додадат
дополнителни редјусери:
extraReducers(builder) {},
Ќе користиме еден од методите на builder -
addCase, кој како прв параметар прима
креатор на акција, а како втор reducer. Една од
акциите, кои ќе ни ги испраќа
fetchProducts при барањето е
fetchProducts.pending, што ни кажува
дека барањето е испратено. Да во овој
случај го смениме статусот на 'in progress'
(пред тоа беше 'idle'):
extraReducers(builder) {
builder.addCase(fetchProducts.pending, (state) => {
state.status = 'in progress'
})
},
Сега да ја обработиме акцијата, која ќе се испрати
во случај на успешно барање. Овде ќе
смениме не само статусот во состојбата на
'success', туку и ќе ги земеме производите во
слајсот products од payload на акцијата.
За да ги собереме сите производи ќе ни треба
методот 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)
})
},
Во случај на неуспешно барање, ќе го смениме
статусот на 'fail' и ќе запишеме во состојбата
порака за грешката:
.addCase(fetchProducts.rejected, (state, action) => {
state.status = 'fail'
state.error = action.error.message
})
Ако сега ја стартуваме нашата апликација
и во менито кликнеме на 'Products', тогаш
за неколку секунди (се сеќавате на доцнењето,
кое го поставивме на серверот?) ќе видиме
листа со производи.
Исто така ќе ги видиме промените и во Redux
DevTools. Сега нашите производи ќе се појават и
во состојбата (погледнете ја јазичката 'State'),
ако сте кликнале на акцијата
products/fetchProducts/fulfilled.
Таму ќе се појави и новиот статус 'success'.
Сега кликнете на акцијата
products/fetchProducts/pending и погледнете,
со што се разликува јазичката 'State'.
Единствениот непријатен момент, кој
може да ви се случи (зборував за ова
на претходниот час) - е дуплирање на
барањето на податоци. Како резултат на што, кај нас
во листата ќе добиеме не 8, туку целых
16 производи и критични предупредувања
во конзолата на развивачот. Да го
разгледаме ова на следниот час.
Отворете ја вашата апликација со студенти.
Отворете ја во неа датотеката studentsSlice.js. Во
телото на функцијата createSlice после својството
reducers додадете својство extraReducers.
Проследете му на методот extraReducers builder.
Со помош на методот builder.addCase
додадете обработка за акциите pending,
fulfilled и rejected, кои
ги испраќа fetchStudents при барање
на податоци, како што е прикажано на часот.