服务器和客户端从相同的JSX代码生成不同的标记

时间:2014-09-24 18:24:45

标签: reactjs react-jsx

这是我的JSX:

<h4>{post.title} <small> (by {post.author})</small> </h4>

这是在服务器上生成的内容(使用React.renderComponentToString())并发送给客户端。

<h4 data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0">
    <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.0">Why JavaScript is eating the world.</span>
    <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.1"> </span>
    <small data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.2">
        <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.2.0"> (by </span>
        <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.2.1">spike</span>
        <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.2.2">)</span>
    </small>
    <span data-reactid=".2ggx1vlvrwg.1.0.0.$posts-about.$2.0.3"></span>
</h4>

这是客户端(在浏览器中)生成的内容:

<h4 data-reactid=".0.1.0.0.$posts-about.$2.0">
    <span data-reactid=".0.1.0.0.$posts-about.$2.0.0">Why JavaScript is eating the world.</span>
    <small data-reactid=".0.1.0.0.$posts-about.$2.0.1">
        <span data-reactid=".0.1.0.0.$posts-about.$2.0.1.0"> (by </span>
        <span data-reactid=".0.1.0.0.$posts-about.$2.0.1.1">spike</span>
        <span data-reactid=".0.1.0.0.$posts-about.$2.0.1.2">)</span>
    </small>
</h4>

显然有两个跨度缺失,导致React attempted to use reuse markup in a container but the checksum was invalid。错误。

我认为问题出在JSX编译器中。生成的捆绑并发送到客户端的JavaScript与服务器使用的不同。

有趣的是,如果我&#34;修复&#34; JSX中的缩进,它的工作原理。服务器和客户端都生成相同的HTML标记,而没有那些额外的跨度。

<h4>{post.title}
    <small> (by {post.author})</small>
</h4>

但是我没有在文档中读到关于小心宽度JSX缩进的任何内容,这让我有点紧张,因为这种问题很难(或者至少很烦人)进行调试。

2 个答案:

答案 0 :(得分:3)

这个问题是由一个过时版本的remtify引起的。因此,使用了两个不同版本的JSX编译器。正如@FakeRainBrigand指出的那样,JSX中处理空格的规则最近发生了变化,这导致了编译JavaScript的差异。

答案 1 :(得分:1)

当你理解规则时,JSX处理空白很有意义。

  • 如果它在同一行,它将完全像html whitespace
  • 删除新换行符之前或之后的空格

最后一条规则与HTML不同,原因很简单。如果你有一个列表,并且你不想在HTML中找到它们之间的空格,你必须选择其中一个:

 <ul><li>Apples</li><li>Oranges</li></ul>
<ul><!-- 
  --><li>Apples</li><!--
  --><li>Oranges</li><!--
--></ul>

就像那些一样精彩,在JSX中它可以看起来像第一个,或

<ul>
  <li>Apples</li>
  <li>Oranges</li>
</ul>

如果您确实需要空间,可以将其插入其中一个元素

<ul>
  <li>Apples </li>
  <li>Oranges </li>
</ul>

或在你想要的地方放置一个非常明确的文字空间

<ul>
  <li>Apples</li>
  {' '}
  <li>Oranges</li>
</ul>

它有我最喜欢的表情符号{' '}