How to display markdown frontmatter as HTML in Gatsby

Viewed 575

my index-page displays blurbs with image and text. But i cant get the text to be formated as HTML. Im using the markdown-widget with Netlify CMS and want linebreak to work when spacing content in the admin view. ive tried use dangerouslySetInnerHTML={item.text} aswell without any luck.

item is just a mapping of all blurbs.

<p> {item.text} </p>

graphql:

markdownRemark(frontmatter: { templateKey: { eq: "index-page" } }) {
      frontmatter {
        intro {
          blurbs {
            image {
              childImageSharp {
                fluid(maxWidth: 2048, quality: 100) {
                  ...GatsbyImageSharpFluid
                }
              }
            }
            heading
            text
          }
          heading
          description
        }
      }
    }
  }

the label in config.yml:

- {label: "Intro", name: "intro", widget: "object", fields: [{label: "Heading", name: "heading", widget: "string"}, {label: "Description", name: "description", widget: text}, {label: Blurbs, name: blurbs, widget: "list", fields: [{label: "Image", name: "image", widget: "image"}, {label: "Rubrik", name: "heading", widget: "string"}, {label: "Text", name: "text", widget: "markdown"}]}]}

the Index.md i want to read from (i guess this works, due to the fact that i get the data to display, just not in html form)

  blurbs:
    - image: /img/img1.jpg
      heading: heading one
      text: >-
        This is the content i want in HTML
    
    - image: /img/img2.jpg
      heading: heading two
      text: >-
        This is also the content i want in HTML
       
        And this should give me a linebreak
2 Answers

You can acchieve this using the gatsby-transformer-remark-frontmatter plugin.

Install the plugin and add it to your gatsby-config.js:

$ npm install gatsby-transformer-remark-frontmatter
// in your gatsby-config.js
plugins: [
  'gatsby-transformer-remark',
  'gatsby-transformer-remark-frontmatter'
]

To tell Gatsby that the text field within each blurb contains markdown and that you want the string to be transformed to html, you need to add a @md directive to your schema. To do that, add the following code to the gatsby-node.js file.

// in your gatsby-node.js

exports.createSchemaCustomization = ({ actions }) => {
  const {createTypes} = actions
  const typeDefs = `
    type MarkdownRemark implements Node {
      frontmatter: Frontmatter
    }

    type Frontmatter {
      intro: Intro
    }

    type Intro {
      blurbs: [Blurb]
    }

    type Blurb {
      text: String @md
    }
  `
  createTypes(typeDefs)
}

Now the text field of the blurbs will have a special html field that you can include in your query:

markdownRemark(frontmatter: { templateKey: { eq: "index-page" } }) {
      frontmatter {
        intro {
          blurbs {
            text {
              html
            }
          }
        }
      }
    }
  }

Lastly, in your component, you should be able to loop over the blurbs and render the html like so:

...
<div dangerouslySetInnerHTML={{ __html: blurb.text.html }} />

Assuming that everything's properly set, as it seems.

By default, there's a html property right inside frontmatter:

markdownRemark(frontmatter: { templateKey: { eq: "index-page" } }) {
      frontmatter {
        html
        intro {
          blurbs {
            image {
              childImageSharp {
                fluid(maxWidth: 2048, quality: 100) {
                  ...GatsbyImageSharpFluid
                }
              }
            }
            heading
            text
          }
        }
      }
    }
  }

Note: test your query at localhost:8000/___graphql

Once you have queried it, just display it as you did, nesting to the correct property:

dangerouslySetInnerHTML={html}

You can check for a full tutorial at https://www.gatsbyjs.com/docs/how-to/sourcing-data/sourcing-from-netlify-cms/

Related