Reactjs converter html string para jsx

212

Estou tendo problemas para lidar com o ReactJS do facebook. Sempre que faço o ajax e quero exibir dados html, o ReactJS os exibe como texto. (Veja a figura abaixo)

Cadeia de renderização ReactJS

Os dados são exibidos através da função de retorno de chamada de sucesso do jquery Ajax.

$.ajax({
   url: url here,
   dataType: "json",
   success: function(data) {
      this.setState({
           action: data.action
      })
   }.bind(this)
});

insira a descrição da imagem aqui

Existe alguma maneira fácil de converter isso em html? Como devo fazer isso usando o ReactJS?

Peter Wateber
fonte

Respostas:

405

Por padrão, o React escapa o HTML para impedir o XSS (script entre sites) . Se você realmente deseja renderizar HTML, pode usar a dangerouslySetInnerHTMLpropriedade:

<td dangerouslySetInnerHTML={{__html: this.state.actions}} />

A reação força essa sintaxe intencionalmente complicada, para que você não renderize acidentalmente o texto como HTML e introduza erros XSS.

Sophie Alpert
fonte
4
Essa sintaxe é mostrada na página inicial e no tutorial, mas eu acabei de perceber que não está documentada em nenhum outro lugar, então enviei o número 413 para corrigir.
Sophie Alpert
Corrigir! Eu resolvi isso já usando dangerouslySetInnerHTML mas graças embora :)
Peter Wateber
Vale a pena jogar com segurança para limpar o conteúdo usando a sanitizefunção do dompurifypacote npm se você estiver obtendo essas informações de uma API externa.
Barry Michael Doyle
77

Agora existem métodos mais seguros para fazer isso. Os documentos foram atualizados com esses métodos.

Outros métodos

  1. Mais fácil - use Unicode, salve o arquivo como UTF-8 e defina-o charsetcomo UTF-8.

    <div>{'First · Second'}</div>

  2. Mais seguro - use o número Unicode da entidade dentro de uma string Javascript.

    <div>{'First \u00b7 Second'}</div>

    ou

    <div>{'First ' + String.fromCharCode(183) + ' Second'}</div>

  3. Ou uma matriz mista com strings e elementos JSX.

    <div>{['First ', <span>&middot;</span>, ' Second']}</div>

  4. Último recurso - insira HTML bruto usando dangerouslySetInnerHTML.

    <div dangerouslySetInnerHTML={{__html: 'First &middot; Second'}} />

Brett DeWoody
fonte
15
Eu preparei a documentação, mas sobre uma longa string HTML, como a de um editor WYSIWYG? Eu não posso ver como podemos usar o 1º, 2º ou 3º método
ericn
4
Eu concordo com @eric. De que servem os métodos 1 a 3 para o conteúdo já escapado armazenado em algum lugar, como um banco de dados? Observe também que o método 4 - o único método - significa que você não pode adicionar nós filhos.
dvdplm
14
Sim. Esses exemplos com conteúdo "dinâmico" codificado não fazem muito sentido.
regularmike
Este é meu innerHTML - "Exibindo admins \ u003cb \ u003e1 \ u0026nbsp; - \ u0026nbsp; 10 \ u003c / b \ u003e de \ u003cb \ u003e13 \ u003c / b \ u003e no total" enquanto isso é renderizado - "Exibindo administradores <b> 1 & nbsp; - & nbsp; 10 </b> de <b> 13 </b> no total ". Quando tento usar o perigosamente SetInnerHTML, tudo quebra.
vipin8169
36

Eu recomendo usar o Interweave criado por milesj . É uma biblioteca fenomenal que utiliza um número de técnicas engenhosas para analisar e inserir HTML com segurança no DOM.

O Interweave é uma biblioteca de reação para renderizar HTML com segurança, filtrar atributos, copiar automaticamente texto com correspondências, renderizar caracteres emoji e muito mais.

  • O Interweave é uma biblioteca robusta do React que pode:
    • Renderize HTML com segurança sem usar o DangerouslySetInnerHTML.
    • Retire com segurança as tags HTML.
    • Proteção automática contra XSS e injeção.
    • Limpe os atributos HTML usando filtros.
    • Interpole componentes usando matchers.
    • URLs, IPs, emails e hashtags de link automático.
    • Renderize caracteres Emoji e emoticon.
    • E muito mais!

Exemplo de uso:

import React from 'react';
import { Markup } from 'interweave';

const articleContent = "<p><b>Lorem ipsum dolor laboriosam.</b> </p><p>Facere debitis impedit doloremque eveniet eligendi reiciendis <u>ratione obcaecati repellendus</u> culpa? Blanditiis enim cum tenetur non rem, atque, earum quis, reprehenderit accusantium iure quas beatae.</p><p>Lorem ipsum dolor sit amet <a href='#testLink'>this is a link, click me</a> Sunt ducimus corrupti? Eveniet velit numquam deleniti, delectus  <ol><li>reiciendis ratione obcaecati</li><li>repellendus culpa? Blanditiis enim</li><li>cum tenetur non rem, atque, earum quis,</li></ol>reprehenderit accusantium iure quas beatae.</p>"

<Markup content={articleContent} /> // this will take the articleContent string and convert it to HTML markup. See: https://milesj.gitbook.io/interweave


//to install package using npm, execute the command
npm install interweave
Arman Nisch
fonte
Você poderia fornecer um exemplo de uso, por favor?
El Anonimo
1
@ElAnonimo Adicionei um exemplo de uso. Espero que isso torne as coisas um pouco mais claras.
Arman Nisch 16/09/19
1
Graças a um milhão, entrelaçar é exatamente o que eu precisava. Felicidades.
Nicholas Hamilton
1
A documentação para isso não é útil. Também tentei com algumas linhas de html e tinha uma página cheia de mensagens de erro. Alguém tem exemplos ou algum recurso com documentação?
Tarun Kolla
8
npm i html-react-parser;

import Parser from 'html-react-parser';

<td>{Parser(this.state.archyves)}</td>
Donatas Kuskys
fonte
6

Eu encontrei este violino js. isso funciona assim

function unescapeHTML(html) {
    var escapeEl = document.createElement('textarea');
    escapeEl.innerHTML = html;
    return escapeEl.textContent;
}

<textarea className="form-control redactor"
                          rows="5" cols="9"
                          defaultValue={unescapeHTML(this.props.destination.description)}
                          name='description'></textarea>

ligação jsfiddle

Hassan Gilak
fonte
Infelizmente, o documento não funciona na renderização do servidor.
Laurent Van Winckel
Poderia se você import JSDOM from 'jsdom'; global.window = new JSDOM('', { url: 'http://localhost' }); global.document = global.window.document;idk goodluck
Coty Embry
2

Você também pode usar Parser () em html-react-parser. Eu usei o mesmo. Link compartilhado.

Abhra Dey
fonte
2

eu começo a usar o pacote npm chamado react-html-parser

Dayan
fonte
1

Para aqueles que ainda estão experimentando, o npm install react-html-parser

Quando eu instalei, ele tinha 123628 downloads semanais.

import ReactHtmlParser from 'react-html-parser'

<div>{ReactHtmlParser(htmlString)}</div>
letele
fonte
0

Você pode usar o seguinte se quiser renderizar html bruto no React

<div dangerouslySetInnerHTML={{__html: `html-raw-goes-here`}} />

Exemplo - Renderizar

O teste é um bom dia

Panayiotis Georgiou
fonte