如何无需个人访问令牌获取GitHub workflow的artifacts构建产物
你直接传递secrets.GITHUB_TOKEN无法使用的核心原因是:该令牌是GitHub为单次工作流运行自动生成的临时凭证,仅在当前工作流运行期间有效,工作流执行完成后会自动失效,因此你的外部服务器收到请求时,令牌已经没有权限访问API了。
以下是两种无需使用个人PAT的可行解决方案:
方案1:工作流内预获取临时下载链接(推荐,配置最简单)
在工作流运行期间(GITHUB_TOKEN仍有效),直接调用API获取artifact的带签名临时下载链接,将链接传递给部署服务器即可,服务器不需要额外处理授权逻辑。
调整后的工作流配置:
- 新增步骤获取下载链接,放在上传artifact之后、调用部署接口之前:
- name: 4. Store artifact in GitHub uses: actions/upload-artifact@v2 with: name: my-artifact path: target/my-project.jar retention-days: 1 if-no-files-found: error - name: Get artifact download URL id: get-artifact uses: actions/github-script@v6 with: script: | // 获取当前工作流运行的所有artifact const res = await github.rest.actions.listWorkflowRunArtifacts({ owner: context.repo.owner, repo: context.repo.repo, run_id: context.runId }) // 匹配目标artifact const target = res.data.artifacts.find(item => item.name === 'my-artifact') if (!target) throw new Error('未找到目标artifact') // 获取带签名的临时下载链接,有效期1小时 const downloadRes = await github.rest.actions.downloadArtifact({ owner: context.repo.owner, repo: context.repo.repo, artifact_id: target.id, archive_format: 'zip' }) core.setOutput('url', downloadRes.url)
- 调整调用部署接口的步骤,直接传递下载链接即可:
- name: 5. Run deploy on server uses: fjogeleit/http-request-action@master with: url: 'my-endpoint' method: 'POST' contentType: 'application/json' data: '{"download_url": "${{ steps.get-artifact.outputs.url }}"}' preventFailureOnNoResponse: 'true'
注意:GitHub返回的artifact是zip压缩包,你的服务器下载后需要先解压即可获取内部的jar包。
方案2:使用GitHub App生成临时令牌(适合部署延迟较高的场景)
如果你的部署队列有较长等待时间,1小时的临时链接有效期无法满足需求,可以用GitHub App生成最长1小时有效期的可控临时令牌:
- 操作步骤:
- 进入GitHub创建私有App,仅为该App分配目标仓库的
Actions 读取权限 - 将App ID、私钥、安装ID存储到仓库的Secrets中
- 工作流中使用
tibdex/github-app-token等动作生成临时令牌,将令牌传递给部署服务器 - 服务器携带该令牌调用artifact查询、下载API即可,令牌到期后自动失效,不会有长期凭证泄露风险
- 进入GitHub创建私有App,仅为该App分配目标仓库的
内容的提问来源于stack exchange,提问作者Dmytro Pastovenskyi
相关产品推荐
相关产品推荐

