DEV Community

chantastic
chantastic

Posted on • Edited on • Originally published at chan.dev

Schedule Netlify Builds with GitHub Actions, Cron, and Webhooks

Instructions

Add this GitHub Action to your repo at
.github/workflows/schedule-netlify-build.yml

# .github/workflows/schedule-netlify-build.yml

name: Schedule Netlify Build
on:
  schedule:
    # Customize schedule expression at crontab.guru
    # This one runs at 800 UTC daily
    - cron: "0 8 * * *"
jobs:
  build:
    name: Call Netlify build hook
    runs-on: ubuntu-latest
    steps:
      - name: Curl request
        run: curl -X POST -d {} #YOUR_BUILD_HOOK_URL#
Enter fullscreen mode Exit fullscreen mode

Tailor your cron schedule

Determine a build schedule and use crontab.guru to describe it as a cron schedule expression.

-    # This one runs at 800 UTC daily
-   - cron: "0 8 * * *"
+    # This one runs every 6 hours
+   - cron: "* */6 * * *"
Enter fullscreen mode Exit fullscreen mode

Generate a Netlify build hook

Netlify build hooks are webhooks with one function: re-build your site when called. Any POST request to your Netlify build hook triggers a build.

Generate a new build hook here:
Site settings > Build & deploy > Continuous deployment > Build hooks.

Settings path: Site settings > Build & deploy > Continuous deployment > Build hooks
Image from Netlify build hooks documentation

You have to name your hook. The name doesn't make much difference as long as it's unique and descriptive to you.

Paste your build hook into the GitHub Action

-        run: curl -X POST -d {} #YOUR_BUILD_HOOK_URL#
+        run: curl -X POST -d {} https://api.netlify.com/build_hooks/#GENERATED_BUILD_HOOK_URL
Enter fullscreen mode Exit fullscreen mode

Push!

Push your new workflow up to your repository and watch the Actions tab. You'll seeing scheduled jobs show up, according to your schedule.

Here's what to expect: https://github.com/LunchDevCommunity/community-calendar/actions

Extra credit

Get fancy and ensure that nobody spams your build hook with a GitHub Action environment variables.

A Story

Dynamic Site; Static Builds

Over at lunch.dev, we've built a calendar of events in Eleventy (a slick static site generator).

Events are listed under Upcoming and Past event headings based on their date. Because Eleventy generates static sites, that deterimation happens at build time.

If we want to keep data fresh, we have to manually re-build the site at least once per day.

Using Netlify build hooks, we can automate those builds on a schedule!

There are plenty of services that will run a cron job. What I like about a GitHub Actions based solution is that everything is kept in the repo. The source can be maintained and documented with the rest of the project!

Resources

Watch me and the lunch.dev crew struggle thru this the first time

Top comments (16)

Collapse
 
michaelcurrin profile image
Michael Currin • Edited

The default for POST is to send form field data rather than JSON - so you can do -d 'foo=bar fizz=buzz.

Which means you can simplify to '' payload. Plus POST is implied.

Example here using simpler syntax and the env variable secret you mentioned

run: curl -d '' {{ NETLIFY_BUILD_HOOK }}
Enter fullscreen mode Exit fullscreen mode
Collapse
 
chantastic profile image
chantastic

thanks!
when i generate the build hook in Netlify, it includes the whole curl command. I left it as provided to prevent confusion but you are correct, the simplified version would work all the same

Collapse
 
michaelcurrin profile image
Michael Currin

Ah ok makes sense

Collapse
 
michaelcurrin profile image
Michael Currin

For interest, how to expand on the Netlify hook:

You could add workflow_dispatch under on, then you get run now kind of button. Which is similar to a button that already exists in Netlify.

If you have another service that supports looks, you could use the URL there instead of GH Actions.

E.g. maybe you build or find a service that can trigger a web hook when content changes. Like a new blog post on a blog site, a new commit in your repo which contains markdown web pages, or a new tweet is made. At the danger that high activity will cause rapid rebuilds on Netlify. If you are going to pull in fast changing data then one is better off with pulling in content on the frontend like Instagram, or a server side HTML with PHP/Python rather than static site.

Another easy trigger to setup would be with IFTT.com - you can set it up to listen to a ton of events like a tweet is created or your phone enters a certain GPS location, then cause an event like send an email or add to a Google Spreadsheet or ping any given URL. Such as the Netlify one. I mean you can even use a thermometer or motion sensor in your smart home IoT setup to trigger an event if you really want.

Collapse
 
chantastic profile image
chantastic

yeah! it's really interesting to think of the possibilities. how we might integrate it with some of our social accounts and trigger updates (say, after a stream ends) would be very cool.

Collapse
 
michaelcurrin profile image
Michael Currin

Thanks. I have be thinking about this idea for a long time but this is the first time I've seen someone do it.

Collapse
 
ajcwebdev profile image
ajcwebdev

That's great to hear, when Michael mentioned he was trying to do this I thought, "How can this be a thing that hasn't been done a million times?" Yet we found very little prior art on it.

Collapse
 
michaelcurrin profile image
Michael Currin

The case is you have external content driving your Netlify site. Maybe not many people need that.

You can use a local cron job assuming your laptop is always connected to the internet and awake.

GH Actions is the obvious choice for me, if one knows it exists and it supports schedule.

Maybe there are some other free services which do the same. You could use Datadog or some other monitoring platform even to hit your private URL daily.

Thread Thread
 
ajcwebdev profile image
ajcwebdev • Edited

I know of two projects that are aimed at providing a wide range of different background job and scheduling features that I think would include this kind of use case. I haven't used either but I know the creators of each from their work on Redwood (Rob Cameron) and Blitz (Simon Knott) respectively.

Repeater

Described as being a Job Queue as a Service that is aimed at Background job processing for the Jamstack.

Common uses include:

  • Send emails & notifications
  • Check for heartbeat
  • Image processing
  • Data transformations
  • PDF generation

Quirrel

Described as job queueing for serverless.

Jobs include:

  • Delayed Jobs
  • Fanout Jobs
  • Recurring Jobs
  • Cron Jobs
Collapse
 
chantastic profile image
chantastic

thanks for reading it!
I find GitHub Actions to be a great place for this. I love that anyone in the project can edit and submit a PR to change the schedule.

Collapse
 
michaelcurrin profile image
Michael Currin

BTW you link to Environment variables doc which is about setting and use shell variables in a build.

Rather link to the secrets doc for setting and using secrets.

Collapse
 
chantastic profile image
chantastic

omg. thank you for the proper link!

Collapse
 
michaelcurrin profile image
Michael Currin

PS your article title would be better as Cron, not Chron. Though the body is fine.

Collapse
 
chantastic profile image
chantastic

thanks! updated 🙏

Collapse
 
michaelcurrin profile image
Michael Currin

I've taken your file as inspiration and done my own guide here. I've linked back to your post.

michaelcurrin.github.io/code-cookb...

Collapse
 
chantastic profile image
chantastic

Yes! Love that you took it and made it your own.
We found maybe two articles on the subject. So the more the merrier :)