Having an action stop gracefully when a condition is not met, but not fail

I am new to actions.

I have an action that will start a node instance and build out javascript files when a PR is merged to master.

But sometimes there will be merges with no files to build, so I would like the action to check for files, and if there are none, just exit gracefully.

Right now I am doing this by setting an environment variable that every subsequent step checks, and it seems like there should be a better way. Anyone can tell me how I can stop all subsequent steps/jobs - is there some exit code that will stop everything but not throw an error?

name: Build to Site

on:
  push:
    branches:
      - master

jobs:
  job1:
    runs-on: macos-latest
    steps:
      - name: Checkout code
        uses: actions/checkout@v2
      - name: Check files
        id: check_js_step
        run: echo "::set-env name=HAS_FILES::$(find js -maxdepth 1 -type f)"
      - name: Proceed with build?
        if: ${{ env.HAS_FILES == '' }}
        run: echo "::set-env name=YES_BUILD::1"

  job2:
    needs: [job1]
    runs-on: macos-latest

    strategy:
      matrix:
        node-version: [12.x]

    steps:
    - name: Use Node.js ${{ matrix.node-version }}
      if: ${{ env.YES_BUILD == 1 }}
      uses: actions/setup-node@v1
      with:
        node-version: ${{ matrix.node-version }}
    - run: yarn install
      if: ${{ env.YES_BUILD == 1 }}
    - name: Build project
      if: ${{ env.YES_BUILD == 1 }}
      run: yarn run build_js
    - name: Move and name directory
      if: ${{ env.YES_BUILD == 1 }}
      run: cp -r build current
2 Likes

Hi @unjust ,

Thanks for being here!

Typically we will use ‘continue-on-error’ or expand command with ‘exit 0’ to skip the fail step, but the next step will continue to be executed.

The rule is that if prior step succeeds, the next step will be started. Hence, if you don’t want to throw an error, I’m afraid you have to use ‘if’ expression to skip your build steps accordingly.

Thanks.

So is it correct to assume that a job can only fail or succeed, there’s no way to say “OK, we’re done here, we can’t proceed, but don’t worry, it’s not your fault (or mine)”

You could probably create an output (rather than environment variable) in job1 and then a job-level if (see jobs.<job_id>.if ) to run job2 or not depending on that output.

1 Like