如何将字符串转换为jsx?

时间:2016-03-19 16:40:17

标签: reactjs react-jsx

我如何获取字符串并将其转换为jsx?例如,如果我从textarea引入字符串,我该如何将其转换为React元素;

var jsxString = document.getElementById('textarea').value;

我会用什么过程在客户端转换它?有可能吗?

9 个答案:

答案 0 :(得分:21)

您可以考虑使用JSX属性dangerouslySetInnerHTML

以下示例用法:

class YourComponent{

render() {
   someHtml = '<div><strong>blablabla<strong><p>another blbla</p/></div>'

   return(
       <div className="Container" dangerouslySetInnerHTML={{__html: 
        someHtml}}></div>
    )
  }
}

我知道你迟到了:)但希望它可以帮助别人

答案 1 :(得分:7)

如果你考虑字符串

<div>Hello World</div>

如果我们非常严格,这实际上是有效的JSX。问题是如何将这个JSX字符串编译成React代码。

最简单,推荐的方法是下载像Babel这样的库并用它来转换代码。 Babel可以像repl does一样在浏览器中运行。

也可以将JSX转换为其他格式,但在这种情况下,您必须找到一个编译器或自己创建一个。

创建JSX =&gt;的步骤自己做出反应是:

  1. 将代码字符串转换为AST表示
  2. 解析AST并将代码输出回字符串
  3. 所以你需要像espree这样的AST解析器来支持JSX,然后你可以创建一个代码来遍历AST树并输出一些东西,比如React -code。

    JSX数据的AST树由普通的JavaScript AST和JSX节点组成。解析器应遍历树并将JSX节点转换为普通的JavaScript代码。

    如果您编译为React并遇到带有标记“div”的JSX节点,则应将其编译为React.createElement("div",...调用,并将该AST节点下的属性和子节点作为该调用的参数插入。

    我创建了一个小的AST Walker,它可以处理AST树ASTWalker,它可以用来将AST树转换成某种输出格式,比如React或DOM。

    如何使用它的在线示例如下:

    http://codepen.io/teroktolonen/pen/KzWVqx?editors=1010

    主要代码如下:

        // here is the JSX string to parse
        var codeStr = "<div>Hello world</div>";
        var walker = ASTWalker({
            defaultNamespace: "react",
        });
        // compile AST representation out of it.
        var rawAST = espree.parse(codeStr, {
              ecmaVersion: 6,
              sourceType: "script",
              // specify additional language features
              ecmaFeatures: {
                // enable JSX parsing
                jsx: true
              } 
            });
    
       // then you can walk the walk to create the code
       walker.startWalk( rawAST, {} );
       var code = walker.getCode();  
       console.log(code); 
       document.getElementById("sourceCode").innerHTML = code;
    

    免责声明:图书馆并不打算编译成React。它主要与defaultNamespace: "DOM",一起使用,用它来编译成纯JavaScript + DOM表示。尝试比简单标签更复杂的东西可能会导致错误。

    重要的是要注意React不仅是JSX的可能输出格式。

答案 2 :(得分:5)

我一直在使用html-to-react取得一些成功(自闭标签导致了一个问题,但修复是在pull请求中......)将标记字符串解析为DOM类对象,并在转动React元素。它不漂亮,如果你可以避免它,那就这样做。但它完成了工作。

html-to-react at github:https://github.com/mikenikles/html-to-react

答案 3 :(得分:3)

我个人喜欢这样做,就像前面的建议(建议在JSX中使用dangerouslySetInnerHTML属性)一样。

只是一种替代方法,如今有一个名为 react-html-parser 的库。您可以检查它并通过以下URL从NPM注册表中安装:https://www.npmjs.com/package/react-html-parser。该软件包今天的每周下载统计信息是 23,696 。看起来很受欢迎的库。即使是看起来更方便使用,我自己,在真正使用它之前仍需要更多阅读和进一步考虑。

从NPM页面复制的代码段:

import React from 'react';
import ReactHtmlParser, { processNodes, convertNodeToElement, htmlparser2 } from 'react-html-parser';

class HtmlComponent extends React.Component {
  render() {
    const html = '<div>Example HTML string</div>';
    return <div>{ ReactHtmlParser(html) }</div>;
  }
}

答案 4 :(得分:1)

我最近遇到了这个答案,对我来说这很划算。您不需要提供字符串。返回一个JSX元素数组即可解决问题。

我们可以将JSX元素存储在JavaScript数组中。

let arrUsers = [<li>Steve</li>,<li>Bob</li>,<li>Michael</li>];

并在您的HTML(JSX)中将其绑定,

<ul>{arrUsers}</ul>

就这么简单。

答案 5 :(得分:0)

这是一个小实用程序组件:

const RawHtml = ({ children="", tag: Tag = 'div', ...props }) =>
  <Tag { ...props } dangerouslySetInnerHTML={{ __html: children }}/>;

样品用量:

<RawHtml tag={'span'} style={{'font-weight':'bold'}}>
  {"Lorem<br/>ipsum"}
</RawHtml>

答案 6 :(得分:0)

这是无需使用危险的SetInnerHTML即可实现的方法。

import React from "react";

let getNodes = str =>
  new DOMParser().parseFromString(str, "text/html").body.childNodes;
let createJSX = nodeArray => {
  const className = nodeArray[0].className;
  return nodeArray.map(node => {
    let attributeObj = {};
    const {
      attributes,
      localName,
      childNodes,
      nodeValue
    } = node;
    if (attributes) {
      Array.from(attributes).forEach(attribute => {
        if (attribute.name === "style") {
          let styleAttributes = attribute.nodeValue.split(";");
          let styleObj = {};
          styleAttributes.forEach(attribute => {
            let [key, value] = attribute.split(":");
            styleObj[key] = value;
          });
          attributeObj[attribute.name] = styleObj;
        } else {
          attributeObj[attribute.name] = attribute.nodeValue;
        }
      });
    }
    return localName ?
      React.createElement(
        localName,
        attributeObj,
        childNodes && Array.isArray(Array.from(childNodes)) ?
        createJSX(Array.from(childNodes)) :
        []
      ) :
      nodeValue;
  });
};

export const StringToJSX = props => {
  return createJSX(Array.from(getNodes(props.domString)));
};

导入StringToJSX并以以下格式将字符串作为道具传递。

<StringToJSX domString={domString}/>

PS:我可能错过了一些边缘情况,例如属性

答案 7 :(得分:0)

html-react-parser 正是您所需要的。

import parse from 'html-react-parser';
import React from 'react';

export default function YourComponent() {
    someHtml = '<div><strong>blablabla<strong><p>another blbla</p/></div>'
     
    return (
        <div className="Container">{parse(someHtml)}</div>
    )
}

答案 8 :(得分:-5)

您需要使用预设react

的babel
npm install --save-dev babel-cli babel-preset-react

将以下行添加到.babelrc文件中:

{
  "presets": ["react"]
}

然后运行

./node_modules/.bin/babel script.js --out-file script-compiled.js

您可以找到更多信息here