Basic knowledge: Hugoshellnpmgit

Preface

I deployed my blog on GitHub Page formerly, a platform for static site providing by GitHub. But GitHub Page has some limitation when we are using free account, like we should keep our repository public. However, I want to set my blog repository as private. Since I have some draft post on it. Another reason is I do not want to expose all my blog content to public like an open source. I did some research for some static site hosting platform. Then here comes two platform I am interest in: Deno and Vercel. And here I just wrote it down as a note about what I did, problems I faced.

Vercel Deployment

Vercel is a well known deployment platform of front end application. It is also recommended on Next.js official documentation. Vercel provides one-click deployment feature with zero configuration, but this time I want to deploy it by my own with GitHub Actions and its workflow.

I found an article about this topic, it is written by an engineer from Ukraine called Oleh Andrushko. He wrote it well, but I faced some issues. So I just write it down here as a note.

Prerequisite

  • Install Vercel CLI at local
  • Log in Vercel CLI
  • Prepare three secret keys for Vercel (Vercel account token, Vercel organization Id, project Id)

Install Vercel CLI & Sign In Vercel Account

First, we install Vercel CLI GLOBALLY with NPM:

npm i -g vercel

Then open terminal (or cmd on Windows), type vercel, it might popup login request message:

vercel
Vercel CLI 28.10.1
> > No existing credentials found. Please log in:
> Log in to Vercel (Use arrow keys)
❯ Continue with GitHub
  Continue with GitLab
  Continue with Bitbucket
  Continue with Email
  Continue with SAML Single Sign-On
  ─────────────────────────────────
  Cancel

Here we choose log in Vercel with GitHub account:

> Log in to Vercel github
> Please visit the following URL in your web browser:
> Success! GitHub authentication complete for "<Your Email when logging-in GitHub>"
? You are deploying your home directory. Do you want to continue? [y/N] n

In the end, it asks us whether to deploy home directory, actually we don’t. So choose n.

Get Necessary Secret Keys

Accessing into the project folder we want to deploy, then type vercel command again:

vercel
Vercel CLI 28.10.1
? Set up and deploy "<Your repo directory at local>"? [Y/n] y
? Which scope do you want to deploy to? "<Your GitHub name>"
? Link to existing project? [y/N] n
? What’s your project’s name? "<Your GitHub account name>"
? In which directory is your code located? ./
Auto-detected Project Settings (Hugo):
- Build Command: hugo -D --gc
- Development Command: hugo server -D -w -p $PORT
- Install Command: None
- Output Directory: `public` or `publishDir` from the `config` file
? Want to modify these settings? [y/N] n
⠸ Deploying "<Your Vercel account name>/<Your project name>"
🔗  Linked to "<Your Vercel account name>/<Your project name>" (created .vercel and added it to .gitignore)
🔍  Inspect: "<Vercel deployment project link>" [2s]
✅  Preview: "<Vercel preview deployment link>" [10s]
📝  To deploy to production (hugo-test-navy.vercel.app), run `vercel --prod`

After that, we should find a folder named .vercel in our project. The folder has two files: project.json and README.txt respectively. Open project.json we will find:

{
  "projectId": "<Vercel project Id>",
  "orgId": "<Vercel organization Id>"
}

For now, we’ve got two secret keys: Vercel organization Id and Vercel project Id.

These two keys should be keep in the save place. When we ran vercel command, there are already added in .gitignore list. Further information can be found in README.txt.

For the third secret key, we have to go to Vercel’s dashboard to create it manually. Go to Tokens > Account > Dashboard > Vercel, create one for connection between GitHub and Vercel.

Setup GitHub Actions

Setup Secret Keys

Go to our project page on GitHub, then head to actions secrets settings: repo > Settings > Secrets > Actions. Then click “New repository secret” button, adding three keys into it. (Here’s the link if you can not find it: https://github.com/<Your GitHub account>/<Your repo name>/settings/secrets/actions)

Create GitHub Actions Workflow

In project folder, creating a GitHub actions workflow file: /.github/workflows/vercel-prod.yaml (File name can be anything we like.)

Referring to Oleh’s config, modify it for my own. Here’s the whole workflow: GitHub Actions for Vercel Deployment

Override Vercel Auto-build Setting

Since we want to use GitHub actions workflow to do deployment job, we have to override Vercel built-in auto deployment feature.

Following document from vercel-action, go to project setting page on Vercel: repo > Settings > General. In “Build & Development Settings”, Framework Preset is automatically detection by default. There’s no doubt our framework is Hugo. We change it to “Other”, then click Override button on the right of “BUILD COMMAND”, keeping the input as empty. Then save it. (If Vercel prevent you to save it, adding a whitespace can fix it.) As shown below:

Troubleshooting

Output Directory Error

Error message in GitHub actions console:

Error: No Output Directory named "public" found after the Build completed. You can configure the Output Directory in your Project Settings.

According to Oleh’s workflow file, he set working-directory as public, but this got me error:

- name: Deploy to Vercel
  uses: amondnet/vercel-action@v20
  id: vercel-action
  with:
    vercel-token: ${{ secrets.VERCEL_TOKEN }}
    vercel-org-id: ${{ secrets.VERCEL_ORG_ID }}
    vercel-project-id: ${{ secrets.VERCEL_PROJECT_ID }}
    github-comment: false
    vercel-args: --prod
    working-directory: public # This line got error.

I removed this line, use root as working directory, then everything works fine.

Environment Variables Error

Error message in GitHub actions console:

Error: Input required and not supplied: env
  at getInput

Adding env variable:

- name: Update Deployment Status
  uses: bobheadxi/deployments@v1
  if: always()
  with:
    step: finish
    token: ${{ secrets.GITHUB_TOKEN }}
    status: ${{ job.status }}
    env: ${{ steps.deployment.outputs.env }} # Adding env variable.
    deployment_id: ${{ steps.deployment.outputs.deployment_id }}
    env_url: ${{ steps.vercel-action.outputs.preview-url }}

Deprecated Old Version Warning Message

Error message in GitHub actions console:

vercel-production
Node.js 12 actions are deprecated. For more information see: https://github.blog/changelog/2022-09-22-github-actions-all-actions-will-begin-running-on-node16-instead-of-node12/. Please update the following actions to use Node.js 16: amondnet/vercel-action@v20

This kind of message is just a warning, it does not block us from deployment. But we should keep in mind. Old version of Node will not work in the future. Updating the GitHub actions runner to latest version, then the warning message will disappear.

Final Thoughts

So, that’s all. We finish all deployment workflow! It will run automatically later when we push any code into main branch.

As I mentioned at the beginning, I did some research for deployment platform. Vercel and Deno are in my wishlist, and I decided to use Vercel. Vercel provides two deployment environment: production and review. So we can prepare two GitHubs Actions workflow separately for deploying develop and main branch. I set up workflows for two branches, but finally disable the preview part. As I write posts on main branch and push it to remote directly. 1 Since there’s front matter in markdown meta, deployment will ignore building markdown files with setting draft: true in markdown front matter. As it is similar between production and preview deployment workflow (difference like branch name), you can also take a look in Ukraine guy’s post if necessary.

By the way, maybe I will take a note about deploying hugo blog on Deno.

References


  1. When talking about Git flow for blogging workflow, I wrote about a short post about it: GitFlow & Blog Version Control ↩︎