I converted a Jekyll site into a Gatsby one: see what happened

- 7 min

Continuing my learning path during this quarantine, I focused my efforts in converting a site I made previously in Jekyll to a Gatsby one. After I started to get familiar with the "React way" of doing things, I decided to test what I learned in a real project, with no help of tutorials. In the "do it yourself" style, trying to solve the issues that came up by myself.

But what is Jekyll?

Jekyll homepag Jekyll homepage

If you ended up in this article and don't know what it is, no problems. Jekyll is a static site generator1 made in Ruby. These ones make a content created with another programming language be compiled into the old and famous HTML and CSS, in a way it could be hosted in any server.

In Jekyll's case, Markdown2 is used to create the pages content and HTML with a special markup called Liquid3, to create iteration and ease the modularization of the pages. Thus, it's not necessary to repeat HTML in all pages.

It works like a Wordpress theme, without the nedd to configure a database in the server.

And this Gatsby guy?

Gatsby homepage Gatsby homepage

As stated by its own creators: is a free and open source framework based on React that helps developers build blazing fast websites and apps.

The result of a site built with it follows the same philosophy of the static site generators. However, it makes possible using React to render in a native way, opening up many choices. This, and all the automations achieved with the help of plugins. The library of plugins is huge: from Wordpress integration to Progressive Web Apps (PWAs)4 creation.

Differences and features


For a person coming from HTML, Jekyll is much more friendly. Page template are just .html files. See the example code below. The strange markup is Liquid stuff.

layout: default

<h1 class="archive-title">Articles</h1>

<div class="blog-content">
  <section class="posts-list">
    {% for post in paginator.posts %}
    <article class="post" data-type="{{ post.layout }}">
      <div class="details columns">
        <div class="text">
          <a class="post-link" href="{{ post.url | prepend: site.baseurl }}">
            <h4>{{ post.title }}</h4>
            <small>{{ | date: '%d/%m/%Y' }}</small>
          <p>{{ post.excerpt | strip_html }}</p>
    {% endfor %}

  {% include pagination.html %}

In Gatsby, the things are completely different. Page templates are React components, written in JSX, a blend between JavaScript and HTML. Notice the stark difference in the code:

import React from "react"
import { Link } from "gatsby"
import Layout from "../components/Layout"
import Pagination from "../components/Pagination"

export default function PostList({ postList }) {
  return (
      <h1 className="archive-title">Articles</h1>
      <div className="blog-content">
        <section className="posts-list">
          { => {
            return (
              <article className="post">
                <div className="details columns">
                  <div className="text">
                    <Link className="post-link" to={post.url}>
                    <p dangerouslySetInnerHTML={{ __html: post.excerpt }} />
        <Pagination />

The code above is equivalent to the example shown in Jekyll. In my real code, I O código acima é o equivalente ao mostrado anteriormente no Jekyll. In the code I remade, I modularized more: article became another component. Seeing JSX, strangeness is inevitable. I myself always had something against leaving everything to JavaScript, but it is a question of getting used to it.


Both accept CSS. Jekyll accept Sass by default. In Gatsby, there is the

Both accept CSS. Jekyll accepts Sass by default. In Gatsby, there is the possibility to use Sass with the help of a plugin. In addition, you can modularize the styles for each component, that is, the classes are only valid for that part, not affecting other areas of the project. You can do this using the native CSS Modules natively or the React Styled Components, which requires a plugin. To make it clearer, CSS modules look like this:

Nothing changes in the CSS, just the file name, which must end with ".module.css".

.title {
  font-size: 3em
  color: #036

In the component, just import the style, which must be in the same folder as the component, and pass the style in the className as an object notation between braces.

import React from "react"
import titleStyles from "./title.module.css"

export default function Title({ text }) {
  return <h1 className={titleStyles.title}>{text}</h1>


In addition to enabling the use of other modules, like any modern JavaScript application, Gatsby has many features and a large community, with plugins for almost everything. They are all in JavaScript and can be installed by Node JS package managers, such as NPM and Yarn.

For example: to create a PWA, just install a plugin. It creates icons in different sizes based on an image, creates manifest.json and caches what you define in the configuration. In Jekyll, although there are plugins for this, they have little documentation.

Page preload

Another thing that I found very interesting is that Gatsby loads data from a page before you click on the link. That's why the site turns out to be faster, as there is no need to wait for it to load after clicking.

Hot reload

Gatsby shows the changes you make in real time during development. It is not necessary to press F5 for each change.


Both have Markdown support. In Jekyll the support comes by default without any configuration needed. In Gatsby, you need to install a plugin and configure the creation of the pages. Despite this initial complexity, you end up having more freedom to customize the features you want.


How Gatsby works How Gatsby works

Gatsby comes with support for GraphQL, which is a language for querying and manipulating data. Several sources can be used: APIs, Wordpress, Markdown files, databases, JSON and even CSVs.

With the help of plugins, data in these files are made available for manipulation by the GraphQL console. The idea is scary at first, but once you understand how it works, the fear vanishes. It is not as hard as it looks.

The interesting thing about this language is that we can convert dates to the desired format if informed in the query, without having to do the conversion in the JavaScript code.

import React from "react"
import { graphql, useStaticQuery, Link } from "gatsby"

const data = useStaticQuery(graphql`
  query {
    allMarkdownRemark(limit: 100, sort: { fields: id, order: DESC }) {
      edges {
        node {
          frontmatter {
            date(locale: "en-US", fromNow: true)

In the example, the date(locale: "en-US", fromNow: true) is going to display the date as "2 days ago".

Qual devo usar?

Use Jekyll if you are not comfortable with JavaScript. That's it. It is a powerful tool and I will continue to use it for simpler sites.

But in Jekyll site, while easier to create, it is more complicated to extend. If you need a feature where there is not yet a plugin, it will have to be developed in Ruby. The probability of not finding a JavaScript plugin is much lower, and their integration within the Gatsby environment is much more natural.

In short, use Gatsby if you like React / JavaScript and need more advanced features on your site.

Sobre a experiência

This challenge was great for me, because I was able to deal with the concepts that were still a bit fuzzy for me in React, like the use of React Hooks, and even learn some GraphQL, which I was completely unaware of.

If you made it this far, congratulations! The article turned out to be longer than I thought! In fact, the site I converted is the one where you read this text now: this blog was made in Jekyll and I converted it to Gatsby.

I will still write more about my learning process, but I will stop here, because the article got huge!

Leave your suggestion or criticism in the comments below!


  1. Static sites: basically, sites made only in HTML and CSS, that do not fetch data when it is opened. I wrote an article about it.
  2. Markdown: a markup language for creating content. However, this is much simpler and does not use HTML tags, as it focuses on readability.
  3. Liquid: markup that enables the iteration of variables and the inclusion of files and logic on a page.
  4. Progressive Web Apps (PWAs): applications developed in HTML, CSS and JavaScript that can be added as apps on phones. They have features such as notifications, offline use and hardware access. If well done, the app can even replace a native one, speed up development and avoid the bureaucracy of current app stores.