簡體   English   中英

用 JS function 替換 href 鏈接

[英]Replace href link with a JS function

在我的反應 electron 應用程序中,它正在使用 API,我收到 JSON 值以將數據顯示到組件中。 例如,我有一個Features組件:

const Features = () => {
  const { title } = useSelector(({ titles }) => titles);
  let string = title.features;
  // the string can contain some html tags. Example bellow:
  // sting = 'This is a string containing a href to <a href="www.google.com">Google</a>';

  string = string.replace(/href="(.*?)"/g, function() {
    return `onClick="${() => shell.openExternal('www.google.com')}"`;
  });

  return (
    <>
      <Heading>Features</Heading>
      <Text content={parsedHTML} />
    </>
  );
};

我想要的是用onClick替換href屬性並分配電子的shell.openExternal() function。

string.replace()回調 function 會這樣做,但是當我單擊<a>元素時,應用程序會拋出下一個錯誤:

錯誤:uncaughtException:預期onClick偵聽器是 function,而不是string類型的值。

更新

也試過這個邏輯,同樣的錯誤發生:

  global.openInBrowser = openInBrowser; // openInBrowser is basically a function that calls shell.openExternal(url)

  const re = new RegExp('<a([^>]* )href="([^"]+)"', 'g');
  string = string.replace(re, '<a$1href="#" onClick="openInBrowser(\'$2\')"');

這是 沙盒代表的鏈接。

我該如何正確地做到這一點?

Not sure on specifics of electron, but passing a (function(){functionName()})() would not work in html if there is no functionName variable available on window scope. 在 electron 中有一個全球環境,這可能會回答您的問題:

const Features = () => {
  const { title } = useSelector(({ titles }) => titles);
  let string = title.features;
  // the string can contain some html tags. Example bellow:
  // sting = 'This is a string containing a href to <a href="www.google.com">Google</a>';
  
  function runOpen(href){
      shell.openExternal(href)
  }      

  global.runOpen = runOpen;

  string = string.replace(/href="(.*?)"/g, function() {
    return `onClick="runOpen(${'www.google.com'})"`;
  });

  return (
    <>
      <Heading>Features</Heading>
      <Text content={parsedHTML} />
    </>
  );
};

如果它沒有,你可以使用類似onclick="console.log(this)"的東西來找出 scope 是什么 onclick 運行,並在那里進一步分配你的 runOpen 變量。

未在 React 元素上設置onclick實際上是預期的行為。

因為在評估onclick字符串時存在 XSS 安全風險。 推薦的解決方案是在html-react-parser中使用replace選項。

您也可以使用dangerouslySetInnerHTML的SetInnerHTML,這會帶來安全風險。

沙盒演示

export default function App() {
  let string =
    'This is a string containing html link to <a href="www.google.com">Google</a>';

  const re = new RegExp('<a([^>]* )href="([^"]+)"', "g");
  let replaced = string.replace(re, "<a onclick=\"alert('$2')\"");

  return (
    <div className="App">
      <p dangerouslySetInnerHTML={{__html: replaced}}></p>
      <p>{parse(string, {
        replace: domNode => {
          if (domNode.name === 'a') {
            let href = domNode.attribs.href
            domNode.attribs.onClick = () => { alert(href) }
            delete domNode.attribs.href
          }
        }
      })}</p>
    </div>
  );
}

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM