I want to enable automatic builds on Heroku anytime I push to master branch on GitHub just like Heroku would do whenever I push to a branch that is connected to an app on their platform. Is there any way to achieve this?
We can achieve this feat with GitHub Actions. We can automate builds on Heroku whenever a push is made hence no need to worry about deploying to Heroku via heroku-cli.
At the root of your application, create a .github folder.
Inside of the .github folder, create a workflow folder
lastly, in the workflow folder, create a yaml file. I'll call mine build-heroku-app.yml. So the file structure is going to look like so:
my-awesome-app
- .github
- workflow
- build-heroku-app.yml
In build-heroku-app.yml file
# .github/workflows/build-heroku-app.yml // Just a comment
name: Build App on Heroku
on:
push: // type of event
branches:
- master // name of branch we want to listen to for event
jobs:
heroku-pull-request:
runs-on: ubuntu-latest
env:
HEROKU_APP_NAME: my-awesome-app // name of app on heroku
steps:
- name: Checkout repository
uses: actions/checkout#v3
with:
fetch-depth: 0
ref: ${{ github.ref_name }}
- name: Login to Heroku
uses: akhileshns/heroku-deploy#v3.12.12
with:
heroku_email: ${{ secrets.HEROKU_EMAIL }} // Heroku email address
heroku_api_key: ${{ secrets.HEROKU_API_KEY }} // Heroku API key
heroku_app_name: ${{ env.HEROKU_APP_NAME }} // Declared above
justlogin: true
- name: Add Heroku remote
run: heroku git:remote --app=${{ env.HEROKU_APP_NAME }}
- name: Push to master branch app on Heroku
run: git push heroku ${{ github.ref_name }}:master --force
Visit Github Actions Secrets Documentation to understand how secrets work in Github actions and how to create them.
You can view your Heroku API key by going to the API Key section on your Heroku Account settings page.
Related
I'm trying to automatically deploy an SPA website to an S3 bucket on AWS. I created a user in AWS specially to do this, and got the Access ID and Secret. I then added the main.yml file shown below to .github/workflows.
It certainly gets triggered when a PR from a branch is approved, but fails with the message: Could not load credentials from any providers
Here is my code:
name: CI
on:
push:
branches:
- main #here we choose to deploy only when a push is detected on the main branch
permissions:
id-token: write
contents: read
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout#v1
- name: Configure AWS Credentials
uses: aws-actions/configure-aws-credentials#v1
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: us-west-2 # Use your bucket region here
# Here you could add some building steps if you were dealing with some angular/react/Vue...
# - name: Build static site
# run: yarn install && npm run-script build
- name: Deploy static site to S3 bucket
run: aws s3 sync ./dist/robert-phoenix/ s3://arn:aws:s3:::robertphoenix.info --delete
# --delete flag will remove any file in the s3 that are not on the "thefolder
I added the permissions entry based on comments I saw elsewhere. Examples given previously seemed to be at a time when GitHub only had one set of secrets. I added them to both Actions and Dependabot.
I'm not sure I have the right description for the S3 bucket, but the script doesn't get that far anyway, so that is not the cause of the current error.
Can I trigger a new workflow from another workflow?
I'm trying to run a workflow after the first workflow has pushed a new release and it seems to ignore it.
Found the answer here:
An action in a workflow run can't trigger a new workflow run. For example, if an action pushes code using the repository's GITHUB_TOKEN, a new workflow will not run even when the repository contains a workflow configured to run when push events occur.
EDIT:
The quote above might be confusing. When I add a Personal Access Token (PAT) to the checkout action with repo permissions granted (and not repository's GITHUB_TOKEN), the following commands DO trigger other workflows:
- name: Checkout Repo
uses: actions/checkout#v2
with:
token: ${{ secrets.PAT_TOKEN }}
(In my case, running semnatic-release after this checkout, which creates a new release with a new tag - did trigger another workflow that runs only if a tag was created)
As described here, you can trigger another workflow using the workflow_run event.
For example we could think of two workflow definitions like this (the only prerequisite is, that both reside in the same repository - but I'am sure, there's also an event for other repos as well):
release.yml
name: CI release
on: [push]
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout#v2
- name: Release artifact
run: ...
do-something-different.yml
name: Do anything after the release of the first workflow
on:
workflow_run:
workflows: ["CI release"]
types:
- completed
jobs:
notify:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout#v2
- name: Do something
run: ...
A crucial point here is that the name: CI release definition of the first yaml file must exactly match the workflow_run: workflows: ["CI release"] definition in the second yaml file. Another point is that this approach needs to be done on the default branch (which is mostly main or master) as the docs state:
Note: This event will only trigger a workflow run if the workflow file
is on the default branch.
If you don't want to use a general Personal Access Token (which has access to all of your repos), you can generate a dedicated SSH keypair for this purpose and add it to the repository as a Deploy Key. This is done as follows:
Generate an SSH keypair:
ssh-keygen -N "" -f deploy_key -C "github-actions"
Add the private key (generated file deploy_key) as an encryped secret, e.g. COMMIT_KEY to the GitHub project.
Add the public key (generated file deploy_key.pub) as a deploy key with write access to the GitHub project. Tick the Allow write access checkbox.
When checking out the source code in your workflow, add the SSH key:
- name: Checkout
uses: actions/checkout#v3
with:
ssh-key: "${{secrets.COMMIT_KEY}}"
Subsequent push actions in the same workflow will then trigger any configured GitHub workflow as if they were pushed manually.
I want to read version from a file and create tag as v11.0.5.1.aws using the workflow . Then I want to use that tag in the docker image.
For that, I have created a branch as devops.
First created a VERSION file as
1.1.3 20 Apr, 2022
Created a workflow as release-version.yml
name: Release Version
on:
push:
branches:
- devops
jobs:
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout#master
- name: Bump version and push tag
uses: melheffe/version_release_composer#master
env:
PREPEND: 'v'
APPEND: '.aws' # must include '.' or it will append without separation
DRAFT: 'false'
PRERELEASE: 'true'
TOKEN: ${{ secrets.AUTH_TOKEN }}
TRIGGER: ${{ github.event.pull_request.base.ref }} # can use the triggering branch or define a fixed one like this: 'master'
REPO_OWNER: rohit
VERSION_FILE_NAME: 'VERSION'
Then created another workflow as ci.yml which will get tag from release-version workflow
name: CI
# Only trigger, when the build workflow succeeded
on:
workflow_run:
workflows: ["Release Version"]
types:
- completed
jobs:
# This workflow contains a single job called "build"
build:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout#v2
DeployDev:
# Steps represent a sequence of tasks that will be executed as part of the job
name: Deploy to Dev
needs: [Build]
runs-on: ubuntu-latest
environment:
name: Dev
steps:
- uses: actions/checkout#v2
with:
token: ${{ secrets.AUTH_TOKEN }}
- name: Build, tag, and push image to Amazon ECR
id: build-image
#env:
# IMAGE_TAG: ${{ github.sha }}
run: |
# Build a docker container and push it to ECR so that it can
# be deployed to ECS.
echo "$GITHUB_REF_NAME"
docker build -t ${{secrets.ECR_REPO_URI}}/${{secrets.REPO_NAME}}:$GITHUB_REF_NAME .
docker push ${{secrets.ECR_REPO_URI}}/${{secrets.REPO_NAME}}:$GITHUB_REF_NAME
I'm able to trigger release version workflow after making changes on devops branch but ci workflow is not getting triggered after triggering the release-version.
Any suggestion will be helpful for me.
If the workflow_run trigger isn't working as expected, there are two other ways to achieve what you want (triggering a workflow from another workflow, sending an input parameter from the first one to use in the second one).
The workflow_dispatch event.
The repository_dispatch event.
The documentation is very good about how to use them, but I'll add here some references that can help as well:
Triggering Github Action using a POST request (Github REST API)
How to trigger a workflow_dispatch from Github API?
Triggering GitHub workflow using gh CLI
As you can see, you can trigger those events using directly the Github API in a step (with a CURL request) or using some actions from the Github Marketplace that perform the same operation.
The answer below also explains the difference between both events (as they are similar, and CURL payload differences may be confusing)
Correct request with client-payload to run workflow_dispatch in github action
I'll also add here an example that can be useful to understand how to use the repository_dispatch event to receive a callback from the other workflow to the first one:
workflow A
workflow B
Note that you will also need to use a PAT to trigger a workflow using a dispatch event.
Problem: We use github actions workflow for CI and we have many github repositories. I need to be able change everything repeatable for every repository at once.
Is it possible to use in github action workflow yml file some snippet that located mb in different repository.
You can include other public and local actions in your workflow, which lets you reuse common steps. Using versioned actions with {owner}/{repo}#{ref}:
steps:
- uses: actions/setup-node#74bc508 # Reference a specific commit
- uses: actions/setup-node#v1 # Reference the major version of a release
- uses: actions/setup-node#v1.2 # Reference a minor version of a release
- uses: actions/setup-node#master # Reference a branch
..or local actions with ./path/to/dir:
jobs:
my_first_job:
steps:
- name: Check out repository
uses: actions/checkout#v2
- name: Use local my-action
uses: ./.github/actions/my-action
https://help.github.com/en/actions/reference/workflow-syntax-for-github-actions#jobsjob_idstepsuses
One way of doing this is having a central CICD / GitHub actions repository with shared workflows which are triggered on repository_dispatch events.
on:
repository_dispatch:
types:
- your_event
jobs:
job1:
name: Do something
runs-on: ubuntu-latest
env:
SOURCE_BRANCH: ${{ github.event.client_payload.source_branch }}
SOURCE_REPO: ${{ github.event.client_payload.source_repo }}
# do all your stuff
Then in each github repo you write a small workflow file which outlines the triggers for the local repo, pushing to master / opening a PR etc. That action simply dispatches a repository_dispatch event to your central CICD repo with the repo and branchname it came from.
name: Trigger external CICD
on:
push:
branches:
- master
jobs:
trigger_cicd:
name: Trigger external CICD
runs-on: ubuntu-latest
steps:
- name: Send repository_dispatch event
uses: peter-evans/repository-dispatch#v1
with:
token: ${{ secrets.CICD_GITHUB_TOKEN }}
repository: yourorg/centralcicdrepo
event-type: ${{ env.EVENT_TYPE }}
client-payload: '{"source_branch": "${{ github.ref }}", "source_repo": "${{ github.repository }}" }'
One gotcha is that you need an access token to talk between repos, in the above example it's added as a secret called CICD_GITHUB_TOKEN. The easiest is to just use your own account but this will label all your central CICD runs as 'triggered by you'. You can also create a bot account or you can have each developer add their access tokens as secrets then map the right author to the right access token.
There is currently (Feb. 3, 2021) no supported method for reusing workflows or snippets from a centralized repository. There are hacks, as Michael Parker has cleverly demonstrated, but these come with significant downsides (eg. observability, opacity, etc.).
I've written this blog post that describes the problem you have in more detail, along with an open-source solution.
––
Similar topics:
DRYing GH Actions workflows
External workflow configuration
Bringing this issue to GH's attention:
Raise this issue with GH
GH Roadmap item
So I'm quite new to Github actions and trying to implement an action in a workflow.
I need to clone/checkout repo_2 into where my workflow is located, repo_1. Both are private repos.
It looks like this
job:
name: Cloning private repo
runs-on: ubuntu-latest
steps:
- name: Cloning
uses: actions/checkout#v1
with:
repository: my-username/repo_2
token: ${{ secrets.PAT }}
I created a PAT and added it as a secret key to repo_2. However whenever I run the workflow I get the following error:
[error]fatal: repository 'https://github.com/my-username/repo_2/' not
found
Seems to me like the authentication couldn't be verified. Is this what's happening? How do I fix it?