React представляет новое API (context API), которое использует "паттерн" (шаблон) render props (подробнее). На семинарах, встречах и в твиттере я вижу, что возникает много вопросов об использовании render props вне рендера, например, в обработчиках событий или "хуках" жизненного цикла(`lifecycle hooks').

Полтора года назад, когда я работал над React Router v4, меня особенно заинтересовало, как раз и навсегда решить проблему "глубоких обновлений". Я создал библиотеку с названием react-context-emission (позднее — react-broadcast) с API концептуально идентичным тому, что представил React в своем новом context API.
// React context emission API
const { LocationEmitter, LocationSubscriber } = createContextEmission('location')
<LocationEmitter location={value}/>
<LocationSubscriber>{({ location }) => (...)}</LocationSubscriber>
// Новое React Context API
const { Provider, Consumer } = React.createContext()
<Provider value={location}/>
<Consumer>{value => (...)}</Consumer>После использования этого шаблона мне действительно понравилось связывать значения переменных с компонентами через контекст и отрисовывать свойства (рендерить props), однако я изо всех сил старался получить доступ к контекстным значениям за пределами рендеринга. В моей реализации я привык получать их из this.context повсеместно. Это было одной из причин, по которой мы вернулись к использованию текущего (устаревшего?) contextTypes API в React Router.
Решить эту проблему не так сложно. Чтобы понять это, мне потребовалось время. Однако, как только вы увидите решение, оно покажется вам очевидным. Убедитесь сами!
Доступ к значениям в обработчиках событий
Нужно лишь… передать значение в обработчик:
class Something extends React.Component {
  handleClick = (event, stuff) => {
    console.log(stuff);
  };
  render() {
    return (
      <SomeContext.Consumer>
        {stuff => (
          <div>
            <h1>Cool! {stuff}</h1>
            <button onClick={event => this.handleClick(event, stuff)}>
              Click me
            </button>
          </div>
        )}
      </SomeContext.Consumer>
    );
  }
}Доступ к значениям в lifecycle hooks
В случае с lifecycle hooks предыдущий шаблон не работает, т.к. не мы вызываем хуки, а React. Предлагаю три шаблона, которые я использовал, выбирайте, который больше понравится (третий — мой любимый!). 
Оборачиваем
Вы можете получить доступ к данным путем создания двух компонентов: контейнера, который использует контекст, и контейнера, который принимает контекст как свойство.
// Поглотите его (имеется, в виду компонент)
const SomethingContainer = () => (
  <SomeContext.Consumer>
    {stuff => <Something stuff={stuff} />}
  </SomeContext.Consumer>
);
// Вуаля, получите stuff в prop! Context в ваших методах жизненного цикла
class Something extends React.Component {
  componentDidMount() {
    console.log(this.props.stuff);
  }
  render() {
    return (
      <div>
        <h1>Cool! {this.props.stuff}</h1>
      </div>
    );
  }
}Создаем компоненты высшего порядка (HOC-компоненты)
Возможно, вы уже привыкли декорировать одни компоненты другими (например, с помощью HOC — High Order Component). Можно довольно быстро превратить render prop компонент в компонент высшего порядка. Я не особо люблю такой способ, поскольку для реализации он требует значительные перетасовки в коде и множество концепций. 
// HOC
const withStuff = Comp => props => (
  <SomeContext.Consumer>
    {stuff => <Comp stuff={stuff} />}
  </SomeContext.Consumer>
);
// Декорированный класс
class SomethingImpl extends React.Component {
  componentDidMount() {
    console.log(this.props.stuff);
  }
  render() {
    return (
      <div>
        <h1>Cool! {this.props.stuff}</h1>
      </div>
    );
  }
}
// the actual decoration
const Something = withStuff(SomethingImpl)Компонентный компонент: моя новая любовь.
Однажды я создал компонент, который просто брал функцию как свойство и вызывал функцию в componentDidUpdate. Я уже делал свойство с именем render и теперь у меня появилось еще одно под названием didUpdate. Я понял, что можно преобразовать каждый метод класса компонента в свойство компонента, и вот так появился @reactions/component!
Очень удобно компоновать render props в хуках жизненного цикла без всяких перетасовок в коде:
import Component from '@reactions/component';
const Something = () => (
  <SomeContext.Consumer>
    {stuff => (
      <Component didMount={() => console.log(stuff)}>
        <h1>Cool! {stuff}</h1>
      </Component>
    )}
  </SomeContext.Consumer>
);Обычно свойства можно сравнить в componentDidUpdate, это тоже неплохо работает:
const Something = () => (
  <SomeContext.Consumer>
    {stuff => (
      <Component
        stuff={stuff}
        didUpdate={({prevProps, props}) => {
          console.log(prevProps.stuff === props.stuff);
        }}
      >
        <h1>Cool! {stuff}</h1>
      </Component>
    )}
  </SomeContext.Consumer>
);Это мой любимый метод. Код может изменяться и перемещаться без каких-либо несоответствий, поскольку он не несет новых концепций, вся структура организуется компонентами. Если вы больше не нуждаетесь в методах жизненных циклов, вам не надо распутывать абстракцию, просто удалите <Component/>.
Итак, теперь у вас есть все необходимое. Все очевидно, стоит лишь раз увидеть, а ведь до этого все казалось сложным.
          
 
rzcoder
Был хороший context api который прекрасно решал свои задачи. Абрамов решил «улучшить» частный случай использования, сломав все остальные сценарии: использование вне рендера, простое использование нескольких контекстов одновременно. Теперь, чтобы всё «починить» нам предлагают использовать bind в рендере (что тысячу раз уже заклеймили антипаттерном) и оборачивать компоненты в компоненты, только ради того чтобы решить задачу которая раньше не требовала решения вообще.
faiwer
Ну и помимо прочего даже "нативное" применение consumer-а теперь сопровождается callback-ом. Элегантным такое решение назвать никак не получается. Кто-то очень любит матрёшки. Особенно они изящно выглядят, когда нужно несколько полей из context-а. Интересно, как скоро мы придём к
iojsфорку React-а? :)Особенно меня впечатляют вот такие вот публикации. Такие восторги, охи и ахи. "I’m excited about what this new API has to offer".
rzcoder
Думаю форк случится на моменте выпуска react 17, где они уберут componentWillMount и сделают shouldComponentUpdate статичным методом. Фактически разделят экосистему реакта на до и после 17 версии.