From 14f95f52f36fb8e194b21cc58ce8ec460c1ada1b Mon Sep 17 00:00:00 2001 From: Maxim Date: Sun, 10 Feb 2019 22:13:32 +0300 Subject: [PATCH 01/24] Update error-boundaries.md --- content/docs/error-boundaries.md | 46 ++++++++++++++++---------------- 1 file changed, 23 insertions(+), 23 deletions(-) diff --git a/content/docs/error-boundaries.md b/content/docs/error-boundaries.md index 147732911..910239459 100644 --- a/content/docs/error-boundaries.md +++ b/content/docs/error-boundaries.md @@ -4,25 +4,25 @@ title: Error Boundaries permalink: docs/error-boundaries.html --- -In the past, JavaScript errors inside components used to corrupt React’s internal state and cause it to [emit](https://github.com/facebook/react/issues/4026) [cryptic](https://github.com/facebook/react/issues/6895) [errors](https://github.com/facebook/react/issues/8579) on next renders. These errors were always caused by an earlier error in the application code, but React did not provide a way to handle them gracefully in components, and could not recover from them. +В прошлом, ошибки JavaScript внутри компонентов портили внутреннуу состояние React и заставляли его [выдавать](https://github.com/facebook/react/issues/4026) [таинственные](https://github.com/facebook/react/issues/6895) [сообщения об ошибках](https://github.com/facebook/react/issues/8579) во время следующего рендера. Эти сообщения всегда вызывались ошибками, расположенными где-то выше в коде приложения, но React не предоставлял способа адекватно обрабатывать их в компонентах и не мог обработать их самостоятельно. -## Introducing Error Boundaries {#introducing-error-boundaries} +## Представляем Error Boundaries {#introducing-error-boundaries} -A JavaScript error in a part of the UI shouldn’t break the whole app. To solve this problem for React users, React 16 introduces a new concept of an “error boundary”. +Ошибка JavaScript где-то в коде UI не должна рушить всё приложение. Чтобы реализовать это утверждение для пользователей React, React 16 водит концепцию "рубеж ошибок"("error boundary"). -Error boundaries are React components that **catch JavaScript errors anywhere in their child component tree, log those errors, and display a fallback UI** instead of the component tree that crashed. Error boundaries catch errors during rendering, in lifecycle methods, and in constructors of the whole tree below them. +Error boundaries это компоненты React, которые **отлавливают ошибки JavaScript в любом месте дерева их дочерних компонентов, сохраняют их в журнал и выводят запасной UI** вместо рухнувшего дерева компонентов. Error boundaries ловят ошибки при рендеринге, в методах жизненного цикла и в конструкторах дерева компонентов, расположенного под ними. -> Note +> Замечание > -> Error boundaries do **not** catch errors for: +> Error boundaries **не** поймают ошибки в: > -> * Event handlers ([learn more](#how-about-event-handlers)) -> * Asynchronous code (e.g. `setTimeout` or `requestAnimationFrame` callbacks) -> * Server side rendering -> * Errors thrown in the error boundary itself (rather than its children) +> * Обработчиках событий ([подробнее](#how-about-event-handlers)) +> * Асинхронном коде (напр. колбэки из `setTimeout` или `requestAnimationFrame`) +> * Серверсайд рендеринге +> * Самом компоненте error boundary (а не в его дочерних компонентах) -A class component becomes an error boundary if it defines either (or both) of the lifecycle methods [`static getDerivedStateFromError()`](/docs/react-component.html#static-getderivedstatefromerror) or [`componentDidCatch()`](/docs/react-component.html#componentdidcatch). Use `static getDerivedStateFromError()` to render a fallback UI after an error has been thrown. Use `componentDidCatch()` to log error information. +Классовый компонент является error boundary если он включает любой из двух (или оба) методов жизненного цикла [`static getDerivedStateFromError()`](/docs/react-component.html#static-getderivedstatefromerror) или [`componentDidCatch()`](/docs/react-component.html#componentdidcatch). Пользуйтесь `static getDerivedStateFromError()` при рендеринге запасного UI в случае отлова ошибки. Используйте `componentDidCatch()` при написании кода для журналирования информации об отловленной ощибке. ```js{7-10,12-15,18-21} class ErrorBoundary extends React.Component { @@ -32,18 +32,18 @@ class ErrorBoundary extends React.Component { } static getDerivedStateFromError(error) { - // Update state so the next render will show the fallback UI. + // Обновить состояние с тем, чтобы следующий рендер показал запасной UI. return { hasError: true }; } componentDidCatch(error, info) { - // You can also log the error to an error reporting service + // Можно так же сохранить информацию об ошибке в соответствующую службу журнала ошибок logErrorToMyService(error, info); } render() { if (this.state.hasError) { - // You can render any custom fallback UI + // В качестве запасного можно отрендерить UI произвольного вида return

Something went wrong.

; } @@ -52,7 +52,7 @@ class ErrorBoundary extends React.Component { } ``` -Then you can use it as a regular component: +И можно дальше им пользоваться, как обыконовенным компонентом: ```js @@ -60,23 +60,23 @@ Then you can use it as a regular component: ``` -Error boundaries work like a JavaScript `catch {}` block, but for components. Only class components can be error boundaries. In practice, most of the time you’ll want to declare an error boundary component once and use it throughout your application. +Error boundaries работают как `catch {}` блоки JavaScript, только для компонентов. Только классовые компоненты могут выступать в роли error boundaries. На практике, чаще всего целесообразным будет один раз описать компонент error boundary и использовать его по всему приложению. -Note that **error boundaries only catch errors in the components below them in the tree**. An error boundary can’t catch an error within itself. If an error boundary fails trying to render the error message, the error will propagate to the closest error boundary above it. This, too, is similar to how catch {} block works in JavaScript. +Стоит обратить внимание, что **error boundaries отлавливают ошибки исключительно в своих дочерних компонентах**. Error boundary не сможет отловить ошибку внутри самого себя. Если error boundary не удается отрендерить сообщение об ощибке, то ошибка всплывает до ближайшего error boundary, расположенного над ним в дереве компонентов. В этом тоже ситуация напоминает то, как работают блоки `catch {}` в JavaScript. -## Live Demo {#live-demo} +## Работающая демонстрация {#live-demo} -Check out [this example of declaring and using an error boundary](https://codepen.io/gaearon/pen/wqvxGa?editors=0010) with [React 16](/blog/2017/09/26/react-v16.0.html). +См. [пример объявления и использования error boundary](https://codepen.io/gaearon/pen/wqvxGa?editors=0010) в [React 16](/blog/2017/09/26/react-v16.0.html). -## Where to Place Error Boundaries {#where-to-place-error-boundaries} +## Где располагать Error Boundaries {#where-to-place-error-boundaries} -The granularity of error boundaries is up to you. You may wrap top-level route components to display a “Something went wrong” message to the user, just like server-side frameworks often handle crashes. You may also wrap individual widgets in an error boundary to protect them from crashing the rest of the application. +Гранулярность error boundaries оставляется на ваше усмотрение. Например вы можете охватить им навигационные (route) компоненты верхнего уровня, чтобы выводить пользователю сообщение "Что-то пошло не так", как часто делают при обработке ошибок серверные фреймворки. Также вы можете охватить error boundary отдельные виджеты, чтобы помешать им обрушить всё приложение. -## New Behavior for Uncaught Errors {#new-behavior-for-uncaught-errors} +## Новое поведение при обработке неотловленных ошибок {#new-behavior-for-uncaught-errors} -This change has an important implication. **As of React 16, errors that were not caught by any error boundary will result in unmounting of the whole React component tree.** +Это изменение влечёт за собой существенное последствие. **Начиная с React 16, ошибки, не отловленные ни одним из error boundary будут приводить к размонтированию всего дерева компонентов React.** We debated this decision, but in our experience it is worse to leave corrupted UI in place than to completely remove it. For example, in a product like Messenger leaving the broken UI visible could lead to somebody sending a message to the wrong person. Similarly, it is worse for a payments app to display a wrong amount than to render nothing. From b8b1c28c3710ea42188baadb84bf17e4147eca73 Mon Sep 17 00:00:00 2001 From: Maxim Date: Sun, 10 Feb 2019 23:21:31 +0300 Subject: [PATCH 02/24] Update error-boundaries.md --- content/docs/error-boundaries.md | 54 ++++++++++++++++---------------- 1 file changed, 27 insertions(+), 27 deletions(-) diff --git a/content/docs/error-boundaries.md b/content/docs/error-boundaries.md index 910239459..984a855c4 100644 --- a/content/docs/error-boundaries.md +++ b/content/docs/error-boundaries.md @@ -78,35 +78,35 @@ Error boundaries работают как `catch {}` блоки JavaScript, то Это изменение влечёт за собой существенное последствие. **Начиная с React 16, ошибки, не отловленные ни одним из error boundary будут приводить к размонтированию всего дерева компонентов React.** -We debated this decision, but in our experience it is worse to leave corrupted UI in place than to completely remove it. For example, in a product like Messenger leaving the broken UI visible could lead to somebody sending a message to the wrong person. Similarly, it is worse for a payments app to display a wrong amount than to render nothing. +Хотя принятие этого решения и вызвало споры, согласно нашему опыту бОльшим злом будет вывести испорченный UI, чем удалить его целиком. К примеру в приложении типа Messenger, вывод поломанного UI может привести к тому, что пользователь отправит сообщение не тому адресату. Аналогично, будет хуже, если приложение для проведения платежей выведет пользователю неправильную сумму платежа, чем если оно не выведет вообще ничего. -This change means that as you migrate to React 16, you will likely uncover existing crashes in your application that have been unnoticed before. Adding error boundaries lets you provide better user experience when something goes wrong. +Это изменение означает, что при мигрировании на React 16, вы с большой вероятностью натолкнётесь на незамеченные ранее ошибки в вашем приложении. Добавляя в ваше приложение error boundaries, вы получаете возможность обеспечивать более качественный пользовательский опыт (user experience) при возниновении ошибок. -For example, Facebook Messenger wraps content of the sidebar, the info panel, the conversation log, and the message input into separate error boundaries. If some component in one of these UI areas crashes, the rest of them remain interactive. +Например, Facebook Messenger охватывает содержимое боковой и информационной панелей, журнала общения и поля ввода сообщений отдельными error boundary. Если один из этих компонентов UI упадёт, то остальные сохранят интерактивность. -We also encourage you to use JS error reporting services (or build your own) so that you can learn about unhandled exceptions as they happen in production, and fix them. +Так же, мы очень рекомендуем пользоваться сервисами обработки ошибок JS (или написать ваш собственный аналогичный сервис) с тем, чтобы вы оказывались в курсе и могли устранять неотловленные исключения по мере их появления, ещё в продакшен—режиме. -## Component Stack Traces {#component-stack-traces} +## Stack Trace компонентов {#component-stack-traces} -React 16 prints all errors that occurred during rendering to the console in development, even if the application accidentally swallows them. In addition to the error message and the JavaScript stack, it also provides component stack traces. Now you can see where exactly in the component tree the failure has happened: +В режиме разработки React 16 выводит на консоль сообщения обо всех ошибках, возникших при рендеринге, даже если приложения случайно их проглотило. Помимо сообщения об ошибке и стэка JavaScript, React 16 также выводит и stack trace компонентов. Теперь вы в точности можете видеть в каком именно месте дерева компонентов случилось страшное: -Error caught by Error Boundary component +Ошибка, отловленная компонентом Error Boundary -You can also see the filenames and line numbers in the component stack trace. This works by default in [Create React App](https://github.com/facebookincubator/create-react-app) projects: +Кроме этого, в stack trace компонентов выводятся имена файлов и номера строк. Такое поведение по умолчанию настроено в проектах, созданных при помощи [Create React App](https://github.com/facebookincubator/create-react-app): -Error caught by Error Boundary component with line numbers +Ошибка, отловленная компонентом Error Boundary, включая номера строк -If you don’t use Create React App, you can add [this plugin](https://www.npmjs.com/package/babel-plugin-transform-react-jsx-source) manually to your Babel configuration. Note that it’s intended only for development and **must be disabled in production**. +Если вы не пользуетесь Create React App, вы можете вручную добавить к вашей конфигцурации Babel [вот этот плагин](https://www.npmjs.com/package/babel-plugin-transform-react-jsx-source). Обратите внмание, что он предназначен исключительно для режима разработки и **должен быть деактивирован в продакшен**. -> Note +> Замечание > -> Component names displayed in the stack traces depend on the [`Function.name`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/name) property. If you support older browsers and devices which may not yet provide this natively (e.g. IE 11), consider including a `Function.name` polyfill in your bundled application, such as [`function.name-polyfill`](https://github.com/JamesMGreene/Function.name). Alternatively, you may explicitly set the [`displayName`](/docs/react-component.html#displayname) property on all your components. +> Имена компонентов, выводимые в их stack trace определяются свойством [`Function.name`](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Function/name). Если ваше приложение поддерживает более старые браузеры и устройства, которые могут ещё не предоставлять его нативно (напр. IE 11), рассмотрите возможность включения полифилла `Function.name` в бандл вашего приложения, например [`function.name-polyfill`](https://github.com/JamesMGreene/Function.name). Альтернативно, вы можете явным образом задать значение пропа [`displayName`](/docs/react-component.html#displayname) в каждом из ваших компонентов. -## How About try/catch? {#how-about-trycatch} +## А как насчёт try/catch? {#how-about-trycatch} -`try` / `catch` is great but it only works for imperative code: +`try` / `catch` - отличная конструкция, но она работает исключительно в императивном коде: ```js try { @@ -116,21 +116,21 @@ try { } ``` -However, React components are declarative and specify *what* should be rendered: +В то время, как компоненты React являются декларативными, указывая *что* должно быть отрендерено: ```js