我正在用Github动作构建Docker图像,并想用分支名称标记图像。

我找到了GITHUB_REF变量,但它导致了refs/heads/feature-branch-1,我只需要feature-branch-1。


当前回答

你可以使用https://github.com/rlespinasse/github-slug-action

# Just add this  => 
- name: Inject slug/short variables
  uses: rlespinasse/github-slug-action@v3.x



# And you get this  => 
- name: Print slug/short variables
  run: |
    echo "Slug variables"
    echo " - ${{ env.GITHUB_REF_SLUG }}"    
    echo " - ${{ env.GITHUB_HEAD_REF_SLUG }}"
    echo " - ${{ env.GITHUB_BASE_REF_SLUG }}"
    echo " - ${{ env.GITHUB_REPOSITORY_SLUG }}"
    # output e.g. : master feat-new-feature v1.0.0 product-1.0.0-rc.2 new-awesome-product
    echo "Slug URL variables"
    echo " - ${{ env.GITHUB_REF_SLUG_URL }}"
    echo " - ${{ env.GITHUB_HEAD_REF_SLUG_URL }}"
    echo " - ${{ env.GITHUB_BASE_REF_SLUG_URL }}"
    echo " - ${{ env.GITHUB_REPOSITORY_SLUG_URL }}"
    # output e.g. : master feat-new-feature v1-0-0 product-1-0-0-rc-2 new-awesome-product
    echo "Short SHA variables"
    echo " - ${{ env.GITHUB_SHA_SHORT }}"
    # output e.g. : ffac537e

其他回答

下面是一个适用于push和pull_request事件的完整工作流

name: whichBranch
on: [pull_request, push]

jobs:
  which_branch:
    runs-on: ubuntu-latest
    steps:
      - name: Extract branch name on push
        if: github.event_name != 'pull_request'
        shell: bash
        run: echo "::set-env name=BRANCH_NAME::$(echo ${GITHUB_REF#refs/heads/})"
        id: extract_branch

      - name: Extract branch name on pull request
        if: github.event_name == 'pull_request'
        run: echo "::set-env name=BRANCH_NAME::$(echo ${GITHUB_HEAD_REF})"

      - name: Print branch name
        run: echo 'The branch name is' $BRANCH_NAME

要处理pull_request事件(在这种情况下,$GITHUB_REF包含一些无用的东西,如refs/pull/519/merge),你可以使用这一行:

   - name: Set branch name
     run: echo "::set-output name=branch_name::$(echo ${GITHUB_HEAD_REF:-${GITHUB_REF#refs/heads/}})"

同时处理pull_request和push事件的解决方案。由于set-env已弃用,因此实现了保存获得的分支名称以供后续步骤使用的变通方法。 不需要第三方操作。

name: CI
on: [ pull_request, push ]
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
      - name: "Get branch name and save to env"
        env:
          IS_PR: ${{ github.EVENT_NAME == 'pull_request' }}
        run: |
          if ${IS_PR}; then
            BRANCH_NAME="${GITHUB_HEAD_REF}"
          else
            BRANCH_NAME="${GITHUB_REF##*/}"
          fi
          echo "BRANCH_NAME=${BRANCH_NAME}" >> $GITHUB_ENV

      - name: "Another step uses branch name"
        run: echo "Branch name is ${{ env.BRANCH_NAME }}"

GitHub动作中的运行时变量

通常,我总是有一个用nodejs或python编写的脚本,从workflow.yaml中调用。该脚本通常负责获取适当的分支引用等工作。

我有一个函数如下,在一个prepare-deployment.js脚本-

const VALID_REF_PREFIX = 'refs/heads/';
...

function getBranchRef(isProd = false) {
  let branchRef = 'origin/master';

  if (isProd) {
    return branchRef;
  }
  /**
   * When the workflow is invoked from manual flow, the branch name
   * is in GITHUB_REF, otherwise, we have to look into GITHUB_BASE_REF
   */
  if (GITHUB_REF.startsWith(VALID_REF_PREFIX)) {
    // coming from a manual workflow trigger
    branchName = `origin/${GITHUB_REF.replace(VALID_REF_PREFIX, '')}`;
  } else {
    // coming from a PR
    branchRef = `origin/${GITHUB_HEAD_REF}`;
  }

  return branchRef;
}

这涉及到以下场景-

我想从PR部署到我的开发环境的变化 我想通过手动触发器将任何分支的更改部署到我的dev env中 我想从master部署更改到我的prod环境

为了获得delete事件上的ref名称,我最终使用了sed。

on:
  delete:
...
steps:
  - name: Do something
    shell: bash
    run: |
      refname=$(sed -e s:refs/heads/::g -e s:/:-:g <<< ${{ github.event.ref }})

剪掉指针/头/并将斜杠转换为破折号,例如。引用/heads/feature/somefeature到feature-somefeature