Инъекция зависимостей и контекст

В реакте необходимость dependency injection очевидна. Рассмотрим следующее дерево приложений:

// Title.jsx
export default function Title(props) {
  return <h1>{ props.title }</h1>;
}
// Header.jsx
import Title from './Title.jsx';
export default function Header() {
  return (
    <header>
      <Title />
    </header>
  );
}
// App.jsx
import Header from './Header.jsx';
class App extends React.Component {
  constructor(props) {
    super(props);
    this.state = { title: 'React Dependency Injection' };
  }
  render() {
    return <Header />;
  }
}

Строка «React Dependency Injection» должна каким-то образом достичь компонента Title. Прямой способ сделать это - передать его из App to Header, а затем Header, чтобы передать его Title. Однако это может работать для этих трех компонентов, но что произойдет, если будет добавлено много свойств и более глубокое вложение. У многих компонентов будут много свойств, которые им не нужны. Понятно, что большинство компонентов React получают свои зависимости через пропсы( свойства), но вопрос в том, как эти зависимости достигают этой точки.

Одним из способов достижения dependency injection является использование компонента высокого порядка( в народе HOC).

// inject.jsx
var title = 'React Dependency Injection';
export default function inject(Component) {
  return class Injector extends React.Component {
    render() {
      return (
        <Component
          {...this.state}
          {...this.props}
          title={ title }
        />
      )
    }
  };
}
// Title.jsx
export default function Title(props) {
  return <h1>{ props.title }</h1>;
}
// Header.jsx
import inject from './inject.jsx';
import Title from './Title.jsx';

var EnhancedTitle = inject(Title);
export default function Header() {
  return (
    <header>
      <EnhancedTitle />
    </header>
  );
}

title скрыт в среднем слое (в inject.jsx - компонент высокого порядка, HOC), где мы передаем его в качестве свойств для исходного компонента Title. Это все хорошо, но он решает только половину проблемы. Теперь нам не нужно передавать заголовок по дереву, но как эти данные достигнут помощника enh.jsx

Использование контекста React

React имеет концепцию контекста. Контекст - это то, что к чему имеет доступ каждый компонент. Это что-то вроде шины событий, но для данных. Единственная модель, к которой мы можем получить доступ везде

место, где мы определим контекст

var context = { title: 'React in patterns' };
class App extends React.Component {
  getChildContext() {
    return context;
  }
  // ...
}

App.childContextTypes = {
  title: PropTypes.string
};

место, где нам нужны данные

class Inject extends React.Component {
  render() {
    var title = this.context.title;
  // ...
  }
}
Inject.contextTypes = {
  title: PropTypes.string
};

Ссылки по теме:

Контекст в React и инъекция зависимостей

Мир недокументированного React.js. Context

results matching ""

    No results matching ""