1

I'm new to reactjs and working on a project that is pushing json data to the template.

json structure

"description" : "Some text with a <a href=\"/de/datenschutz\">link</a> and another <a href=\"/de/cookie-richtlinie\">link</a>",

I propose using the following on the template

<p className='paragraph-margin-bottom-10 text--font-size-14 paragraph--justified' dangerouslySetInnerHTML={{ __html: lang.privacy[0].description }} />

but in terms of the output - I would maybe need to append a set of classes to ALL links. What is the best practice for this

so the links render with the following

<a class="text--font-size-14 hyperlink-primary" href="#">link</a>
The Old County
  • 89
  • 13
  • 59
  • 129

1 Answers1

0

I can imagine that many people will not agree with me. You can actually do this. But you shouldn't. It is bad enough that you want to use dangerouslySetInnerHTML. It is possible to parse html but there are many edge cases that you would need to handle.

Either tell your backend that they should return the links with proper classes or target the links inside the description directly with css.

See some similar question like: Using regular expressions to parse HTML: why not? Using regular expressions to parse HTML: why not?

This is how I would do it. I will write the regex later if you run into some problems. I don't have much time to spare right now. Hope it will help. :)

import React from 'react';
import { render } from 'react-dom';


const htmlFromApi = 'some html from API'

const attachClassesToLinks = (htmlWithLinks) => {
  // do something special
  return htmlWithLinks
}

const App = () => (
  <div>
    <h1>My Component</h1>
    <p dangerouslySetInnerHTML={{ __html: attachClassesToLinks(htmlFromApi) }} />
  </div>
);

render(<App />, document.getElementById('root'));
Michal
  • 4,952
  • 8
  • 30
  • 63
  • well using regex seems more bespoke for something like this – The Old County Jun 06 '17 at 10:09
  • In the end it depends on your needs. If you can be sure that all links that you will get from the API will not have class atribute for example. Then it will be easy. It will get much harder though if you will need to find out whether the link has class atribute. If the class atribute has any value in it. And so on. :) – Michal Jun 06 '17 at 10:14
  • if I were to use a regular expression on this -- how would I go about it -- do a componentDidMount? – The Old County Jun 06 '17 at 11:19
  • I would probably create function that would parse the html (the variable) that you are using in dangerouslySetInnerHTML. Component does not need to know anything about classess of those links unless you plan to change them using component state or something. – Michal Jun 06 '17 at 11:50
  • 1
    const attachClassesToLinks = (htmlWithLinks) => { // do something special return htmlWithLinks.replace(/ – The Old County Jun 06 '17 at 13:50
  • 1
    what do you think - its a bit borky – The Old County Jun 06 '17 at 13:50
  • Looks good enough. Change `class` to `className` `a` is jsx component. But you have to be sure that all the links that you get from the API don't have className attribute. – Michal Jun 06 '17 at 15:56
  • When I do that -- it just spews out raw html - it doesnt get rendered on the fly properly – The Old County Jun 06 '17 at 16:06
  • I mean what I'm trying to resolve here -- is a clean way of pushing html fragment data from a single tag like description --- then applying any styles to that markup -- so at least everything is malleable on a template level – The Old County Jun 06 '17 at 16:08
  • I am sorry but no. – Michal Jun 06 '17 at 23:19
  • what do you mean? – The Old County Jun 07 '17 at 05:03