
Gatsby.JS Live Previews with Drupal
If you have a decoupled Gatsby + Drupal site, then you’re probably annoyed waiting for 5-10 minutes for the build to finish - to see how your CMS changes landed on the actual website. There’s a better way - Gatsby Previews (took me a while to look into it). With Live Previews you can view your new and edited content instantly.
How to enable the Preview
There’s this neat contrib module - called “Gatsby” - https://www.drupal.org/project/gatsby
It consists of 4 different sub-modules:
- Gatsby - Improves integration with GatsbyJS including adding Live Preview and Incremental Builds;
- Gatsby Fast Builds - Enables faster Gatsby development builds by only downloading content that has changed;
- Gatsby JSON:API Extras - Adds additional enhancers when using Gatsby with JSON:API;
- Gatsby JSON:API Instant Preview and Incremental Builds - Enables a faster preview experience and incremental builds support when using JSON:API and gatsby-source-drupal.
I usually use all these, except for “Gatsby JSON:API Extras” - this one alters the GraphQL output and it doesn’t always suit me - because I already built my GraphQL queries and I don’t want to alter those.
I’ll consider that you want to enable a special sub-domain: preview, i.e. preview.nikro.me, or, preview.YOURDOMAIN.com.
Once you enable all these - head to: admin/config/services/gatsby/settings
Here you specify the following (example):
- Gatsby Preview Server URL: http://preview.YOURDOMIAN.com:8000
- Incremental Build Server Callback Hook(s): http://preview.YOURDOMIAN.com:8000/__refresh
- Entity types to send to Gatsby Preview and Build Server: go ahead and check some entities that you want.
Make it as a running Service
I assume you run your builds via some CI/CD process (i.e. CircleCI or Netlify) - so you’ll need to make sure that your Drupal’s server (the one you use for editing content) has also node installed, gatsby, and all the node packages (dependencies) - basically make sure it can run: build or develop.
Edit package.json - add this bit:
... "scripts": { ... "preview": "gatsby develop -- --host 'preview.YOURDOMAIN.com --port 8000", ... }, …
This will allow us to run ‘gatsby develop’ by running: npm run preview.
If you’re running an Ubuntu machine, that has systemd - create a file here:
/lib/systemd/system/preview_gatsby.service
Here’s a template:
[Unit] Description=preview_gatsby.js - Preview for YOUR DOMAIN. Documentation=https://YOURDOMAIN.com After=network.target [Service] Environment=NODE_PORT=8000 Environment=ENABLE_GATSBY_REFRESH_ENDPOINT=1 Type=simple User=ubuntu ExecStart=/usr/bin/npm --prefix /var/www/PATH/app run preview Restart=on-failure [Install] WantedBy=multi-user.target
Here - make sure to change the YOURDOMAIN and the PATH towards your app. The important line here is Environment=ENABLE_GATSBY_REFRESH_ENDPOINT=1 this is what will expose the /__refresh hook and enable our develop - act as a preview service.
Once you’re done with this, run: sudo service preview_gatsby start - if everything goes fine - you should see no errors. You can check for errors (?) by running: systemctl status preview_gatsby.service - green is good, red is bad ?
All good, even though we’re running the gatsby preview and the modules are installed and configured - the missing piece is nginx acting as a proxy. Create a virtual-host, in example: /etc/nginx/sites-availabe/preview.YOURDOMAIN.com with similar contents:
server { listen 80; server_name preview.YOURDOMAIN.com root /var/www; default_type application/octet-stream; sendfile on; keepalive_timeout 300; client_max_body_size 256M; fastcgi_buffers 16 16k; fastcgi_buffer_size 32k; fastcgi_read_timeout 120; location / { proxy_buffer_size 32k; proxy_buffers 8 16k; } }
And then create a symlink in /etc/nginx/sites-enabled and run a test: sudo nginx -t
Now you’ll have traffic proxied from :80 -> :8000 (preview) and things should work. Now you might be asking - why did we specify to Drupal the :8000 port? Through trial-and-error I came to this conclusion - it’s because Drupal sits on the same machine ? (in my case), so it doesn’t like to go through the nginx proxy, and triggers the hook directly.
Securing the Preview
As you might have noticed - I used http and not https, nor I have specified Gatsby Secret Key - in the configuration of the Gatsby module in Drupal.
To make things the right way - you’d want your Nginx to listen to 443 instead of 80 -> install let’s encrypt and make sure everything’s secured.
What about that secret? ? Here you can see the example - secret can be used on both sides:
- In Drupal - you specify the random string.
- In Gatsby - where you specify the Drupal source (in gatsby-config.js) - you specify the same string.
This adds a layer of protection for previews between the two.
Test and have fun!
I add / edit content once a month or so - and when I do, I start the preview service, get my stuff done and then shut it down (for security purposes, greener planet and all that) - I recommend you do the same ?
Have fun!
💡 Inspired by this article?
If you found this article helpful and want to discuss your specific needs, I'd love to help! Whether you need personal guidance or are looking for professional services for your business, I'm here to assist.
Comments:
Feel free to ask any question / or share any suggestion!