Skip to content
This page has been auto-translated and may contain errors.View in English

JSX

Construir até mesmo uma pequena interface com JavaScript puro significa fazer malabarismos entre etapas separadas: criar um elemento, definir sua classe, definir seu texto, depois anexá-lo à página. O markup e o código que o controla ficam separados, e mantê-los em sincronia fica mais difícil conforme a interface cresce. JSX fecha essa lacuna: o markup fica diretamente dentro do seu JavaScript, perto o bastante para você misturá-los livremente em vez de manter templates e scripts apartados.

Markup dentro de JavaScript

Como JSX é JavaScript, você pode colocar qualquer expressão JavaScript nele envolvendo-a em chaves, {}. Uma variável, uma chamada de função, um pouco de matemática, qualquer valor que você precise vai direto para o markup onde você digitaria texto estático.

jsx
const name = 'Ada'
return <p className="greeting">Hello, {name}</p>

Aqui {name} é substituído pelo valor da variável name quando isso é renderizado, então a página mostra "Hello, Ada". Fora das chaves, tudo é markup; dentro delas, você está de volta ao JavaScript puro.

Algumas regras vêm com JSX. A maioria dos atributos usa camelCase em vez dos nomes em minúsculas e com hífen que o HTML usa, então é className, htmlFor e tabIndex ao invés de class, for e tabindex, enquanto atributos ARIA e data- mantêm seus hífens, como em aria-hidden e data-testid. Toda tag precisa ser fechada, incluindo as que ficariam abertas em HTML, então <img /> e <br /> precisam dessa barra de fechamento. E um componente só pode retornar um elemento raiz. Se você precisar retornar dois elementos lado a lado sem envolvê-los em um <div> extra, envolva-os em um fragment, escrito como colchetes angulares vazios:

jsx
return (
  <>
    <h1>Title</h1>
    <p>Some text</p>
  </>
)

Como JSX difere do HTML

JSX parece próximo o bastante do HTML para que as diferenças sejam sutis o suficiente para você perder de vista até tropeçar nelas. Os nomes dos atributos são o primeiro: class vira className, porque class é uma palavra reservada em JavaScript. O atributo style é outro: em HTML é uma string de CSS, mas em JSX recebe um objeto JavaScript, com nomes de propriedades em camelCase e valores como strings.

jsx
<div style={{ backgroundColor: 'lightblue', fontSize: '18px' }}>Styled</div>

As chaves externas {} aqui são as mesmas que incorporam qualquer expressão, e as chaves internas {} são o objeto literal sendo incorporado, é por isso que um atributo style em JSX termina com duas chaves seguidas.

A outra diferença é o que é permitido dentro de {}. Aceita apenas expressões, coisas que produzem um valor, como uma variável, uma chamada de função ou um ternário. Não aceita statements, então um if ou um for não podem ir diretamente dentro de chaves no seu markup. Quando você precisa desse tipo de lógica, você a executa acima do return e incorpora o resultado em seu lugar.

Nos bastidores, JSX compila para chamadas de função JavaScript puro antes de chegar ao navegador. Esse é um detalhe de ferramental mais do que algo em que você vai pensar dia a dia, e o capítulo Beyond the basics volta a isso depois que o resto do React está no lugar.

JSX é açúcar sintático. O compilador transforma cada elemento em uma chamada para React.createElement ou, com o JSX runtime automático que as ferramentas desta trilha usam (padrão desde React 17, e o padrão que você vai obter com qualquer setup moderno), uma chamada equivalente gerada pela ferramenta de build sem precisar ter React em escopo. Aquele exemplo anterior compila para algo próximo a React.createElement('p', { className: 'greeting' }, 'Hello, ', name).

Essa etapa de compilação é exatamente o motivo de {} só conter expressões. Cada {} vira um argumento passado para essa chamada de função, e um argumento de função tem que avaliar para um valor. Um statement como if ou for não produz um valor, então não pode ficar onde um argumento é esperado. Um ternário funciona inline porque é uma expressão; um if não, porque é um statement. Quando a lógica é mais do que um ternário consegue conter de forma limpa, calcule o valor em uma variável acima do return e incorpore essa variável em seu lugar.

JunoJSX é markup com JavaScript misturado A coisa principal para lembrar: {} é sua porta de volta para JavaScript dentro do markup. Qualquer coisa entre essas chaves é um valor, uma variável, um cálculo, uma chamada de função, e ela cai direto na página.

Todo o resto segue de lá: className em vez de class, fechar toda tag, e um elemento raiz por return.

JunoJSX é markup com JavaScript misturado Trate {} como seu slot de expressão: variáveis, chamadas de função, ternários, tudo bem, statements como if não são.

Combine isso com as diferenças de nomenclatura, className, htmlFor, style como um objeto, e JSX para de parecer uma variante de HTML e começa a parecer o que é, JavaScript vestindo sintaxe de markup.

JunoJSX é markup com JavaScript misturado Cada {} compila para um argumento de função, que é toda a razão pela qual expressões funcionam lá e statements não.

Mantenha esse modelo mental e o resto das peculiaridades de JSX, atributos em camelCase, o objeto style, tags auto-fecháveis, param de parecer regras arbitrárias e começam a parecer consequências de "isso são chamadas React.createElement disfarçadas."

Próximo: Styling components, onde esses elementos ganham seu visual.