Technology
The Nextform Team
December 8, 2021

Syntax Highlighting with Highlight.js and Next.js

Syntax Highlighting with Highlight.js and Next.js

If you publish content with code snippets, it can be helpful to provide syntax highlighting to your readers (and, let’s be honest, it just looks cool). In this post, we are going to share our own implementation of Highlight.js within our front-end JavaScript framework, Next.js.

Highlight.js is a JavaScript library for syntax highlighting. It works in the browser and on the server. It can highlight a wide variety of programming languages, has no dependencies, and has automatic language detection. I can also be incredibly lightweight if you're careful about how you import it, since it allows you to selectively import the features you need.

Next.js is a popular front-end JavaScript framework that provides production-ready features and enhancements on top of React. One of the key benefits of Next.js is server-side rendering, which is great for SEO and user experience. Server-side rendering (SSR) can also add a layer of complexity when implementing a library like Highlight.js, as you must plan out your implementation to avoid breaking the SSR.

Highlight.js provides a lot of helpful documentation, however, it is primarily focused on the client-side implementation. There are other articles out there that explain how to do client-side rendering with Highlight.js and Next.js specifically, but we did not find any that demonstrated a good server-side implementation, so we set out to figure it out for ourselves, and we'd like to share our implementation with the world.

Installing and Importing Highlight.js

Install Highlight.js in your Next.js project with npm install highlight.js or yarn add highlight.js. To keep the footprint small, you can load just the core module and then add the languages you need. You must also register the languages you've imported. Here we are just using JavaScript:

// import Highlight.js and just the languages you need
import hljs from 'highlight.js/lib/core'
import javascript from 'highlight.js/lib/languages/javascript'
hljs.registerLanguage('javascript', javascript)

Creating the React Component

Now let’s create a React component that renders our code, but before we do, take note that we’re using the dangerouslySetInnerHTML attribute, so named because you should think hard about what kind of content you’re passing to it. It is safe to use static content, which is what we’re doing here.

// this should only be used to display static content (hence the "dangerously")
export default function CodeBlock() {
  const myCode = "console.log('Hello World!')"
  const myHtml = hljs.highlight(myCode, { language: 'javascript' }).value
  return (
    <pre>
      <code dangerouslySetInnerHTML={{ __html: myHtml }} />
    </pre>
  )
}

The hljs.highlight() method generates an HTML string. This differs from the more common implementation where you might see the hljs.highlightAll() method called, which scans the page on the client side and updates it with syntax highlighting. Since hljs.highlightAll() runs client-side, it can unintentionally spill out into other parts of your page and apply highlighting where you don't want it. Using hljs.highlight() and then setting the HTML ourselves ensures that the highlighting is confined to our one component.

Bonus: Super Simple JSON Highlighting

We created an alternative version of this component that chews up JavaScript objects and spits out fully valid, sytax-highlighted JSON objects. It's similar to the above, with a few minor modificaitons:

import hljs from 'highlight.js/lib/core'
import json from 'highlight.js/lib/languages/json'
hljs.registerLanguage('json', json)

// accepts a javascript object, which it will display as JSON
export default function JsonBlock() {
  const myObject = { example: 'object' }
  const myJson = JSON.stringify(myObject, null, 2)
  const myHtml = hljs.highlight(myJson, { language: 'json' }).value
  return (
    <pre>
      <code dangerouslySetInnerHTML={{ __html: myHtml }} />
    </pre>
  )
}

We hope you find this tutorial helpful! At Nextform, we love software that makes our lives easier. That's why we created an API that helps businesses collect and track standard forms like W-9 and W-8BEN. This is a great service for SaaS businesses that need to collect these forms as part of a streamlined onboarding process. If that's you, sign up for a free account and don't hesitate to contact us with any questions or feature requests.