尝试在 JSX 中的字符串中呈现 link

Trying to render a link within a string, within JSX

我正在尝试渲染 link,它位于具有属性和值的对象数组中。

const arr = [
  {
    id: 1,
    title: "This is a title",
    body: [
      "This is some stuff. Lorem ipsum, lorizzle for shizzle.",
      "Click here to send an <Link to="mailto:yo@mail.com">email</Link>"
    ]
  },
  {
    id: 2,
    title: "This is another title",
    body: [
      "Moar stuff.",
      "Here is ma' <Link to="mailto:hello@mail.com">email</Link>"
    ]
  }
]

我正在使用此逻辑映射数组的对象并将它们存储在组件数组中。这按预期工作,如果我打算做的只是在段落中呈现一些文本。当涉及到 links 时,这根本行不通。我的猜测是 React 将字符串作为文本,并将整个内容呈现为文本。它不关心内容。

            <section key={item.key} className="">
                <h2 className="text-base">{item.title}</h2>
                {
                    item.body.map(function(paragraph) {
                        return(
                            <p className="text-sm">{paragraph}</p>
                        )
                    })
                }
            </section>

我试过将 Link 标签括在大括号内,以连接字符串和电子邮件(就像在 HTML 中出现的那样)、字符串模板文字。没有任何效果。

我不确定我是否缺少依赖项或步骤。也许我采取的方法是错误的?也许我想做的事情在 React 中是不可能的?

希望对此事有所了解。

您可以尝试使用 dangerouslySetInnerHtml

像这样:<div dangerouslySetInnerHtml={paragraph} />

这个属性的命名是有原因的,所以要小心你在那里发送的内容,因为它可能会导致 XSS 注入。

在此处了解更多信息:https://reactjs.org/docs/dom-elements.html#dangerouslysetinnerhtml

这是在数组中传输 jsx 的一种非常幼稚的方法。

const arr = [
  {
    id: 1,
    title: "This is a title",
    body: [
      ["This is some stuff. Lorem ipsum, lorizzle for shizzle."],
      ["Click here to send an ", <Link to="mailto:yo@mail.com">email</Link>"]
    ]
  },
item.body.map(function(paragraph) {
    const content = paragraph.reduce((combined, elem) => {
        return content + elem;
    });

    return(
        <p className="text-sm">{paragraph}</p>
    )
});

对我发现的问题进行一些更正

假设你想要一个锚标签

所以调整你的阵列,改变

  1. <a href='mailto:yo@mail.com'>email</a> 而不是 <Link to="mailto:yo@mail.com">email</Link>
  2. "Click here to send an <Link to="mailto:yo@mail.com">email</Link>" 而不是 "Click here to send an <a href='mailto:yo@mail.com'>email</a>",引号应该在双引号内正确使用你需要有单引号,反之亦然

添加解决方案进行上述更改

这里可以有多种做法

  1. 使用库

例子
html-react-parser

代码片段

App.js

import React, { Fragment } from "react";
import Parser from "html-react-parser";

const arr = [
  {
    id: 1,
    title: "This is a title",
    body: [
      "This is some stuff. Lorem ipsum, lorizzle for shizzle.",
      "Click here to send an <a href='mailto:yo@mail.com'>email</a>"
    ]
  },
  {
    id: 2,
    title: "This is another title",
    body: [
      "Moar stuff.",
      "Here is ma' <a href='mailto:hello@mail.com'>email</a>"
    ]
  }
];
export default function App() {
  return (
    <Fragment>
      {arr.map(item => (
        <section key={item.key} className="">
          <h2 className="text-base">{item.title}</h2>
          {item.body.map(function(paragraph) {
            return <p className="text-sm">{Parser(paragraph)}</p>;
          })}
        </section>
      ))}
    </Fragment>
  );
}
  1. 使用 dangerouslySetInnerHtml,但此方法有一些缺陷,如文档中所述

dangerouslySetInnerHTML is React’s replacement for using innerHTML in the browser DOM. In general, setting HTML from code is risky because it’s easy to inadvertently expose your users to a cross-site scripting (XSS) attack.

代码片段

App.js

import React, { Fragment } from "react";

const arr = [
  {
    id: 1,
    title: "This is a title",
    body: [
      "This is some stuff. Lorem ipsum, lorizzle for shizzle.",
      "Click here to send an <a href='mailto:yo@mail.com'>email</a>"
    ]
  },
  {
    id: 2,
    title: "This is another title",
    body: [
      "Moar stuff.",
      "Here is ma' <a href='mailto:hello@mail.com'>email</a>"
    ]
  }
];
export default function App() {
  return (
    <Fragment>
      {arr.map(item => (
        <section key={item.key} className="">
          <h2 className="text-base">{item.title}</h2>
          {item.body.map(function(paragraph) {
            return (
              <p
                className="text-sm"
                dangerouslySetInnerHTML={{ __html: paragraph }}
              />
            );
          })}
        </section>
      ))}
    </Fragment>
  );
}

在上面的方法中,你可以做一个dompurify并设置dangerouslysetinnerhtml来避免XSS攻击

import DOMPurify from "dompurify";

<p
  className="text-sm"
  dangerouslySetInnerHTML={{ __html: DOMPurify.sanitize(paragraph) }}
/>;

我希望这能让你更好地理解