CI/CD with Github Actions

Github Actions let us create custom software development life cycle (SDLC) workflows directly in your GitHub repository. With GitHub Actions you can build end-to-end continuous integration (CI) and continuous deployment (CD) capabilities directly in your repository.

#About Github Actions GitHub Actions help you automate your software development workflows in the same place you store code and collaborate on pull requests and issues. You can write individual tasks, called actions, and combine them to create a custom workflow. Workflows are custom automated processes that you can set up in your repository to build, test, package, release, or deploy any code project on GitHub.

Workflows run in Linux, macOS, Windows, and containers on GitHub-hosted servers. You can create workflows using actions defined in your repository, open source actions in a public repository on GitHub, or a published Docker container image.

#Discovering actions in the Github community GitHub Marketplace is a central location for you to find, share, and use actions built by the GitHub community.

You can also customize your project with open source actions shared in public repositories on GitHub and use actions built by GitHub in the actions organization.

#Use Case Github Actions are in my view very flexible and you can design your workflows in many different ways and when testing it out I decided to test two common use cases:

  • Run test when you push code to your Github repo master branch.
  • Publish new versions of your package to NPM

##Run test when pushing code to master branch The first test I did was to create an action that should test my code when I push it to the master branch of my Github repository. An action must be created in a directory named .github in your own Github repo as an .yml file.

The action below is named Node CI, it is triggered on the push event on the master branch, it runs one job called build, the build job uses a matrix strategy - meaning it will build for different versions of Node.js in this case, the build job has several steps, check out code, set up a Node.js environment and run npm commands such as ci, install, build and test.

# Job name is Node CI
name: Node CI

# This workflow is triggered on pushes to the master repository.
on:
  push:
    branches:
      - master  # Push events on master branch

# We define our jobs
jobs:

  # Build job
  build:

    # This job runs on Linux
    runs-on: ubuntu-latest

    # Runs the jobs for Node.js 12.x and 10.x
    strategy:
      matrix:
        node-version: [12.x, 10.x]

    # Steps for the build job
    steps:

      # This step check outs code
      - name: Checkout code
        uses: actions/checkout@v1

      # This step sets up Node.js according to the strategy chosen
      - name: Set up Node.js ${{ matrix.node-version }}
        uses: actions/setup-node@v1
        with:
          node-version: ${{ matrix.node-version }}

      # This step runs ci, install packages, build app if available and runs test
      - name: Run CI, install, build and test
        run: |
          npm ci
          npm install
          npm run build --if-present
          npm test
        env:
          CI: true

This action works perfectly fine every time I pushes code to my master branch in my remote repo located at Github.

##Publish releases to NPM The second test I did, publish a package to NPM on release, was little trickier since I got some errors indicating access failure to NPM. However, the solution was to log in at NPM, create an access token and in my repo, go to settings and add the NPM token to the repo as a secret. A repo secret is available in Github Actions via ${{secrets.NPM_TOKEN}}

# Job name is Publish to NPM
name: Publish to NPM

# This workflow is triggered on each release event, the types: [published] 
# is required here since releases could also be updated or deleted, we only 
# want to publish to npm when a new release is created (published).
on:
  release:
    types: [published]

# We define our jobs
jobs:

  # Build job
  build:

    # This job runs on Linux
    runs-on: ubuntu-latest

    # Steps for the build job
    steps:

      # This step check outs code
      - name: Checkout code
        uses: actions/checkout@v1

      # This step sets up Node.js
      - name: Set up Node.js
        uses: actions/setup-node@v1
        with:
          node-version: 12
          registry-url: https://registry.npmjs.org/

      # Install 
      - run: npm install

      # Publish to NPM
      - run: npm publish --access public
        env:
          NODE_AUTH_TOKEN: ${{secrets.NPM_TOKEN}}

#Summary I'm surprised how easy it was to use Github Actions and there are also many actions available in the Github Marketplace you can use to build your CI/CD solutions. For example, there are templates to integrate with different cloud providers such as AWS, Azure, etc.


Published: 2019-12-15
Author: Henrik Grönvall
Henrik Grönvall
Copyright © 2022 Henrik Grönvall Consulting AB