Coder Social home page Coder Social logo

awslabs / amazon-app-runner-deploy Goto Github PK

View Code? Open in Web Editor NEW
49.0 8.0 32.0 1.24 MB

Registers an AWS AppRunner Service and deploys the application using the source code of a given GitHub repository. Supports both source code and Docker image based service

License: MIT No Attribution

JavaScript 0.43% TypeScript 99.57%
aws automation build deployment cicd containerization github-actions apprunner

amazon-app-runner-deploy's Introduction

Amazon "App Runner Service Deploy" action for GitHub Actions

Registers an AWS App Runner Service and deploys the application using the source code of a given GitHub repository. Supports both source code and Docker image based service.

Table of Contents

V2 Changes

This action's codebase has been refactored to support future growth as well as to simplify to processes of adding new capabilities.

Refer to the Changelog for the change history.

Usage

This github action supports two types of App Runner services: source code based and docker image based.

See action.yml for the full documentation for this action's inputs and outputs.

Code based service

Source code is application code that App Runner builds and deploys for you. You point App Runner to a source code repository and choose a suitable runtime. App Runner builds an image that's based on the base image of the runtime and your application code. It then starts a service that runs a container based on this image.

Note: The list of supported runtime platforms is available here.

Here is the sample for deploying a NodeJS based service:

name: Deploy to App Runner 
on:
  push:
    branches: [main] # Trigger workflow on git push to main branch
  workflow_dispatch: # Allow manual invocation of the workflow

jobs:  
  deploy:
    runs-on: ubuntu-latest
    # These permissions are needed to interact with GitHub's OIDC Token endpoint.
    permissions:
      id-token: write
      contents: read
    
    steps:            
      - name: Configure AWS credentials
        uses: aws-actions/configure-aws-credentials@v1-node16
        with:
          # Use GitHub OIDC provider
          role-to-assume: ${{ secrets.AWS_ASSUME_ROLE_ARN }}
          aws-region: ${{ secrets.AWS_REGION }}
          
      - name: Deploy to App Runner
        id: deploy-apprunner
        uses: awslabs/amazon-app-runner-deploy@main
        env:
          SERVER_PORT: 80
          SECRET_ENV: secret_env
        with:
          service: app-runner-git-deploy-service
          source-connection-arn: ${{ secrets.AWS_CONNECTION_SOURCE_ARN }}
          repo: https://github.com/${{ github.repository }}
          branch: ${{ github.ref }}
          runtime: NODEJS_16
          build-command: npm install
          start-command: npm start
          port: 18000
          region: ${{ secrets.AWS_REGION }}
          cpu : 1
          memory : 2
          # Deprecated: wait-for-service-stability: true
          # The new way to control service stability timeout
          wait-for-service-stability-seconds: 600
          copy-env-vars: |
            SERVER_PORT
          copy-secret-env-vars: |
            SECRET_ENV
          instance-role-arn: ${{ secrets.INSTANCE_ROLE_ARN }}
          tags: >
            { "env": "test" }
      
      - name: App Runner URL
        run: echo "App runner URL ${{ steps.deploy-apprunner.outputs.service-url }}" 

Note:

  • AWS_CONNECTION_SOURCE_ARN is the ARN of the source code connector in AWS App Runner, for more details refer to this documentation

Image based service

Here, a source image (that could be a public or private container image stored in an image repository) can get used by App Runner to get the service running on a container. No build stage is necessary. Rather, you provide a ready-to-deploy image.

Here is the sample for deploying a App Runner service based on docker image:

name: Deploy to App Runner
on:
  push:
    branches: [main] # Trigger workflow on git push to main branch
  workflow_dispatch: # Allow manual invocation of the workflow

jobs:  
  deploy:
    runs-on: ubuntu-latest
    # These permissions are needed to interact with GitHub's OIDC Token endpoint.
    permissions:
      id-token: write
      contents: read
    
    steps:      
      - name: Checkout
        uses: actions/checkout@v2
        with:
          persist-credentials: false
          
      - name: Configure AWS credentials
        id: aws-credentials
        uses: aws-actions/configure-aws-credentials@v1-node16
        with:
          # Use GitHub OIDC provider
          role-to-assume: ${{ secrets.AWS_ASSUME_ROLE_ARN }}
          aws-region: ${{ secrets.AWS_REGION }}

      - name: Login to Amazon ECR
        id: login-ecr
        uses: aws-actions/amazon-ecr-login@v1        

      - name: Build, tag, and push image to Amazon ECR
        id: build-image
        env:
          ECR_REGISTRY: ${{ steps.login-ecr.outputs.registry }}
          ECR_REPOSITORY: nodejs
          IMAGE_TAG: ${{ github.sha }}
        run: |
          docker build -t $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG .
          docker push $ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG
          echo "::set-output name=image::$ECR_REGISTRY/$ECR_REPOSITORY:$IMAGE_TAG"  
          
      - name: Deploy to App Runner Image
        id: deploy-apprunner
        uses: awslabs/amazon-app-runner-deploy@main
        with:
          service: app-runner-git-deploy-service
          image: ${{ steps.build-image.outputs.image }}
          access-role-arn: ${{ secrets.ROLE_ARN }}
          region: ${{ secrets.AWS_REGION }}
          cpu : 1
          memory : 2
          # Deprecated: wait-for-service-stability: true
          # The new way to control service stability timeout
          wait-for-service-stability-seconds: 1200
      
      - name: App Runner URL
        run: echo "App runner URL ${{ steps.deploy-apprunner.outputs.service-url }}" 

Note:

  • The above example uses github action, to build the docker image, push it to AWS ECR and use the same for App Runner deployment
  • ROLE_ARN is the Amazon Resource Name (ARN) of the IAM role that grants the App Runner service access to a source repository. It's required for ECR image repositories (but not for ECR Public repositories)

Credentials and Region

This action relies on the default behavior of the AWS SDK for Javascript to determine AWS credentials and region. Use the aws-actions/configure-aws-credentials action to configure the GitHub Actions environment with environment variables containing AWS credentials and your desired region.

We recommend using GitHub's OIDC provider to get short-lived credentials needed for your actions.

It is recommended to follow Amazon IAM best practices for the AWS credentials used in GitHub Actions workflows, including:

  • Do not store credentials in your repository's code. You may use GitHub Actions secrets to store credentials and redact credentials from GitHub Actions workflow logs.
  • Create an individual IAM user with an access key for use in GitHub Actions workflows, preferably one per repository. Do not use the AWS account root user access key.
  • Grant least privilege to the credentials used in GitHub Actions workflows. Grant only the permissions required to perform the actions in your GitHub Actions workflows. See the Permissions section below for the permissions required by this action.
  • Rotate the credentials used in GitHub Actions workflows regularly.
  • Monitor the activity of the credentials used in GitHub Actions workflows.

Permissions

Generally this action requires the following minimum set of permissions:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "apprunner:ListServices",
                "apprunner:CreateService",
                "apprunner:UpdateService",
                "apprunner:DescribeService",
                "apprunner:TagResource",
                "iam:PassRole"
            ],
            "Resource": "*"
        }
    ]
}

For Image based service this action requires additionally the following minimum set of permissions:

{
    "Version": "2012-10-17",
    "Statement": [
        {
            "Effect": "Allow",
            "Action": [
                "ecr:GetDownloadUrlForLayer",
                "ecr:BatchGetImage",
                "ecr:DescribeImages",
                "ecr:GetAuthorizationToken",
                "ecr:BatchCheckLayerAvailability"
            ],
            "Resource": "*"
        }
    ]
}

Troubleshooting

This action emits debug logs to help troubleshoot deployment failures. To see the debug logs, create a secret named ACTIONS_STEP_DEBUG with value true in your repository.

License Summary

This code is made available under the MIT-0 license, for details refer to LICENSE file.

Security Disclosures

If you would like to report a potential security issue in this project, please do not create a GitHub issue. Instead, please follow the instructions here or email AWS security directly.

amazon-app-runner-deploy's People

Contributors

amazon-auto avatar deki avatar dependabot[bot] avatar dmitrygulin avatar haagy avatar hariohmprasath avatar joeyhage avatar jritsema avatar mptg94 avatar odlp avatar yyamanoi1222 avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

amazon-app-runner-deploy's Issues

Add support for StartDeployment Command

Currently the action creates or updates the service accordingly. If support is added for a flag that jsut calls a StartDeployment for the use-cases where a user may not want to update any configuration and jiust trigger a new version of their code/image.

Error: ConfigurationSource cannot be changed from REPOSITORY to API for CREATE_FAILED services.

My pipeline is this:

` name: Deploy to App Runner
on:
push:
branches: [main]

jobs:
deploy:
name: Deploy
runs-on: ubuntu-latest

steps:
- name: Checkout
  uses: actions/checkout@v3

- 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: ${{ secrets.AWS_REGION }}
      
- name: Deploy to App Runner
  id: deploy-apprunner
  uses: awslabs/amazon-app-runner-deploy@main
  env:
    SERVER_PORT: 80
    SECRET_ENV: secret_env
  with:
    service: DEVOPS-NA-INFRA
    source-connection-arn: ${{ secrets.AWS_CONNECTION_SOURCE_ARN }}
    repo: https://github.com/${{ github.repository }}
    branch: ${{ github.ref }}
    runtime: NODEJS_16
    build-command: npm install
    start-command: npm start
    port: 80
    region: ${{ secrets.AWS_REGION }}
    cpu : 1
    memory : 2
    copy-env-vars: |
      SERVER_PORT
    copy-secret-env-vars: |
      SECRET_ENV
  
- name: App Runner URL
  run: echo "App runner URL ${{ steps.deploy-apprunner.outputs.service-url }}" `

I used this blog post as an example: https://aws.amazon.com/pt/blogs/containers/deploy-applications-in-aws-app-runner-with-github-actions/ and it's not working.
My service user has maximum permission to deploy to App Runner

README.md ROLE_ARN mismatch

Reviewing the .yml file in the README.md of this repo:

name: Deploy to App Runner
on:
  push:
    branches: [main] # Trigger workflow on git push to main branch
  workflow_dispatch: # Allow manual invocation of the workflow

jobs:  
  deploy:
    runs-on: ubuntu-latest
    # These permissions are needed to interact with GitHub's OIDC Token endpoint.
    permissions:
      id-token: write
      contents: read
    
    steps:      
      - name: Checkout
        uses: actions/checkout@v2
        with:
          persist-credentials: false
          
      - name: Configure AWS credentials
        id: aws-credentials
        uses: aws-actions/configure-aws-credentials@v1-node16
        with:
          # Use GitHub OIDC provider
          role-to-assume: ${{ secrets.AWS_ASSUME_ROLE_ARN }}
          aws-region: ${{ secrets.AWS_REGION }}

        ....
          
      - name: Deploy to App Runner Image
        id: deploy-apprunner
        uses: awslabs/amazon-app-runner-deploy@main
        with:
          service: app-runner-git-deploy-service
          image: ${{ steps.build-image.outputs.image }}
          access-role-arn: ${{ secrets.ROLE_ARN }}

      - name: App Runner URL
        run: echo "App runner URL ${{ steps.deploy-apprunner.outputs.service-url }}" 

Is there a discrepancy between the ${{ secrets.AWS_ASSUME_ROLE_ARN }} in configure-aws-credentials and access-role-arn: ${{ secrets.ROLE_ARN }}?

Thanks for clarifying.

Action to fail when deployment fail and is rolled back

Description:
Current behavior does not catch when deployment fail but successfully recover to previous version.

Current behavior:
Action uses build from repository or ECR, updates service and waits for status !== operation_in_progress.

Suggested behavior:
Action should store OperationID on updateServiceCommand() and then poll that operation until status !== operation_in_progress. Then return success on status == succeded or else fail

How do I see a job status after deployment?

After completing deployment, there might a situation when the deployment isn't successful and App Runner is performing rollback. In this case, we don't see any error in the action performed on Github side. Is there a flag to configure this behavior?
If not, I was hoping to get the operation id from the outputs to be able to access aws cli listOperations with it?
Would be glad to hear how to deal with this case

Validation error with cpu less than 1 or memory less than 1

Setting cpu or memory with value less than 1 (floating point) yield validation error.

e.g.:

cpu: 0.25
memory: 0.5

output:

2 validation errors detected: Value '0 GB' at 'instanceConfiguration.memory' failed to satisfy constraint: Member must satisfy regular expression pattern: 512|1024|2048|3072|4096|6144|8192|10240|12288|(0.5|1|2|3|4|6|8|10|12) GB; Value '0 vCPU' at 'instanceConfiguration.cpu' failed to satisfy constraint: Member must satisfy regular expression pattern: 256|512|1024|2048|4096|(0.25|0.5|1|2|4) vCPU

Probably because the input field is parsed as int.

const result = Number.parseInt(val);

Missing python 3.11 runtime

The version of the aws-sdk/client-apprunner did not include the python 3.11 runtime, as it was launched on december 2023.

Add support for setting either a custom domain or some kind of prefix (for PR Previews)

Using this github action to deploy on a PR I can almost get PR Previews setup (like heroku, netlify, render, etc).

The only roadblock that I'm running into is I need to know the URL ahead of time-- I need a predictable URL.

If we could set the URL through the apprunner step, I have access to the PR number inside the github action so it would be easy to formulate a url to pass in pretty easily.

It seems like maybe I can create my own action/step in the mean time using the API?

https://docs.aws.amazon.com/apprunner/latest/api/API_AssociateCustomDomain.html

Otherwise, only other missing thing to match heroku etc would be shutting down a service when a PR get's closed

Issue while setting up AWS_ACCESS_KEY_ID & AWS_SECRET_ACCESS_KEY using copy-secret-env-vars

I have a valid instance-role-arn with the necessary SSM and KMS permission. I have created 2 ssm parameters pointing to each app runner environment variable AWS_ACCESS_KEY_ID & AWS_SECRET_ACCESS_KEY respectively.

while running the git hub action pipeline it fails with UnrecognizedClientException: The security token included in the request is invalid.

But if I edit App Runner Environment values directly with the same parameter value (SSM) and update the service manually through the console - it is working.

Is there any additional setting needed?

Failed to assume instance-role-arn

I followed the README and https://aws.amazon.com/blogs/containers/deploy-applications-in-aws-app-runner-with-github-actions/ documentation to implement GitHub action flow for image-based service. I am also successfully able to implement copy-env-vars. While implementing copy-secret-env-vars first it errored about not including instance-role-arn. I tried to follow a similar approach to create a role with SSM Read Only access and used that ARN as instance-role-arn. But it failed with error Failed to assume instance-role-arn.

Trusted Policy:
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Principal": {
"Service": "ssm.amazonaws.com"
},
"Action": "sts:AssumeRole"
}
]
}

Permission: (AmazonSSMReadOnlyAccess)
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": [
"ssm:Describe*",
"ssm:Get*",
"ssm:List*"
],
"Resource": "*"
}
]
}

How to resolve this issue or what is the correct role should be used with instance-role-arn?

Error: The auto scaling configuration ARN you specified isn't valid. ARN: ''

Summary

I have a pipeline that was working fine until yesterday. Without making any changes, it started failing today with this error:

Error: The auto scaling configuration ARN you specified isn't valid. ARN: ''

Relevant

I highly suspect #33 and this change are relevant.

- Optional `auto-scaling-config-arn` input. When specified this will be applied to new and existing services.

Reproduction

Step configuration that fails:

      - name: Deploy to App Runner Image
        id: deploy-apprunner
        uses: awslabs/amazon-app-runner-deploy@main
        with:
          service: my-app-staging-app-runner-service
          image: ${{ steps.login-ecr.outputs.registry }}/my-app-staging-dotnet-backend:${{ github.sha }}
          access-role-arn: ${{ secrets.ROLE_ARN }}
          region: eu-west-1
          cpu: 1
          memory: 2
          wait-for-service-stability: true

Error screenshot:

image

Contributing Guidelines checklist:

  • A reproducible test case or series of steps -> Done, to some extent.
  • The version of our code being used -> awslabs/amazon-app-runner-deploy@main
  • Any modifications you've made relevant to the bug -> Nope. But there are 2.20 changes that might be relevant.
  • Anything unusual about your environment or deployment -> Nope.

Update: A workaround

You can lock the version of awslabs/amazon-app-runner-deploy to 54d9f229e41b80f7cace6480c45ab6dcb1d1af0f, a version that seems to work.

In your yaml, change:

uses: awslabs/amazon-app-runner-deploy@main

to:

uses: awslabs/amazon-app-runner-deploy@54d9f229e41b80f7cace6480c45ab6dcb1d1af0f

It may be a good idea to lock the version even regardless of this issue.

Add serviceUrl to output

It is useful to have serviceUrl in the output to comment or notify url.
If that's not a problem, I'll be happy to throw pr

Add support for setting InstanceRoleArn

Hi!

I have a backend app that needs to access other AWS resources during its work. It would be nice to have options to set a "InstanceRoleArn" in configuration params, to pass this inside the service.

Thanks in advance!

Image is ignored for existing App Runner Service

Repro steps:

  1. Push two different images/tags to the ECR private registry (e.g. main and develop)
  2. Configure App Runner manual to deploy one of those, e.g. main
  3. Configure and run App Runner to deploy/refresh that service but with image set to the second image, e.g. develop
  4. After the job is finished check whether the develop image is deployed

Current result:
Service was refreshed but with the first image (main)

Expected result:
Image from the image field should be used for the new service instance.

My setup:

  1. demo:main and demo:develop are uploaded to ECR
  2. demo-env App Runner service is configured with main image
  3. I'm triggering the workflow with imageTag set to develop
name: Deploy to demo env

on:
  workflow_dispatch:
    inputs:
      imageTag:
        description: "Image tag to deploy"
        required: true
        default: "develop"

jobs:
  deploy-demo:
    # avoid running the job when build for the branch is running
    concurrency:
      group: refs/heads/${{ github.event.inputs.imageTag }}
      cancel-in-progress: false
    runs-on: ubuntu-latest
    env:
      AWS_REGION: <<redacted>>
    steps:
      - 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: ${{ env.AWS_REGION }}

      - name: Deploy to App Runner Image
        id: deploy-apprunner
        uses: awslabs/amazon-app-runner-deploy@main
        with:
          service: demo-env
          image: ${{ secrets.AWS_ECR_REPOSITORY }}/<<redacted>>/demo:${{ github.event.inputs.imageTag }}
          access-role-arn: ${{ secrets.AWS_ECR_ACCESS_ROLE_ARN }}
          region: ${{ env.AWS_REGION }}
          cpu: 1
          memory: 2
          wait-for-service-stability: true

      - name: Demo output
        run: |
          echo "App runner service-id ${{ steps.deploy-apprunner.outputs.service-id }}"
          echo "Visit <<redacted>>"

Job log:

Run awslabs/amazon-app-runner-deploy@main
  with:
    service: demo-env
    image: ***/<<redacted>>/demo:develop
    access-role-arn: ***
    region: <<redacted>>
    cpu: 1
    memory: 2
    wait-for-service-stability: true
  env:
    AWS_REGION: <<redacted>>
    AWS_DEFAULT_REGION: <<redacted>>
    AWS_ACCESS_KEY_ID: ***
    AWS_SECRET_ACCESS_KEY: ***
Updating existing service demo-env
Service update initiated with operation ID - <<redacted>>
Waiting for the service <<redacted>> to reach stable state
Service <<redacted>> has reached the stable state RUNNING
App Runner step - DONE!

Action fails when deploying App Runner Private Services deployments

Hey all,

We started making use of this action to deploy an App Runner Private Service, after making use of this action many times for standard "public" app runner deployments.

The issue is that the AWS CLI/API does not report back a serviceUrl when describing an app runner private service, which causes this action to wrongfully fail (the service is deployed correctly, but the action fails because it didn't report a URL back).

I looked inside the code a bit and it seems that a PR that doesn't fail in case a serviceUrl is not returned can be easy to make, so I'd be happy to help if that solution works for everyone.

If not, please let me know if you have plans to fix this issue.

Can't Run Multiple Commands Under "Build command" Config?

I have the following in my package.json file:

"scripts": {
    "migrate": "knex migrate:latest"
},

Running npm run migrate works fine on my local machine. When I try to add this command onto my existing build command:

1

App Runner always gives an error and rolls back my change:

2

Does App Runner not support multiple build commands?

Deployment Ignoring apprunner.yaml File

I have been following this guide to integrate a custom apprunner.yaml file into my Node 18 application. I added apprunner.yaml to the root folder of my ExpressJS repo. The file looks like:

version: 1.0
runtime: nodejs18
build:
  commands:
    build:
      - npm install
    post-build:
      - knex migrate:latest
      - knex seed:run

After adding this to my repo and triggering a build, the App Runner instance deploys without any errors. But when I look at the Postgres instance that's connected to my app, I notice that the migration and seed commands under the post-build section of my apprunner.yaml file did not run.

Looking through the deployment logs, I also don't see any mention of the post-build commands of knex migrate:latest or knex seed:run. There are also no errors reported in the logs.

It seems like App Runner is ignoring the apprunner.yaml file in my repo. Is there another step that needs to be taken into account to get it to use the apprunner.yaml file?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.