{"componentChunkName":"component---src-templates-blog-js","path":"/blog/2016/07/13/mixins-considered-harmful.html","result":{"data":{"markdownRemark":{"html":"<p>“Como eu compartilho o código entre diversos componentes?” é uma das primeiras perguntas que as pessoas fazem quando aprendem React. Nossa resposta sempre foi usar composição de componentes para reutilização do código. Você pode definir um componente e usá-lo em diversos outros componentes.</p>\n<p>Nem sempre é óbvio como um determinado padrão pode ser resolvido com a componetização. O React é influenciado pela programacão funcional, mas entrou em um campo que é dominado por bibliotecas orientadas à objetos. Foi difícil para os engenheiros, dentro e fora do Facebook, de abrir mão dos padrões que estavam acostumados.</p>\n<p>Para facilitar a adoção e o aprendizado inicial, incluimos algumas válvulas de escape no React. O sistema mixin era uma dessas válvulas de escape, e seu objetivo era dar a você uma maneira de reutilizar o código entre os componentes, quando você não tem certeza de como resolver o mesmo problema com a composição.</p>\n<p>Três anos se passaram desde que o React foi lançado. O cenário mudou. Agora, várias bibliotecas de visualizações adotam um modelo de componente semelhante ao React. Usar composição sobre a herança para criar interfaces de usuário declarativas não é mais uma novidade. Também estamos mais confiantes no modelo do componente React, e vimos muitos usos criativos dele tanto internamente quanto na comunidade.</p>\n<p>Neste post, vamos considerar os problemas comumentes causados por mixins. Em seguida, sugeriremos vários padrões alternativos para os mesmos casos de uso. Descobrimos que esses padrões escalam melhor com a complexidade da base de código do que os mixins.</p>\n<h2 id=\"why-mixins-are-broken\"><a href=\"#why-mixins-are-broken\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Por que Mixins estão quebrados? </h2>\n<p>No Facebook, o uso do React cresceu de alguns componentes para milhares deles. Isso nos dá uma janela sobre como as pessoas usam o React. Graças à renderização declarativa e ao fluxo de dados de cima para baixo, muitas equipes conseguiram corrigir vários bugs ao enviar novos recursos à medida que o React era adotado.</p>\n<p>No entando, é inevitável que parte do nosso código usando React se torne gradualmente incompreensível. Ocasionalmente, a equipe do React veria grupos de componentes em diferentes projetos que as pessoas tinham medo de tocar. Esses componentes eram muito fáceis de serem quebrados acidentalmente, eram confusos para novos desenvolvedores e acabaram se tornando tão confusos para as pessoas que os escreveram em primeiro lugar. Muito dessa confusão ocorreu por causa dos mixins. Na época, eu não estava trabalhando no Facebook, mas cheguei <a href=\"https://medium.com/@dan_abramov/mixins-are-dead-long-live-higher-order-components-94a0d2f9e750\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">as mesmas conclusões</a> depois de escrever vários de terríveis mixins.</p>\n<p>Isso não significa que os próprios mixins são ruins. As pessoas empregam com sucesso em diferentes linguagens e paradigmas, incluindo algumas linguagens funcionais. No Facebook, usamos extensivamente traços no Hack que são bastante semelhantes aos mixins. No entanto, pensamos que os mixins são desnecessários e problemáticos nas bases de código do React. E aqui está o porquê.</p>\n<h3 id=\"mixins-introduce-implicit-dependencies\"><a href=\"#mixins-introduce-implicit-dependencies\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Mixins introduzem dependências implícitas </h3>\n<p>Às vezes, um componente depende de um determinado método definido no mixin, como <code class=\"gatsby-code-text\">getClassName()</code>. Às vezes é o contrário, e mixins chama um método como <code class=\"gatsby-code-text\">renderHeader()</code> no componente. JavaScript é uma linguagem dinâmica, por isso é difícil impor ou documentar tais dependências.</p>\n<p>Os mixins quebram a suposição comum e geralmente segura de que você pode renomear uma chave de estado ou um método pesquisando suas ocorrências no arquivo do componente. Você pode escrever um componente com estado e, em seguida, seu colega de trabalho pode adicionar um mixin que leia esse estado. Em alguns meses, você pode querer mover esse estado para o componente pai para que ele possa ser compartilhado com um irmão. Você vai se lembrar de atualizar o mixin para ler a prop em vez disso? E se, até agora, outros componentes também usarem este mixin?</p>\n<p>Essas dependências implícitas dificultam que novos membros da equipe contribuam para uma base de código. O método <code class=\"gatsby-code-text\">render()</code> de um componente pode fazer referência a algum método que não está definido na classe. É seguro remover? Talvez esteja definido em um dos mixins. Mas qual deles? Você precisa rolar até a lista de mixins, abrir cada um desses arquivos e procurar por este método. Pior ainda, mixins podem especificar seus próprios mixins, então a pesquisa pode se aprofundar.</p>\n<p>Muitas vezes, os mixins passam a depender de outros mixins, e a remoção de um deles quebra o outro. Nessas situações, é muito complicado dizer como os dados entram e saem dos mixins e como é o seu gráfico de dependências. Ao contrário dos componentes, os mixins não formam uma hierarquia: eles são achatados e operam no mesmo namespace.</p>\n<h3 id=\"mixins-cause-name-clashes\"><a href=\"#mixins-cause-name-clashes\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Mixins causam confronto de nomes </h3>\n<p>Não há garantia de que duas misturas específicas possam ser usadas juntas. Por exemplo, se <code class=\"gatsby-code-text\">FluxListenerMixin</code> define <code class=\"gatsby-code-text\">handleChange()</code> e <code class=\"gatsby-code-text\">WindowSizeMixin</code> define <code class=\"gatsby-code-text\">handleChange()</code>, você não pode usá-los juntos. Você também não pode definir um método com esse nome em seu próprio componente.</p>\n<p>Não é um grande problema se você controlar o código do <em>mixin</em>. Quando você tem um conflito, você pode renomear esse método em um dos <em>mixins</em>. No entanto, é complicado porque alguns componentes ou outros <em>mixins</em> já podem estar chamando esse métodos diretamente, e você precisa encontrar e corrigir essas chamadas também.</p>\n<p>Se você tiver um conflito de nome com um <em>mixin</em> de um pacote de terceiros, não será possível renomear um método dele. Em vez disso, você precisa usar nomes desconhecidos de métodos em seu componente para evitar conflitos.</p>\n<p>A situação não é melhor para os autores dos <em>mixins</em>. Até mesmo a adição de um novo método a um <em>mixin</em> é sempre uma alteração potencial, pois um método com o mesmo nome já pode existir em alguns dos componentes que o usam, diretamente ou por meio de outro <em>mixin</em>. Uma vez escritos, os <em>mixins</em> são difíceis de remover ou mudar. Idéias ruins não são refatoradas porque a refatoração é muito arriscada.</p>\n<h3 id=\"mixins-cause-snowballing-complexity\"><a href=\"#mixins-cause-snowballing-complexity\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Mixins desencadeiam complexidade de bola de neve </h3>\n<p>Mesmo quando os <em>mixins</em> começam de forma simples, eles tendem a se tornar complexos ao longo do tempo. O exemplo abaixo é baseado em um cenário real que vi em um repositório.</p>\n<p>Um componente precisa de algum estado para rastrear o foco do mouse. Para manter essa lógica reutilizável, você pode extrair <code class=\"gatsby-code-text\">handleMouserEnter()</code>, <code class=\"gatsby-code-text\">handleMouseLeave()</code> e <code class=\"gatsby-code-text\">isHovering()</code> em um <code class=\"gatsby-code-text\">HoverMixin</code>. Em seguida, alguém precisa implementar uma dica de ferramenta. Eles não querem duplicar a lógica em <code class=\"gatsby-code-text\">HoverMixin</code>, de modo que criam um <code class=\"gatsby-code-text\">TooltipMixin</code> que usa o <code class=\"gatsby-code-text\">HoverMixin</code>. <code class=\"gatsby-code-text\">TooltipMix</code> lê <code class=\"gatsby-code-text\">isHovering()</code> fornecido pelo <code class=\"gatsby-code-text\">HoverMixin</code> no seu <code class=\"gatsby-code-text\">componentDidUpdate()</code> e mostra ou oculta a dica da ferramenta.</p>\n<p>Alguns meses depois, alguém quer tornar a direção da dica de ferramenta configurável. Em um esforço para evitar a duplicação de código, eles adicionam suporte a um novo método opcional chamado <code class=\"gatsby-code-text\">getTooltipOptions ()</code> em <code class=\"gatsby-code-text\">TooltipMixin</code>. A essa altura, os componentes que mostram popovers também usam o <code class=\"gatsby-code-text\">HoverMixin</code>. No entanto, os popovers precisam de um atraso diferente. Para resolver isso, alguém adiciona suporte para um método opcional <code class=\"gatsby-code-text\">getHoverOptions ()</code> e o implementa no <code class=\"gatsby-code-text\">TooltipMixin</code>. Esses mixins estão agora fortemente acoplados.</p>\n<p>Isso é bom enquanto não há novos requisitos. No entanto esta solução não escala muito bem. E se você deseja oferecer suporte à exibição de várias dicas de ferramentas em um único componente? Você não pode definir o mesmo mixin duas vezes em um componente. E se as dicas de ferramentas precisarem ser exibidas automaticamente em um tour guiado ao invés do hover? Boa sorte ao separar o <code class=\"gatsby-code-text\">TooltipMixin</code> do <code class=\"gatsby-code-text\">HoverMixin</code>. E se você precisar dar suporte ao caso onde a área do hover e a âncora da dica de ferramenta estejam localizadas em componentes diferentes? Você não pode elevar facilmente o estado usado misturando-se ao componente pai. Ao contrário dos componentes, mixins não se prestam naturalmente a essas mudanças.</p>\n<p>Cada novo requisito torna os mixins mais difíceis de entender. Os componentes que usam o mesmo mixin ficam cada vez mais acoplados ao tempo. Qualquer novo recurso é adicionado a todos os componentes usando esse mixin. Não há como dividir uma parte “mais simples” do mixin sem duplicar o código ou introduzir mais dependências e indiretas entre mixins. Gradualmente, os limites do encapsulamento diminuem e, como é difícil alterar ou remover os mixins existentes, eles ficam cada vez mais abstratos até que ninguém entenda como eles funcionam.</p>\n<p>Esses são os mesmos problemas que enfrentamos ao criar aplicativos antes do React. Descobrimos que eles são resolvidos por renderização declarativa, fluxo de dados de cima para baixo e componentes encapsulados. No Facebook, estamos migrando nosso código para usar padrões alternativos para mixins, e geralmente estamos felizes com os resultados. Você pode ler sobre esses padrões logo abaixo.</p>\n<h2 id=\"migrating-from-mixins\"><a href=\"#migrating-from-mixins\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Migrando de Mixins </h2>\n<p>Vamos deixar claro que mixins não são tecnicamente obsoletos. Se você usar <code class=\"gatsby-code-text\">React.createClass()</code>, poderá continuar usando-os. Dizemos apenas que eles não funcionaram bem para nós e, portanto, não recomendamos usá-los no futuro.</p>\n<p>Cada seção abaixo corresponde a um padrão de uso de mixin que encontramos na base de código do Facebook. Para cada um deles, descrevemos o problema e uma solução que achamos que funciona melhor que os mixins. Os exemplos estão escritos no ES5, mas quando você não precisar de mixins, poderá mudar para as aulas do ES6, se desejar.</p>\n<p>Esperamos que você ache esta lista útil. Informe-nos se não citamos algum caso de uso importante, para que possamos alterar a lista ou provar que estamos errados!</p>\n<h3 id=\"performance-optimizations\"><a href=\"#performance-optimizations\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Otimizações de desempenho </h3>\n<p>Um dos mixins mais usados é o <a href=\"/docs/pure-render-mixin.html\"><code class=\"gatsby-code-text\">PureRenderMixin</code></a>. Você pode usá-lo em alguns componentes para <a href=\"/docs/advanced-performance.html#shouldcomponentupdate-in-action\">impedir repetições desnecessárias</a> quando os props e o estado são superficialmente iguais aos props e estado anteriores:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> PureRenderMixin <span class=\"token operator\">=</span> <span class=\"token function\">require</span><span class=\"token punctuation\">(</span><span class=\"token string\">'react-addons-pure-render-mixin'</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Button <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  mixins<span class=\"token operator\">:</span> <span class=\"token punctuation\">[</span>PureRenderMixin<span class=\"token punctuation\">]</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token comment\">// ...</span>\n\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<h4 id=\"solution\"><a href=\"#solution\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solução </h4>\n<p>Para expressar o mesmo sem mixins, você pode usar a função <a href=\"/docs/shallow-compare.html\"><code class=\"gatsby-code-text\">shallowCompare</code></a>:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> shallowCompare <span class=\"token operator\">=</span> <span class=\"token function\">require</span><span class=\"token punctuation\">(</span><span class=\"token string\">'react-addons-shallow-compare'</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Button <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">shouldComponentUpdate</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">nextProps<span class=\"token punctuation\">,</span> nextState</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token function\">shallowCompare</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">,</span> nextProps<span class=\"token punctuation\">,</span> nextState<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token comment\">// ...</span>\n\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<p>Se você usar um mix personalizado implementando uma função <code class=\"gatsby-code-text\">shouldComponentUpdate</code> com algoritmo diferente, sugerimos exportar apenas essa função única de um módulo e chamá-la diretamente de seus componentes.</p>\n<p>Entendemos que mais digitação pode ser chato. Para o caso mais comum, planejamos <a href=\"https://github.com/facebook/react/pull/7195\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">introduzir uma nova classe base</a> chamada <code class=\"gatsby-code-text\">React.PureComponent</code> na próxima versão menor. Ele usa a mesma comparação superficial que o <code class=\"gatsby-code-text\">PureRenderMixin</code> faz hoje.</p>\n<h3 id=\"subscriptions-and-side-effects\"><a href=\"#subscriptions-and-side-effects\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Assinaturas e efeitos colaterais </h3>\n<p>O segundo tipo mais comum de mixins que encontramos são os mixins que assinam um componente React em uma fonte de dados de terceiros. Se essa fonte de dados é um Flux Store, um Rx Observable ou qualquer outra coisa, o padrão é muito semelhante: a assinatura é criada em <code class=\"gatsby-code-text\">componentDidMount</code>, destruída em <code class=\"gatsby-code-text\">componentWillUnmount</code> e o manipulador de alterações chama <code class=\"gatsby-code-text\">this.setState()</code>.</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> SubscriptionMixin <span class=\"token operator\">=</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">getInitialState</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">{</span>\n      comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">componentDidMount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">addChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">componentWillUnmount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">removeChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">handleChange</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">setState</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n      comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> CommentList <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  mixins<span class=\"token operator\">:</span> <span class=\"token punctuation\">[</span>SubscriptionMixin<span class=\"token punctuation\">]</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token comment\">// Lendo comentários do estado gerenciado por mixin.</span>\n    <span class=\"token keyword\">var</span> comments <span class=\"token operator\">=</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>state<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span>comments<span class=\"token punctuation\">.</span><span class=\"token function\">map</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">comment</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n          <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">Comment</span></span> <span class=\"token attr-name\">comment</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">}</span></span> <span class=\"token attr-name\">key</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">.</span>id<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span>\n        <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> CommentList<span class=\"token punctuation\">;</span></code></pre></div>\n<h4 id=\"solution-1\"><a href=\"#solution-1\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solução </h4>\n<p>Se houver apenas um componente inscrito nessa fonte de dados, não há problema em incorporar a lógica de assinatura diretamente no componente. Evite abstrações prematuras.</p>\n<p>Se vários componentes usaram esse mixin para assinar uma fonte de dados, uma boa maneira de evitar a repetição é usar um padrão chamado <a href=\"https://medium.com/@dan_abramov/mixins-are-dead-long-live-higher-order-components-94a0d2f9e750\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">“componentes de ordem superior”</a>. Pode parecer intimidador, portanto, examinaremos mais de perto como esse padrão emerge naturalmente do modelo de componentes.</p>\n<h4 id=\"higher-order-components-explained\"><a href=\"#higher-order-components-explained\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Explicação dos componentes de ordem superior </h4>\n<p>Vamos esquecer o React por um segundo. Considere estas duas funções que adicionam e multiplicam números, registrando os resultados conforme são executadas:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">addAndLog</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">var</span> result <span class=\"token operator\">=</span> x <span class=\"token operator\">+</span> y<span class=\"token punctuation\">;</span>\n  console<span class=\"token punctuation\">.</span><span class=\"token function\">log</span><span class=\"token punctuation\">(</span><span class=\"token string\">'result:'</span><span class=\"token punctuation\">,</span> result<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token keyword\">return</span> result<span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token keyword\">function</span> <span class=\"token function\">multiplyAndLog</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">var</span> result <span class=\"token operator\">=</span> x <span class=\"token operator\">*</span> y<span class=\"token punctuation\">;</span>\n  console<span class=\"token punctuation\">.</span><span class=\"token function\">log</span><span class=\"token punctuation\">(</span><span class=\"token string\">'result:'</span><span class=\"token punctuation\">,</span> result<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token keyword\">return</span> result<span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span></code></pre></div>\n<p>Essas duas funções não são muito úteis, mas nos ajudam a demonstrar um padrão que podemos aplicar posteriormente aos componentes.</p>\n<p>Digamos que queremos extrair a lógica de log dessas funções sem alterar suas assinaturas. Como podemos fazer isso? Uma solução elegante é escrever uma <a href=\"https://en.wikipedia.org/wiki/Higher-order_function\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">função de ordem superior</a>, ou seja, uma função que assume uma função como argumento e retorna uma função.</p>\n<p>Novamente, parece mais intimidador do que realmente é:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">withLogging</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">wrappedFunction</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token comment\">// Retorna uma função com a mesma API...</span>\n  <span class=\"token keyword\">return</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token comment\">// ... que chama a função original</span>\n    <span class=\"token keyword\">var</span> result <span class=\"token operator\">=</span> <span class=\"token function\">wrappedFunction</span><span class=\"token punctuation\">(</span>x<span class=\"token punctuation\">,</span> y<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token comment\">// ... mas também registra o resultado</span>\n    console<span class=\"token punctuation\">.</span><span class=\"token function\">log</span><span class=\"token punctuation\">(</span><span class=\"token string\">'result:'</span><span class=\"token punctuation\">,</span> result<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> result<span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span></code></pre></div>\n<p>A função de ordem superior <code class=\"gatsby-code-text\">withLogging</code> nos permite escrever <code class=\"gatsby-code-text\">add</code> e <code class=\"gatsby-code-text\">multiply</code> sem as instruções de log e depois envolvê-las para obter <code class=\"gatsby-code-text\">addAndLog</code> e <code class=\"gatsby-code-text\">multiplyAndLog</code> com exatamente as mesmas assinaturas de antes:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">add</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> x <span class=\"token operator\">+</span> y<span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token keyword\">function</span> <span class=\"token function\">multiply</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> x <span class=\"token operator\">*</span> y<span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token keyword\">function</span> <span class=\"token function\">withLogging</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">wrappedFunction</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">x<span class=\"token punctuation\">,</span> y</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">var</span> result <span class=\"token operator\">=</span> <span class=\"token function\">wrappedFunction</span><span class=\"token punctuation\">(</span>x<span class=\"token punctuation\">,</span> y<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    console<span class=\"token punctuation\">.</span><span class=\"token function\">log</span><span class=\"token punctuation\">(</span><span class=\"token string\">'result:'</span><span class=\"token punctuation\">,</span> result<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> result<span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token comment\">// Equivalente a escrever addLAndLog manualmente:</span>\n<span class=\"token keyword\">var</span> addAndLog <span class=\"token operator\">=</span> <span class=\"token function\">withLogging</span><span class=\"token punctuation\">(</span>add<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token comment\">// Equivalente a escrever multiplyAndLog manualmente:</span>\n<span class=\"token keyword\">var</span> multiplyAndLog <span class=\"token operator\">=</span> <span class=\"token function\">withLogging</span><span class=\"token punctuation\">(</span>multiply<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<p>Higher-order components are a very similar pattern, but applied to components in React. We will apply this transformation from mixins in two steps.</p>\n<p>As a first step, we will split our <code class=\"gatsby-code-text\">CommentList</code> component in two, a child and a parent. The child will be only concerned with rendering the comments. The parent will set up the subscription and pass the up-to-date data to the child via props.</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token comment\">// Este é um componente filho.</span>\n<span class=\"token comment\">// Apenas gera os comentários que recebe como props.</span>\n<span class=\"token keyword\">var</span> CommentList <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token comment\">// Nota: agora lendo das props em vez de estado.</span>\n    <span class=\"token keyword\">var</span> comments <span class=\"token operator\">=</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span>comments<span class=\"token punctuation\">.</span><span class=\"token function\">map</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">comment</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n          <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">Comment</span></span> <span class=\"token attr-name\">comment</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">}</span></span> <span class=\"token attr-name\">key</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">.</span>id<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span>\n        <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token comment\">// Este é um componente pai.</span>\n<span class=\"token comment\">// Ele assina a fonte de dados e renderiza &lt;CommentList />.</span>\n<span class=\"token keyword\">var</span> CommentListWithSubscription <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">getInitialState</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">{</span>\n      comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">componentDidMount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">addChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">componentWillUnmount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">removeChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">handleChange</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">setState</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n      comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token comment\">// Passamos o estado atual como props para CommentList.</span>\n    <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">CommentList</span></span> <span class=\"token attr-name\">comments</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>state<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> CommentListWithSubscription<span class=\"token punctuation\">;</span></code></pre></div>\n<p>Há apenas um passo final a ser feito.</p>\n<p>Lembra como fizemos com <code class=\"gatsby-code-text\">withLogging()</code> pegar uma função e retornar outra função envolvendo-a? Podemos aplicar um padrão semelhante aos componentes React.</p>\n<p>Escreveremos uma nova função chamada <code class=\"gatsby-code-text\">withSubscription(WrappedComponent)</code>. Seu argumento pode ser qualquer componente React. Passaremos <code class=\"gatsby-code-text\">CommentList</code> como <code class=\"gatsby-code-text\">WrappedComponent</code>, mas também poderíamos aplicar <code class=\"gatsby-code-text\">withSubscription()</code> a qualquer outro componente em nossa base de código.</p>\n<p>Esta função retornaria outro componente. O componente retornado gerenciaria a assinatura e renderizaria <code class=\"gatsby-code-text\">&lt;WrappedComponent /&gt;</code> com os dados atuais.</p>\n<p>Chamamos esse padrão de “componente de ordem superior”.</p>\n<p>A composição acontece no nível de renderização React, e não com uma chamada direta da função. É por isso que não importa se o componente agrupado está definido com <code class=\"gatsby-code-text\">createClass()</code>, como uma classe ou função ES6. Se <code class=\"gatsby-code-text\">WrappedComponent</code> for um componente React, o componente criado por <code class=\"gatsby-code-text\">withSubscription()</code> poderá renderizá-lo.</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token comment\">// Esta função pega um componente ...</span>\n<span class=\"token keyword\">function</span> <span class=\"token function\">withSubscription</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">WrappedComponent</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token comment\">// ...e retorna um outro componente...</span>\n  <span class=\"token keyword\">return</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n    <span class=\"token function-variable function\">getInitialState</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token keyword\">return</span> <span class=\"token punctuation\">{</span>\n        comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n      <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">componentDidMount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token comment\">// ...que cuida da assinatura...</span>\n      DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">addChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">componentWillUnmount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">removeChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">handleChange</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">setState</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n        comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n      <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token comment\">// ... e renderiza o componente agrupado com os novos dados! </span>\n      <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">WrappedComponent</span></span> <span class=\"token attr-name\">comments</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>state<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span></code></pre></div>\n<p>Agora podemos declarar <code class=\"gatsby-code-text\">CommentListWithSubscription</code> aplicando <code class=\"gatsby-code-text\">withSubscription</code> ao <code class=\"gatsby-code-text\">CommentList</code>:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> CommentList <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">var</span> comments <span class=\"token operator\">=</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span>comments<span class=\"token punctuation\">.</span><span class=\"token function\">map</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">comment</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n          <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">Comment</span></span> <span class=\"token attr-name\">comment</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">}</span></span> <span class=\"token attr-name\">key</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">.</span>id<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span>\n        <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token comment\">// withSubscription() retorna um novo componente que</span>\n<span class=\"token comment\">// é inscrito na fonte de dados e renderiza</span>\n<span class=\"token comment\">// &lt;CommentList /> com os dados atualizados.</span>\n<span class=\"token keyword\">var</span> CommentListWithSubscription <span class=\"token operator\">=</span> <span class=\"token function\">withSubscription</span><span class=\"token punctuation\">(</span>CommentList<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token comment\">// O restante da aplicação está interessada no componente inscrito</span>\n<span class=\"token comment\">// então exportamos em vez do CommentList original.</span>\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> CommentListWithSubscription<span class=\"token punctuation\">;</span></code></pre></div>\n<h4 id=\"solution-revisited\"><a href=\"#solution-revisited\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solution, Revisited </h4>\n<p>Agora que entendemos melhor os componentes de ordem superior, vamos dar uma olhada na solução completa que não envolve mixins. Existem algumas pequenas alterações anotadas com comentários inseridos nas linhas:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">withSubscription</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">WrappedComponent</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n    <span class=\"token function-variable function\">getInitialState</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token keyword\">return</span> <span class=\"token punctuation\">{</span>\n        comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n      <span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">componentDidMount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">addChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">componentWillUnmount</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">removeChangeListener</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleChange<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">handleChange</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">setState</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n        comments<span class=\"token operator\">:</span> DataSource<span class=\"token punctuation\">.</span><span class=\"token function\">getComments</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span>\n      <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n      <span class=\"token comment\">// Use o spread no JSX para passar todas as props e state para baixo automaticamente.</span>\n      <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">WrappedComponent</span></span> <span class=\"token spread\"><span class=\"token punctuation\">{</span><span class=\"token punctuation\">...</span><span class=\"token attr-value\">this</span><span class=\"token punctuation\">.</span><span class=\"token attr-value\">props</span><span class=\"token punctuation\">}</span></span> <span class=\"token spread\"><span class=\"token punctuation\">{</span><span class=\"token punctuation\">...</span><span class=\"token attr-value\">this</span><span class=\"token punctuation\">.</span><span class=\"token attr-value\">state</span><span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token comment\">// Alteração opcional: converte CommentList em um componente de função</span>\n<span class=\"token comment\">// porque não usa métodos ou estados do ciclo de vida.</span>\n<span class=\"token keyword\">function</span> <span class=\"token function\">CommentList</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">props</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">var</span> comments <span class=\"token operator\">=</span> props<span class=\"token punctuation\">.</span>comments<span class=\"token punctuation\">;</span>\n  <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n    <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n      </span><span class=\"token punctuation\">{</span>comments<span class=\"token punctuation\">.</span><span class=\"token function\">map</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">comment</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n        <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">Comment</span></span> <span class=\"token attr-name\">comment</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">}</span></span> <span class=\"token attr-name\">key</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>comment<span class=\"token punctuation\">.</span>id<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span>\n      <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n    </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n  <span class=\"token punctuation\">)</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token comment\">// Em vez de declarar CommentListWithSubscription,</span>\n<span class=\"token comment\">// exportamos o componente envolvido</span>\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> <span class=\"token function\">withSubscription</span><span class=\"token punctuation\">(</span>CommentList<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<p>Os componentes de ordem superior são um padrão poderoso. Você pode passar argumentos adicionais para eles, se desejar personalizar ainda mais o comportamento deles. Afinal, eles nem são um recurso do React. São apenas funções que recebem componentes e retornam componentes que os envolvem.</p>\n<p>Como qualquer solução, os componentes de ordem superior têm suas próprias armadilhas. Por exemplo, se você usar fortemente <a href=\"/docs/more-about-refs.html\">refs</a>, poderá notar que agrupar algo em um componente de ordem superior altera o ref para apontar para o componente de agrupamento. Na prática, desencorajamos o uso de referências para a comunicação de componentes, por isso não achamos que seja um grande problema. No futuro, podemos considerar a adição de <a href=\"https://github.com/facebook/react/issues/4213\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">ref forwarding</a> ao React para resolver esse incômodo.</p>\n<h3 id=\"rendering-logic\"><a href=\"#rendering-logic\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Lógica de renderização </h3>\n<p>O próximo caso de uso mais comum para mixins que descobrimos em nossa base de código é o compartilhamento da lógica de renderização entre os componentes.</p>\n<p>Aqui está um exemplo típico desse padrão:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> RowMixin <span class=\"token operator\">=</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token comment\">// Chamado por componentes a partir do render()</span>\n  <span class=\"token function-variable function\">renderHeader</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span> <span class=\"token attr-name\">className</span><span class=\"token attr-value\"><span class=\"token punctuation attr-equals\">=</span><span class=\"token punctuation\">'</span>row-header<span class=\"token punctuation\">'</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>h1</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n          </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">getHeaderText</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token comment\">/* Definido por componentes */</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n        </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>h1</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> UserRow <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  mixins<span class=\"token operator\">:</span> <span class=\"token punctuation\">[</span>RowMixin<span class=\"token punctuation\">]</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token comment\">// Chamado por RowMixin.renderHeader()</span>\n  <span class=\"token function-variable function\">getHeaderText</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>user<span class=\"token punctuation\">.</span>fullName<span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">renderHeader</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token comment\">/* Definido por RowMixin */</span><span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n        </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>h2</span><span class=\"token punctuation\">></span></span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>user<span class=\"token punctuation\">.</span>biography<span class=\"token punctuation\">}</span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>h2</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<p>Vários componentes podem estar compartilhando <code class=\"gatsby-code-text\">RowMixin</code> para renderizar o cabeçalho, e cada um deles precisaria definir <code class=\"gatsby-code-text\">getHeaderText()</code>.</p>\n<h4 id=\"solution-2\"><a href=\"#solution-2\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solução </h4>\n<p>Se você ver a lógica de renderização dentro de um mixin, é hora de extrair um componente!</p>\n<p>Em vez de <code class=\"gatsby-code-text\">RowMixin</code>, definiremos um componente <code class=\"gatsby-code-text\">&lt;RowHeader&gt;</code>. Também substituiremos a convenção de definir um método <code class=\"gatsby-code-text\">getHeaderText()</code> pelo mecanismo padrão do fluxo de dados principais no React: passando adereços.</p>\n<p>Por fim, como atualmente nenhum desses componentes precisa de métodos ou estados do ciclo de vida, podemos declará-los como funções simples:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">RowHeader</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">props</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n    <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span> <span class=\"token attr-name\">className</span><span class=\"token attr-value\"><span class=\"token punctuation attr-equals\">=</span><span class=\"token punctuation\">'</span>row-header<span class=\"token punctuation\">'</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>h1</span><span class=\"token punctuation\">></span></span><span class=\"token punctuation\">{</span>props<span class=\"token punctuation\">.</span>text<span class=\"token punctuation\">}</span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>h1</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n    </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n  <span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span>\n\n<span class=\"token keyword\">function</span> <span class=\"token function\">UserRow</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">props</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n    <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">RowHeader</span></span> <span class=\"token attr-name\">text</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>props<span class=\"token punctuation\">.</span>user<span class=\"token punctuation\">.</span>fullName<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>h2</span><span class=\"token punctuation\">></span></span><span class=\"token punctuation\">{</span>props<span class=\"token punctuation\">.</span>user<span class=\"token punctuation\">.</span>biography<span class=\"token punctuation\">}</span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>h2</span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n    </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n  <span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span></code></pre></div>\n<p>As props mantêm as dependências de componentes explícitas, fáceis de substituir e aplicáveis com ferramentas como <a href=\"https://flowtype.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">Flow</a> e <a href=\"https://www.typescriptlang.org/\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">TypeScript</a>.</p>\n<blockquote>\n<p><strong>Nota:</strong></p>\n<p>Definir componentes como funções não é necessário. Também não há nada de errado em usar métodos e estados do ciclo de vida - eles são os primeiros recursos do React quando usado em formato de classe. Usamos componentes de função neste exemplo porque são mais fáceis de ler e não precisávamos desses recursos extras, mas as classes funcionariam da mesma maneira.</p>\n</blockquote>\n<h3 id=\"context\"><a href=\"#context\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Contexto </h3>\n<p>Outro grupo de mixins que descobrimos eram helpers por fornecer e consumir <a href=\"/docs/context.html\">React context</a>. O contexto é um recurso instável experimental, possui <a href=\"https://github.com/facebook/react/issues/2517\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">certos problemas</a> e provavelmente mudará sua API no futuro. Não recomendamos o uso, a menos que você tenha certeza de que não há outra maneira de resolver seu problema.</p>\n<p>No entanto, se você já usa o contexto hoje, pode estar ocultando seu uso com mixins como este:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> RouterMixin <span class=\"token operator\">=</span> <span class=\"token punctuation\">{</span>\n  contextTypes<span class=\"token operator\">:</span> <span class=\"token punctuation\">{</span>\n    router<span class=\"token operator\">:</span> React<span class=\"token punctuation\">.</span>PropTypes<span class=\"token punctuation\">.</span>object<span class=\"token punctuation\">.</span>isRequired\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token comment\">// O mixin fornece um método para que os componentes</span>\n  <span class=\"token comment\">// não precisem utilizar a API de contexto diretamente</span>\n  <span class=\"token function-variable function\">push</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">path</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>context<span class=\"token punctuation\">.</span>router<span class=\"token punctuation\">.</span><span class=\"token function\">push</span><span class=\"token punctuation\">(</span>path<span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Link <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  mixins<span class=\"token operator\">:</span> <span class=\"token punctuation\">[</span>RouterMixin<span class=\"token punctuation\">]</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">handleClick</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">e</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    e<span class=\"token punctuation\">.</span><span class=\"token function\">stopPropagation</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n    <span class=\"token comment\">// Este método é definido em RouterMixin.</span>\n    <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">push</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>to<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>a</span> <span class=\"token attr-name\">onClick</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleClick<span class=\"token punctuation\">}</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>children<span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>a</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> Link<span class=\"token punctuation\">;</span></code></pre></div>\n<h4 id=\"solution-3\"><a href=\"#solution-3\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solução </h4>\n<p>Concordamos que ocultar o uso do contexto do consumo de componentes é uma boa ideia até que a API do contexto se estabilize. No entanto, recomendamos o uso de componentes de ordem superior em vez de mixins para isso.</p>\n<p>Deixe o componente de empacotamento pegar algo do contexto e transmiti-lo com as props para o componente empacotado:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">function</span> <span class=\"token function\">withRouter</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">WrappedComponent</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token keyword\">return</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n    contextTypes<span class=\"token operator\">:</span> <span class=\"token punctuation\">{</span>\n      router<span class=\"token operator\">:</span> React<span class=\"token punctuation\">.</span>PropTypes<span class=\"token punctuation\">.</span>object<span class=\"token punctuation\">.</span>isRequired\n    <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n    <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n       <span class=\"token comment\">// O componente wrapper lê algo do contexto</span>\n       <span class=\"token comment\">// e o passa para baixo como uma prop ao componente empacotado.</span>\n      <span class=\"token keyword\">var</span> router <span class=\"token operator\">=</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>context<span class=\"token punctuation\">.</span>router<span class=\"token punctuation\">;</span>\n      <span class=\"token keyword\">return</span> <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span><span class=\"token class-name\">WrappedComponent</span></span> <span class=\"token spread\"><span class=\"token punctuation\">{</span><span class=\"token punctuation\">...</span><span class=\"token attr-value\">this</span><span class=\"token punctuation\">.</span><span class=\"token attr-value\">props</span><span class=\"token punctuation\">}</span></span> <span class=\"token attr-name\">router</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>router<span class=\"token punctuation\">}</span></span> <span class=\"token punctuation\">/></span></span><span class=\"token punctuation\">;</span>\n    <span class=\"token punctuation\">}</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Link <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">handleClick</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">e</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    e<span class=\"token punctuation\">.</span><span class=\"token function\">stopPropagation</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n    <span class=\"token comment\">// O componente empacotado usa props ao invés do context.</span>\n    <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>router<span class=\"token punctuation\">.</span><span class=\"token function\">push</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>to<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>a</span> <span class=\"token attr-name\">onClick</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>handleClick<span class=\"token punctuation\">}</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>children<span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>a</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token comment\">// Não se esqueça de empacotar o componente!</span>\nmodule<span class=\"token punctuation\">.</span>exports <span class=\"token operator\">=</span> <span class=\"token function\">withRouter</span><span class=\"token punctuation\">(</span>Link<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<p>Se você estiver usando uma biblioteca de terceiros que fornece apenas um mixin, recomendamos que você arquive um problema vinculado a esta postagem para que eles possam fornecer um componente de ordem superior. Enquanto isso, você pode criar um componente de ordem superior exatamente da mesma maneira.</p>\n<h3 id=\"utility-methods\"><a href=\"#utility-methods\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Métodos de utilidade </h3>\n<p>Às vezes, os mixins são usados apenas para compartilhar funções utilitárias entre componentes:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> ColorMixin <span class=\"token operator\">=</span> <span class=\"token punctuation\">{</span>\n  <span class=\"token function\">getLuminance</span><span class=\"token punctuation\">(</span><span class=\"token parameter\">color</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">var</span> c <span class=\"token operator\">=</span> <span class=\"token function\">parseInt</span><span class=\"token punctuation\">(</span>color<span class=\"token punctuation\">,</span> <span class=\"token number\">16</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">var</span> r <span class=\"token operator\">=</span> <span class=\"token punctuation\">(</span>c <span class=\"token operator\">&amp;</span> <span class=\"token number\">0xFF0000</span><span class=\"token punctuation\">)</span> <span class=\"token operator\">>></span> <span class=\"token number\">16</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">var</span> g <span class=\"token operator\">=</span> <span class=\"token punctuation\">(</span>c <span class=\"token operator\">&amp;</span> <span class=\"token number\">0x00FF00</span><span class=\"token punctuation\">)</span> <span class=\"token operator\">>></span> <span class=\"token number\">8</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">var</span> b <span class=\"token operator\">=</span> <span class=\"token punctuation\">(</span>c <span class=\"token operator\">&amp;</span> <span class=\"token number\">0x0000FF</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span><span class=\"token number\">0.299</span> <span class=\"token operator\">*</span> r <span class=\"token operator\">+</span> <span class=\"token number\">0.587</span> <span class=\"token operator\">*</span> g <span class=\"token operator\">+</span> <span class=\"token number\">0.114</span> <span class=\"token operator\">*</span> b<span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Button <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  mixins<span class=\"token operator\">:</span> <span class=\"token punctuation\">[</span>ColorMixin<span class=\"token punctuation\">]</span><span class=\"token punctuation\">,</span>\n\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">var</span> theme <span class=\"token operator\">=</span> <span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span><span class=\"token function\">getLuminance</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>color<span class=\"token punctuation\">)</span> <span class=\"token operator\">></span> <span class=\"token number\">160</span> <span class=\"token operator\">?</span> <span class=\"token string\">'dark'</span> <span class=\"token operator\">:</span> <span class=\"token string\">'light'</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span> <span class=\"token attr-name\">className</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>theme<span class=\"token punctuation\">}</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>children<span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<h4 id=\"solution-4\"><a href=\"#solution-4\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Solução </h4>\n<p>Coloque funções utilitárias em módulos JavaScript regulares e importe-as. Isso também facilita testá-los ou usá-los fora dos seus componentes:</p>\n<div class=\"gatsby-highlight\" data-language=\"jsx\"><pre class=\"gatsby-code-jsx\"><code class=\"gatsby-code-jsx\"><span class=\"token keyword\">var</span> getLuminance <span class=\"token operator\">=</span> <span class=\"token function\">require</span><span class=\"token punctuation\">(</span><span class=\"token string\">'../utils/getLuminance'</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span>\n\n<span class=\"token keyword\">var</span> Button <span class=\"token operator\">=</span> React<span class=\"token punctuation\">.</span><span class=\"token function\">createClass</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">{</span>\n  <span class=\"token function-variable function\">render</span><span class=\"token operator\">:</span> <span class=\"token keyword\">function</span><span class=\"token punctuation\">(</span><span class=\"token punctuation\">)</span> <span class=\"token punctuation\">{</span>\n    <span class=\"token keyword\">var</span> theme <span class=\"token operator\">=</span> <span class=\"token function\">getLuminance</span><span class=\"token punctuation\">(</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>color<span class=\"token punctuation\">)</span> <span class=\"token operator\">></span> <span class=\"token number\">160</span> <span class=\"token operator\">?</span> <span class=\"token string\">'dark'</span> <span class=\"token operator\">:</span> <span class=\"token string\">'light'</span><span class=\"token punctuation\">;</span>\n    <span class=\"token keyword\">return</span> <span class=\"token punctuation\">(</span>\n      <span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;</span>div</span> <span class=\"token attr-name\">className</span><span class=\"token script language-javascript\"><span class=\"token script-punctuation punctuation\">=</span><span class=\"token punctuation\">{</span>theme<span class=\"token punctuation\">}</span></span><span class=\"token punctuation\">></span></span><span class=\"token plain-text\">\n        </span><span class=\"token punctuation\">{</span><span class=\"token keyword\">this</span><span class=\"token punctuation\">.</span>props<span class=\"token punctuation\">.</span>children<span class=\"token punctuation\">}</span><span class=\"token plain-text\">\n      </span><span class=\"token tag\"><span class=\"token tag\"><span class=\"token punctuation\">&lt;/</span>div</span><span class=\"token punctuation\">></span></span>\n    <span class=\"token punctuation\">)</span>\n  <span class=\"token punctuation\">}</span>\n<span class=\"token punctuation\">}</span><span class=\"token punctuation\">)</span><span class=\"token punctuation\">;</span></code></pre></div>\n<h3 id=\"other-use-cases\"><a href=\"#other-use-cases\" aria-hidden class=\"anchor\"><svg aria-hidden=\"true\" height=\"16\" version=\"1.1\" viewBox=\"0 0 16 16\" width=\"16\"><path fill-rule=\"evenodd\" d=\"M4 9h1v1H4c-1.5 0-3-1.69-3-3.5S2.55 3 4 3h4c1.45 0 3 1.69 3 3.5 0 1.41-.91 2.72-2 3.25V8.59c.58-.45 1-1.27 1-2.09C10 5.22 8.98 4 8 4H4c-.98 0-2 1.22-2 2.5S3 9 4 9zm9-3h-1v1h1c1 0 2 1.22 2 2.5S13.98 12 13 12H9c-.98 0-2-1.22-2-2.5 0-.83.42-1.64 1-2.09V6.25c-1.09.53-2 1.84-2 3.25C6 11.31 7.55 13 9 13h4c1.45 0 3-1.69 3-3.5S14.5 6 13 6z\"></path></svg></a>Outros casos de uso </h3>\n<p>Às vezes, as pessoas usam mixins para adicionar seletivamente o log aos métodos do ciclo de vida em alguns componentes. No futuro, pretendemos fornecer uma <a href=\"https://github.com/facebook/react/issues/5306\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">API oficial do DevTools</a> que permita implementar algo semelhante sem tocar nos componentes. No entanto, ainda é um trabalho em andamento. Se você depende muito de registrar mixins para depuração, convém continuar usando esses mixins por mais algum tempo.</p>\n<p>Se você não conseguir realizar algo com um componente, um componente de ordem superior ou um módulo utilitário, isso pode significar que o React deve fornecer isso imediatamente. <a href=\"https://github.com/facebook/react/issues/new\" target=\"_blank\" rel=\"nofollow noopener noreferrer\">Arquive um problema</a> para nos informar sobre seu caso de uso para mixins, e ajudaremos você a considerar alternativas ou talvez implementar sua solicitação de recurso.</p>\n<p>Mixins não são descontinuados no sentido tradicional. Você pode continuar usando-os com <code class=\"gatsby-code-text\">React.createClass()</code>, pois não mudaremos mais. Eventualmente, à medida que as classes ES6 ganham mais adoção e seus problemas de usabilidade no React são resolvidos, podemos dividir <code class=\"gatsby-code-text\">React.createClass()</code> em um pacote separado, porque a maioria das pessoas não precisa disso. Mesmo nesse caso, seus antigos mixins continuariam funcionando.</p>\n<p>Acreditamos que as alternativas acima são melhores para a grande maioria dos casos, e convidamos você a escrever aplicativos React sem usar mixins.</p>","excerpt":"“Como eu compartilho o código entre diversos componentes?” é uma das primeiras perguntas que as pessoas fazem quando aprendem React. Nossa resposta sempre foi usar composição de componentes para reutilização do código. Você pode definir um componente e usá-lo em diversos outros componentes. Nem sempre é óbvio como um determinado padrão pode ser resolvido com a componetização. O React é influenciado pela programacão funcional, mas entrou em um campo que é dominado por bibliotecas orientadas à…","frontmatter":{"title":"Mixins Considerados Nocivos","next":null,"prev":null,"author":[{"frontmatter":{"name":"Dan Abramov","url":"https://twitter.com/dan_abramov"}}]},"fields":{"date":"13 de julho de 2016","path":"content/blog/2016-07-13-mixins-considered-harmful.md","slug":"/blog/2016/07/13/mixins-considered-harmful.html"}},"allMarkdownRemark":{"edges":[{"node":{"frontmatter":{"title":"React v17.0"},"fields":{"slug":"/blog/2020/10/20/react-v17.html"}}},{"node":{"frontmatter":{"title":"Apresentando o novo JSX Transform"},"fields":{"slug":"/blog/2020/09/22/introducing-the-new-jsx-transform.html"}}},{"node":{"frontmatter":{"title":"React v17.0 Candidato à lançamento: Sem novas funcionalidades"},"fields":{"slug":"/blog/2020/08/10/react-v17-rc.html"}}},{"node":{"frontmatter":{"title":"React v16.13.0"},"fields":{"slug":"/blog/2020/02/26/react-v16.13.0.html"}}},{"node":{"frontmatter":{"title":"Construindo Ótimas Experiências de Usuário com Modo Concorrente e Suspense"},"fields":{"slug":"/blog/2019/11/06/building-great-user-experiences-with-concurrent-mode-and-suspense.html"}}},{"node":{"frontmatter":{"title":"Preparando para o Futuro com as Prereleases React"},"fields":{"slug":"/blog/2019/10/22/react-release-channels.html"}}},{"node":{"frontmatter":{"title":"Apresentando o novo React DevTools"},"fields":{"slug":"/blog/2019/08/15/new-react-devtools.html"}}},{"node":{"frontmatter":{"title":"React v16.9.0 e a atualização do Roadmap"},"fields":{"slug":"/blog/2019/08/08/react-v16.9.0.html"}}},{"node":{"frontmatter":{"title":"O React já esta traduzido? ¡Sí! Sim! はい！"},"fields":{"slug":"/blog/2019/02/23/is-react-translated-yet.html"}}},{"node":{"frontmatter":{"title":"React v16.8: O React com Hooks"},"fields":{"slug":"/blog/2019/02/06/react-v16.8.0.html"}}}]}},"pageContext":{"slug":"/blog/2016/07/13/mixins-considered-harmful.html"}},"staticQueryHashes":[]}