Avastage Reacti useActionState hook sujuvaks olekuhalduseks asĂŒnkroonsete tegevuste kaudu. Parandage oma rakenduse tĂ”husust ja kasutajakogemust.
Reacti useActionState'i rakendamine: tegevuspÔhine olekuhaldus
Reacti useActionState hook, mis on kasutusele vĂ”etud hilisemates versioonides, pakub tĂ€iustatud lĂ€henemist asĂŒnkroonsetest tegevustest tulenevate olekuvĂ€rskenduste haldamiseks. See vĂ”imas tööriist lihtsustab mutatsioonide kĂ€sitlemise, kasutajaliidese vĂ€rskendamise ja veaolukordade haldamise protsessi, eriti kui töötada Reacti serverikomponentide (RSC) ja serveri tegevustega. See juhend uurib useActionState'i peensusi, pakkudes praktilisi nĂ€iteid ja parimaid praktikaid rakendamiseks.
TegevuspÔhise olekuhalduse vajaduse mÔistmine
Traditsiooniline Reacti olekuhaldus hÔlmab sageli laadimis- ja veaolukordade eraldi haldamist komponentide sees. Kui tegevus (nt vormi esitamine, andmete toomine) kÀivitab olekuvÀrskenduse, haldavad arendajad neid olekuid tavaliselt mitme useState'i kutse ja potentsiaalselt keeruka tingimusloogikaga. useActionState pakub puhtamat ja integreeritumat lahendust.
MÔelgem lihtsale vormi esitamise stsenaariumile. Ilma useActionState'ita vÔiks teil olla:
- Olekumuutuja vormi andmete jaoks.
- Olekumuutuja, et jÀlgida, kas vormi esitatakse (laadimisolek).
- Olekumuutuja veateadete hoidmiseks.
See lĂ€henemine vĂ”ib viia paljusĂ”nalise koodi ja potentsiaalsete ebakĂ”ladeni. useActionState koondab need mured ĂŒhte hooki, lihtsustades loogikat ja parandades koodi loetavust.
useActionState'i tutvustus
useActionState hook aktsepteerib kahte argumenti:
- AsĂŒnkroonne funktsioon ("tegevus"), mis teostab olekuvĂ€rskenduse. See vĂ”ib olla serveri tegevus vĂ”i mis tahes asĂŒnkroonne funktsioon.
- Algne olekuvÀÀrtus.
See tagastab massiivi, mis sisaldab kahte elementi:
- Hetke olekuvÀÀrtus.
- Funktsioon tegevuse kÀivitamiseks (dispatch). See funktsioon haldab automaatselt tegevusega seotud laadimis- ja veaolukordi.
Siin on pÔhiline nÀide:
import { useActionState } from 'react';
async function updateServer(prevState, formData) {
// Simuleerime asĂŒnkroonset serveri uuendust.
await new Promise(resolve => setTimeout(resolve, 1000));
const data = Object.fromEntries(formData);
if (data.name === "error") {
return 'Serveri uuendamine ebaÔnnestus.';
}
return `Nimi uuendatud: ${data.name}`;
}
function MyComponent() {
const [state, dispatch] = useActionState(updateServer, 'Algne olek');
async function handleSubmit(event) {
event.preventDefault();
const formData = new FormData(event.target);
const result = await dispatch(formData);
console.log(result);
}
return (
);
}
Selles nÀites:
updateServeron asĂŒnkroonne tegevus, mis simuleerib serveri uuendamist. See vĂ”tab vastu eelmise oleku ja vormi andmed.useActionStateinitsialiseerib oleku vÀÀrtusega 'Algne olek' ning tagastab hetke oleku jadispatch-funktsiooni.handleSubmitfunktsioon kutsubdispatch'i vormi andmetega.useActionStatehaldab automaatselt laadimis- ja veaolukordi tegevuse tĂ€itmise ajal.
Laadimis- ja veaolukordade kÀsitlemine
Ăks useActionState'i peamisi eeliseid on selle sisseehitatud laadimis- ja veaolukordade haldamine. dispatch-funktsioon tagastab promise'i, mis laheneb tegevuse tulemusega. Kui tegevus viskab vea, lĂŒkkab promise vea tagasi. Seda saate kasutada kasutajaliidese vastavaks vĂ€rskendamiseks.
Muudame eelmist nÀidet, et kuvada laadimisteade ja veateade:
import { useActionState } from 'react';
import { useState } from 'react';
async function updateServer(prevState, formData) {
// Simuleerime asĂŒnkroonset serveri uuendust.
await new Promise(resolve => setTimeout(resolve, 1000));
const data = Object.fromEntries(formData);
if (data.name === "error") {
throw new Error('Serveri uuendamine ebaÔnnestus.');
}
return `Nimi uuendatud: ${data.name}`;
}
function MyComponent() {
const [state, dispatch] = useActionState(updateServer, 'Algne olek');
const [isSubmitting, setIsSubmitting] = useState(false);
const [errorMessage, setErrorMessage] = useState(null);
async function handleSubmit(event) {
event.preventDefault();
const formData = new FormData(event.target);
setIsSubmitting(true);
setErrorMessage(null);
try {
const result = await dispatch(formData);
console.log(result);
} catch (error) {
console.error("Viga esitamisel:", error);
setErrorMessage(error.message);
} finally {
setIsSubmitting(false);
}
}
return (
);
}
PÔhilised muudatused:
- Lisasime
isSubmittingjaerrorMessageolekumuutujad laadimis- ja veaolukordade jĂ€lgimiseks. handleSubmitfunktsioonis seameisSubmittingvÀÀrtusekstrueennedispatchkutsumist ja pĂŒĂŒame kinni kĂ”ik vead, et uuendadaerrorMessage'i.- Me keelame esitamisnupu esitamise ajal ja kuvame tingimuslikult laadimis- ja veateateid.
useActionState koos serveri tegevustega Reacti serverikomponentides (RSC)
useActionState sÀrab eriti siis, kui seda kasutatakse koos Reacti serverikomponentide (RSC) ja serveri tegevustega. Serveri tegevused on funktsioonid, mis kÀivitatakse serveris ja vÔivad otse muuta andmeallikaid. Need vÔimaldavad teil teha serveripoolseid toiminguid ilma API otspunkte kirjutamata.
MÀrkus: See nÀide nÔuab Reacti keskkonda, mis on konfigureeritud serverikomponentide ja serveri tegevuste jaoks.
// app/actions.js (Serveri tegevus)
'use server';
import { cookies } from 'next/headers'; //NĂ€ide Next.js jaoks
export async function updateName(prevState, formData) {
const name = formData.get('name');
if (!name) {
return 'Palun sisestage nimi.';
}
try {
// Simuleerime andmebaasi uuendust.
await new Promise(resolve => setTimeout(resolve, 1000));
cookies().set('userName', name);
return `Nimi uuendatud: ${name}`; //Ănnestus!
} catch (error) {
console.error("Andmebaasi uuendamine ebaÔnnestus:", error);
return 'Nime uuendamine ebaÔnnestus.'; // TÀhtis: Tagastage sÔnum, Àrge visake viga (Error)
}
}
// app/page.jsx (Reacti serverikomponent)
'use client';
import { useActionState } from 'react';
import { updateName } from './actions';
function MyComponent() {
const [state, dispatch] = useActionState(updateName, 'Algne olek');
async function handleSubmit(event) {
event.preventDefault();
const formData = new FormData(event.target);
const result = await dispatch(formData);
console.log(result);
}
return (
);
}
export default MyComponent;
Selles nÀites:
updateNameon serveri tegevus, mis on defineeritud failisapp/actions.js. See vÔtab vastu eelmise oleku ja vormi andmed, uuendab andmebaasi (simuleeritud) ning tagastab edu- vÔi veateate. Oluline on, et tegevus tagastab sÔnumi, mitte ei viska viga. Serveri tegevused eelistavad informatiivsete sÔnumite tagastamist.- Komponent on mÀrgitud kliendikomponendiks (
'use client'), et kasutadauseActionStatehooki. handleSubmitfunktsioon kutsubdispatch'i vormi andmetega.useActionStatehaldab automaatselt olekuvÀrskendust vastavalt serveri tegevuse tulemusele.
Olulised kaalutlused serveri tegevuste puhul
- Vigade kÀsitlemine serveri tegevustes: Vigade viskamise asemel tagastage oma serveri tegevusest tÀhendusrikas veateade.
useActionStatekĂ€sitleb seda teadet uue olekuna. See vĂ”imaldab sujuvat veakĂ€sitlust kliendi poolel. - Optimistlikud uuendused: Serveri tegevusi saab kasutada koos optimistlike uuendustega, et parandada tajutavat jĂ”udlust. Saate kasutajaliidest kohe uuendada ja tĂŒhistada muudatuse, kui tegevus ebaĂ”nnestub.
- Uuesti valideerimine: PÀrast edukat mutatsiooni kaaluge vahemÀllu salvestatud andmete uuesti valideerimist, et tagada kasutajaliidese vastavus uusimale olekule.
useActionState'i tÀiustatud tehnikad
1. Redutseerija kasutamine keerukate olekuvÀrskenduste jaoks
Keerukama olekuloogika jaoks saate kombineerida useActionState'i redutseerija (reducer) funktsiooniga. See vÔimaldab teil hallata olekuvÀrskendusi prognoositaval ja hooldataval viisil.
import { useActionState } from 'react';
import { useReducer } from 'react';
const initialState = {
count: 0,
message: 'Algne olek',
};
function reducer(state, action) {
switch (action.type) {
case 'INCREMENT':
return { ...state, count: state.count + 1 };
case 'DECREMENT':
return { ...state, count: state.count - 1 };
case 'SET_MESSAGE':
return { ...state, message: action.payload };
default:
return state;
}
}
async function updateState(state, action) {
// Simuleerime asĂŒnkroonset operatsiooni.
await new Promise(resolve => setTimeout(resolve, 500));
switch (action.type) {
case 'INCREMENT':
return reducer(state, action);
case 'DECREMENT':
return reducer(state, action);
case 'SET_MESSAGE':
return reducer(state, action);
default:
return state;
}
}
function MyComponent() {
const [state, dispatch] = useActionState(updateState, initialState);
return (
Arv: {state.count}
SÔnum: {state.message}
);
}
2. Optimistlikud uuendused useActionState'iga
Optimistlikud uuendused parandavad kasutajakogemust, vĂ€rskendades koheselt kasutajaliidest, justkui oleks tegevus Ă”nnestunud, ja seejĂ€rel tĂŒhistades uuenduse, kui tegevus ebaĂ”nnestub. See vĂ”ib muuta teie rakenduse tundlikumaks.
import { useActionState } from 'react';
import { useState } from 'react';
async function updateServer(prevState, formData) {
// Simuleerime asĂŒnkroonset serveri uuendust.
await new Promise(resolve => setTimeout(resolve, 1000));
const data = Object.fromEntries(formData);
if (data.name === "error") {
throw new Error('Serveri uuendamine ebaÔnnestus.');
}
return `Nimi uuendatud: ${data.name}`;
}
function MyComponent() {
const [name, setName] = useState('Algne nimi');
const [state, dispatch] = useActionState(async (prevName, newName) => {
try {
const result = await updateServer(prevName, {
name: newName,
});
return newName; // Uuenda Ônnestumise korral
} catch (error) {
// TĂŒhista vea korral
console.error("Uuendamine ebaÔnnestus:", error);
setName(prevName);
return prevName;
}
}, name);
async function handleSubmit(event) {
event.preventDefault();
const formData = new FormData(event.target);
const newName = formData.get('name');
setName(newName); // Uuenda kasutajaliidest optimistlikult
await dispatch(newName);
}
return (
);
}
3. Tegevuste viivitamine (Debouncing)
MÔnes olukorras vÔite soovida tegevusi viivitada (debounce), et vÀltida nende liiga sagedast kÀivitamist. See vÔib olla kasulik nÀiteks otsingusisendite puhul, kus soovite tegevuse kÀivitada alles siis, kui kasutaja on teatud aja jooksul tippimise lÔpetanud.
import { useActionState } from 'react';
import { useState, useEffect } from 'react';
async function searchItems(prevState, query) {
// Simuleerime asĂŒnkroonset otsingut.
await new Promise(resolve => setTimeout(resolve, 500));
return `Otsingutulemused pÀringule: ${query}`;
}
function MyComponent() {
const [query, setQuery] = useState('');
const [state, dispatch] = useActionState(searchItems, 'Algne olek');
useEffect(() => {
const timeoutId = setTimeout(() => {
if (query) {
dispatch(query);
}
}, 300); // Viivitus 300ms
return () => clearTimeout(timeoutId);
}, [query, dispatch]);
return (
setQuery(e.target.value)}
/>
Olek: {state}
);
}
Parimad praktikad useActionState'i kasutamisel
- Hoidke tegevused puhtad: Veenduge, et teie tegevused oleksid puhtad funktsioonid (vÔi nii lÀhedal sellele kui vÔimalik). Neil ei tohiks olla muid kÔrvalmÔjusid peale oleku uuendamise.
- KÀsitlege vigu sujuvalt: KÀsitlege alati vigu oma tegevustes ja pakkuge kasutajale informatiivseid veateateid. Nagu eespool serveri tegevuste puhul mÀrgitud, eelistage serveri tegevusest veateate stringi tagastamist, mitte vea viskamist.
- Optimeerige jÔudlust: Olge teadlik oma tegevuste jÔudlusmÔjudest, eriti suurte andmekogumitega tegelemisel. Kaaluge memoiseerimistehnikate kasutamist, et vÀltida tarbetuid uuesti renderdamisi.
- Kaaluge ligipÀÀsetavust: Veenduge, et teie rakendus jÀÀks ligipÀÀsetavaks kÔigile kasutajatele, sealhulgas puuetega inimestele. Pakkuge sobivaid ARIA atribuute ja klaviatuurinavigatsiooni.
- PĂ”hjalik testimine: Kirjutage ĂŒhik- ja integratsiooniteste, et tagada teie tegevuste ja olekuvĂ€rskenduste korrektne toimimine.
- Rahvusvahelistamine (i18n): Globaalsete rakenduste jaoks rakendage i18n, et toetada mitut keelt ja kultuuri.
- Lokaliseerimine (l10n): Kohandage oma rakendus konkreetsetele lokaatidele, pakkudes lokaliseeritud sisu, kuupĂ€evavorminguid ja valuutasĂŒmboleid.
useActionState vs. teised olekuhalduse lahendused
Kuigi useActionState pakub mugavat viisi tegevuspÔhiste olekuvÀrskenduste haldamiseks, ei asenda see kÔiki olekuhalduse lahendusi. Keerukate rakenduste puhul, kus on globaalne olek, mida tuleb jagada mitme komponendi vahel, vÔivad raamistikud nagu Redux, Zustand vÔi Jotai olla sobivamad.
Millal kasutada useActionState'i:
- Lihtsa kuni mÔÔduka keerukusega olekuvÀrskendused.
- Olekumuuendused, mis on tihedalt seotud asĂŒnkroonsete tegevustega.
- Integratsioon Reacti serverikomponentide ja serveri tegevustega.
Millal kaaluda teisi lahendusi:
- Keerukas globaalne olekuhaldus.
- Olek, mida tuleb jagada suure hulga komponentide vahel.
- TÀiustatud funktsioonid nagu ajas rÀndamise silumine (time-travel debugging) vÔi vahevara (middleware).
KokkuvÔte
Reacti useActionState hook pakub vĂ”imsat ja elegantset viisi asĂŒnkroonsete tegevuste poolt kĂ€ivitatud olekuvĂ€rskenduste haldamiseks. Koondades laadimis- ja veaolukorrad, lihtsustab see koodi ja parandab loetavust, eriti töötades Reacti serverikomponentide ja serveri tegevustega. Selle tugevuste ja piirangute mĂ”istmine vĂ”imaldab teil valida oma rakenduse jaoks Ă”ige olekuhalduse lĂ€henemisviisi, mis viib hooldatavama ja tĂ”husama koodini.
JÀrgides selles juhendis toodud parimaid praktikaid, saate tÔhusalt kasutada useActionState'i oma rakenduse kasutajakogemuse ja arendustöövoo parandamiseks. Pidage meeles, et peate arvestama oma rakenduse keerukusega ja valima olekuhalduse lahenduse, mis vastab kÔige paremini teie vajadustele. Alates lihtsatest vormide esitamistest kuni keerukate andmete mutatsioonideni vÔib useActionState olla vÀÀrtuslik tööriist teie Reacti arendusarsenalis.