A Cost-effective Way Of Hosting A Personal Website In The Cloud Using WordPress + Gatsby
Experiments
A Subject of the Experiment
When I say the cost-effective way of the hosting a website, I don’t mean only the money side of hosting. To me, it doesn’t make sense if I have to put a lot of time and effort to maintain the site, even if I can host it for free. So when I was thinking about building a website to put my notes in, there was a couple of things that I knew I have to take into the account.
Serverless
Maintenance of the website shouldn’t be my abundance. From my past experiences, I knew that it’s a pain in the but to maintain a blog, to keep its plugins and versions up to date. There gonna be security patches and updates and you have to do those things almost instantly otherwise, your resource gonna be vulnerable. It was obvious that I should take “serverless” approach.
So WordPress.com was the logical place to start. I would be responsible neither to maintain server support nor updates of the CMS. And because I was already familiar with the WordPress, it meant that there won’t be any learning curve either.
Customization
But when it comes to customizing the website, wordpress.com give little to none control over the blog. I would have some sort of access to customize the blog if I’d choose a $8/month plan. But this option didn’t appeal to me too much. Not because it’s too expensive, but mainly because to be able to customize the site only from the WordPress Admin, and using just CSS, seemed bit limiting to me.
Although I wanted something minimalist, still I wanted to have total control over the website.
Stack
When it came to the choosing the stack, again I wanted it is not to be time-consuming. Which meant, I wanted to build with the stack that I was already familiar with before. I already knew about the static website concept, but never tried it myself before. Few times I’ve read about the Jekyll, and how to use it, but it never appealed to me. The main reason was, it didn’t felt intuitive to me to commit the blog post to the git. When I run this little experiments, I always try to think if it has real-world application. Meaning, I never believed that I’m gonna be able to find a blogger or content manager that easily which going to adapt to the process writing and formatting posts with the markdown and push it to the git as a commit.
Then one day I’ve stumbled upon on Gatsby. The main attraction point for me was to be able to have that many data sources. And of course, React. That meant I easily could to build a website using JAMStack with multitier architecture.
So architecture I was thinking was something like this:
- Bitbucket.org will serve as a git, to store the source code of the project.
- WordPress.com will serve as an API for the website
- Netlify.com going to handle build process and will serve as a hosting as well
- Cloudflare.com will handle caching and DNS management. And as a bonus website going to get a free SSL
- And all of these are going to cost $0
So I started to build
This architecture allows me to keep development and publishing environment separately. Editor or publisher works in the WordPress admin and he/she does not have to commit or push the content changes. And with this structure, it’s possible to update the content even from a smartphone.
As you can see from the visual above, Gatsby is one of the most crucial parts of the architecture. Gatsby is the glue that keeps together the whole scheme. Because of it, I can easily get the data from WordPress.com API and build customizable views for posts and pages. And because Gatsby uses GraphQL as a query language, it’s even more fun to work with it.
Gatsby’s official site covers all the steps well enough to know how to start, and where to look. So I’m not gonna copy and paste those things here. Instead, I encourage you to go and check the docs yourself: https://www.gatsbyjs.org/docs/
And because of I myself guilty of doing so, I highly recommend checking the community starters before starting the reinventing the wheel: https://www.gatsbyjs.org/docs/gatsby-starters/
But because tutorials usually show how to integrate with self-hosted WordPress sites, I’m gonna put code piece below to save a couple of seconds of your life.
module.exports = { ... plugins: [ ..., { resolve: `gatsby-source-wordpress`, options: { // your WordPress source baseUrl: `your.wordpress.com`, protocol: `https`, // is it hosted on wordpress.com, or self-hosted? hostingWPCOM: true, // does your site use the Advanced Custom Fields Plugin? useACF: false, auth: { // You'll get Client Secret and Client ID from https://developer.wordpress.com/apps/ wpcom_app_clientSecret: 'client_secret_goes_here', wpcom_app_clientId: 'client_id_goes_here', // Your WordPress.com user credentials wpcom_user: '[email protected]', wpcom_pass: 'veryverystrongpassword', }, verboseOutput: true, } }, ..., ] }
The rest is pretty straightforward. You connect your Bitbucket or Github account with your Netlify.com account and every time when you push a new code, Netlify builds it and hosts it for you: https://www.netlify.com/docs/continuous-deployment/
Now, it’s time to set up a webhook, to notify Netlify.com when we publish new content. You can do this from your WP Admin dashboard. You can get to this dashboard by adding /wp-admin
to the end of your site’s URL (e.g.: your.wordpress.com/wp-admin). You can read detailed instructions on how to set up webhook in here: https://en.support.wordpress.com/webhooks/
And here you can learn how to get URL for incoming hooks: https://www.netlify.com/docs/webhooks/
Now we set up the continuous deployment process, it’s time to automate one more thing. As you can see from the scheme above, we rely on Cloudflare for our CDN. Which means Cloudflare going to cache static files to decrease the latency of user requests. And because our site built just with static files, Cloudflare is gonna cache our whole site. And we have to somehow clear that cache after every successful deployment.
Once again, Netlify hooks come to rescue. This time outgoing webhook. Set up a webhook that visits the Cloudflare API:
https://www.cloudflare.com/api_json.html?a=fpurge_ts&tkn=<TOKEN>&email=<ACCOUNT_EMAIL>&z=<DOMAIN2PURGE.COM>&v=1
Where <TOKEN> is the Cloudflare Global API Key, that you can find instructions on how to find that key here: https://support.cloudflare.com/hc/en-us/articles/200167836-Where-do-I-find-my-Cloudflare-API-key-
That’s it. Now flow fully automated, and everything works as intended.
Experiment succeeded.
Links: