Čeština

Naučte se implementovat React Error Boundaries pro elegantní zpracování chyb, prevenci pádů aplikace a vylepšení uživatelského zážitku. Prozkoumejte osvědčené postupy, pokročilé techniky a příklady z praxe.

React Error Boundaries: Komplexní průvodce robustním zpracováním chyb

Ve světě moderního webového vývoje je plynulý a spolehlivý uživatelský zážitek prvořadý. Jediná neošetřená chyba může způsobit pád celé React aplikace, což zanechá uživatele frustrované a může vést ke ztrátě cenných dat. React Error Boundaries poskytují mocný mechanismus pro elegantní zpracování těchto chyb, prevenci katastrofických pádů a nabízejí odolnější a uživatelsky přívětivější zážitek. Tento průvodce poskytuje komplexní přehled React Error Boundaries, pokrývající jejich účel, implementaci, osvědčené postupy a pokročilé techniky.

Co jsou React Error Boundaries?

Error Boundaries jsou React komponenty, které zachytávají JavaScriptové chyby kdekoli ve stromu svých potomků (child component tree), zaznamenávají tyto chyby a zobrazují záložní uživatelské rozhraní (fallback UI) namísto stromu komponent, který selhal. Fungují jako záchranná síť, která zabraňuje, aby chyby v jedné části aplikace shodily celé UI. Byly představeny v Reactu 16 a nahradily předchozí, méně robustní mechanismy pro zpracování chyb.

Představte si Error Boundaries jako bloky `try...catch` pro React komponenty. Na rozdíl od `try...catch` však fungují pro komponenty a poskytují deklarativní a znovupoužitelný způsob, jak zpracovávat chyby napříč vaší aplikací.

Proč používat Error Boundaries?

Error Boundaries nabízejí několik klíčových výhod:

Vytvoření komponenty Error Boundary

Pro vytvoření komponenty Error Boundary musíte definovat třídní komponentu, která implementuje jednu nebo obě z následujících metod životního cyklu:

Zde je základní příklad komponenty Error Boundary:


class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props);
    this.state = { hasError: false };
  }

  static getDerivedStateFromError(error) {
    // Aktualizuje stav, aby další render zobrazil záložní UI.
    return { hasError: true };
  }

  componentDidCatch(error, info) {
    // Příklad "componentStack":
    //   in ComponentThatThrows (created by App)
    //   in App
    console.error("Caught an error: ", error, info.componentStack);
    // Chybu můžete také zalogovat do služby pro hlášení chyb
    // logErrorToMyService(error, info.componentStack);
  }

  render() {
    if (this.state.hasError) {
      // Můžete vykreslit jakékoliv vlastní záložní UI
      return 

Něco se pokazilo.

; } return this.props.children; } }

Vysvětlení:

Použití Error Boundaries

Chcete-li použít Error Boundary, jednoduše obalte komponentu nebo komponenty, které chcete chránit, komponentou ErrorBoundary:



  


Pokud ComponentThatMightThrow vyvolá chybu, ErrorBoundary chybu zachytí, aktualizuje svůj stav a vykreslí své záložní UI. Zbytek aplikace bude nadále normálně fungovat.

Umístění Error Boundary

Umístění Error Boundaries je klíčové pro efektivní zpracování chyb. Zvažte tyto strategie:

Příklad:


function App() {
  return (
    
); }

V tomto příkladu je každá hlavní část aplikace (Header, Sidebar, ContentArea, Footer) obalena komponentou Error Boundary. To umožňuje každé sekci zpracovávat chyby nezávisle, čímž se zabrání, aby jediná chyba ovlivnila celou aplikaci.

Přizpůsobení záložního UI

Záložní UI zobrazené komponentou Error Boundary by mělo být informativní a uživatelsky přívětivé. Zvažte tyto pokyny:

Příklad:


class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props);
    this.state = { hasError: false };
  }

  static getDerivedStateFromError(error) {
    // Aktualizuje stav, aby další render zobrazil záložní UI.
    return { hasError: true };
  }

  componentDidCatch(error, info) {
    // Chybu můžete také zalogovat do služby pro hlášení chyb
    console.error("Caught an error: ", error, info.componentStack);
  }

  render() {
    if (this.state.hasError) {
      // Můžete vykreslit jakékoliv vlastní záložní UI
      return (
        

Jejda! Něco se pokazilo.

Omlouváme se, ale při pokusu o zobrazení tohoto obsahu došlo k chybě.

Zkuste prosím obnovit stránku nebo kontaktujte podporu, pokud problém přetrvává.

Kontaktovat podporu
); } return this.props.children; } }

Tento příklad zobrazuje informativnější záložní UI, které obsahuje jasnou chybovou zprávu, navrhovaná řešení a odkazy na obnovení stránky a kontaktování podpory.

Zpracování různých typů chyb

Error Boundaries zachytávají chyby, které se vyskytnou během renderování, v metodách životního cyklu a v konstruktorech celého stromu pod nimi. *Nezachytávají* chyby v:

Pro zpracování těchto typů chyb musíte použít jiné techniky.

Obslužné rutiny událostí

Pro chyby, které se vyskytnou v obslužných rutinách událostí, použijte standardní blok try...catch:


function MyComponent() {
  const handleClick = () => {
    try {
      // Kód, který může vyvolat chybu
      throw new Error("Something went wrong in the event handler");
    } catch (error) {
      console.error("Error in event handler: ", error);
      // Zpracujte chybu (např. zobrazte chybovou zprávu)
      alert("Došlo k chybě. Zkuste to prosím znovu.");
    }
  };

  return ;
}

Asynchronní kód

Pro chyby, které se vyskytnou v asynchronním kódu, použijte bloky try...catch uvnitř asynchronní funkce:


function MyComponent() {
  useEffect(() => {
    async function fetchData() {
      try {
        const response = await fetch("https://api.example.com/data");
        const data = await response.json();
        // Zpracujte data
        console.log(data);
      } catch (error) {
        console.error("Error fetching data: ", error);
        // Zpracujte chybu (např. zobrazte chybovou zprávu)
        alert("Načítání dat se nezdařilo. Zkuste to prosím později znovu.");
      }
    }

    fetchData();
  }, []);

  return 
Loading data...
; }

Alternativně můžete použít globální mechanismus pro zpracování chyb pro neošetřená zamítnutí příslibů (unhandled promise rejections):


window.addEventListener('unhandledrejection', function(event) {
  console.error('Unhandled rejection (promise: ', event.promise, ', reason: ', event.reason, ');');
  // Volitelně zobrazte globální chybovou zprávu nebo zalogujte chybu do služby
  alert("Došlo k neočekávané chybě. Zkuste to prosím později znovu.");
});

Pokročilé techniky Error Boundary

Resetování Error Boundary

V některých případech můžete chtít uživatelům poskytnout způsob, jak resetovat Error Boundary a zkusit znovu operaci, která chybu způsobila. To může být užitečné, pokud byla chyba způsobena dočasným problémem, například problémem se sítí.

K resetování Error Boundary můžete použít knihovnu pro správu stavu, jako je Redux nebo Context, pro správu chybového stavu a poskytnutí resetovací funkce. Alternativně můžete použít jednodušší přístup tím, že vynutíte znovupřipojení (remount) Error Boundary.

Příklad (vynucení znovupřipojení):


class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props);
    this.state = { hasError: false, errorCount: 0, key: 0 };
  }

  static getDerivedStateFromError(error) {
    // Aktualizuje stav, aby další render zobrazil záložní UI.
    return { hasError: true };
  }

  componentDidCatch(error, info) {
    // Chybu můžete také zalogovat do služby pro hlášení chyb
    console.error("Caught an error: ", error, info.componentStack);
    this.setState(prevState => ({ errorCount: prevState.errorCount + 1 }));
  }

  resetError = () => {
      this.setState({hasError: false, key: this.state.key + 1})
  }

  render() {
    if (this.state.hasError) {
      // Můžete vykreslit jakékoliv vlastní záložní UI
      return (
        

Jejda! Něco se pokazilo.

Omlouváme se, ale při pokusu o zobrazení tohoto obsahu došlo k chybě.

); } return
{this.props.children}
; } }

V tomto příkladu je do obalujícího divu přidán 'key'. Změna klíče vynutí znovupřipojení komponenty, což efektivně vymaže chybový stav. Metoda `resetError` aktualizuje stav `key` komponenty, což způsobí její znovupřipojení a opětovné vykreslení jejích potomků.

Použití Error Boundaries se Suspense

React Suspense vám umožňuje "pozastavit" vykreslování komponenty, dokud není splněna nějaká podmínka (např. jsou načtena data). Můžete kombinovat Error Boundaries se Suspense a poskytnout tak robustnější zážitek ze zpracování chyb pro asynchronní operace.


import React, { Suspense } from 'react';

function MyComponent() {
  return (
    
      Loading...
}> ); } function DataFetchingComponent() { const data = useData(); // Vlastní hook, který asynchronně načítá data return
{data.value}
; }

V tomto příkladu DataFetchingComponent načítá data asynchronně pomocí vlastního hooku. Komponenta Suspense zobrazuje indikátor načítání, zatímco se data stahují. Pokud během procesu načítání dat dojde k chybě, ErrorBoundary ji zachytí a zobrazí záložní UI.

Osvědčené postupy pro React Error Boundaries

Příklady z reálného světa

Zde je několik příkladů z reálného světa, jak lze Error Boundaries použít:

Alternativy k Error Boundaries

Ačkoli jsou Error Boundaries doporučeným způsobem, jak zpracovávat chyby v Reactu, existují i alternativní přístupy, které můžete zvážit. Mějte však na paměti, že tyto alternativy nemusí být tak účinné jako Error Boundaries v prevenci pádů aplikace a poskytování bezproblémového uživatelského zážitku.

V konečném důsledku poskytují Error Boundaries robustní a standardizovaný přístup ke zpracování chyb v Reactu, což z nich činí preferovanou volbu pro většinu případů použití.

Závěr

React Error Boundaries jsou nezbytným nástrojem pro vytváření robustních a uživatelsky přívětivých React aplikací. Tím, že zachytávají chyby a zobrazují záložní UI, zabraňují pádům aplikace, zlepšují uživatelský zážitek a zjednodušují ladění chyb. Dodržováním osvědčených postupů uvedených v tomto průvodci můžete efektivně implementovat Error Boundaries ve svých aplikacích a vytvořit odolnější a spolehlivější uživatelský zážitek pro uživatele po celém světě.