Skip to content

Commit c3f1647

Browse files
Merge pull request #54 from clouddrove/internal_357
Feature: Updated SST Workflow with Add-ons
2 parents 7a232b8 + e495b23 commit c3f1647

File tree

4 files changed

+205
-66
lines changed

4 files changed

+205
-66
lines changed

.github/actions/yarn-nm-install

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,53 @@
1+
########################################################################################
2+
# "yarn install" composite action for yarn 2/3/4+ and "nodeLinker: node-modules" #
3+
#--------------------------------------------------------------------------------------#
4+
# Cache: #
5+
# - Downloaded zip archive (multi-arch, preserved across yarn.lock changes) #
6+
# - Yarn install state (discarded on yarn.lock changes) #
7+
# References: #
8+
# - bench: https://gist.github.com/belgattitude/0ecd26155b47e7be1be6163ecfbb0f0b #
9+
# - vs @setup/node: https://github.com/actions/setup-node/issues/325 #
10+
########################################################################################
11+
12+
name: 'Yarn install'
13+
description: 'Run yarn install with node_modules linker and cache enabled'
14+
15+
runs:
16+
using: 'composite'
17+
steps:
18+
- name: Expose yarn config as "$GITHUB_OUTPUT"
19+
id: yarn-config
20+
shell: bash
21+
run: |
22+
echo "CACHE_FOLDER=$(yarn config get cacheFolder)" >> $GITHUB_OUTPUT
23+
24+
# Yarn rotates the downloaded cache archives, @see https://github.com/actions/setup-node/issues/325
25+
# Yarn cache is also reusable between arch and os.
26+
- name: Restore yarn cache
27+
uses: actions/cache@v3
28+
id: yarn-download-cache
29+
with:
30+
path: ${{ steps.yarn-config.outputs.CACHE_FOLDER }}
31+
key: yarn-download-cache-${{ hashFiles('yarn.lock') }}
32+
restore-keys: |
33+
yarn-download-cache-
34+
35+
# Invalidated on yarn.lock changes
36+
- name: Restore yarn install state
37+
id: yarn-install-state-cache
38+
uses: actions/cache@v3
39+
with:
40+
path: .yarn/ci-cache/
41+
key: ${{ runner.os }}-yarn-install-state-cache-${{ hashFiles('yarn.lock', '.yarnrc.yml') }}
42+
43+
- name: Install dependencies
44+
shell: bash
45+
run: |
46+
yarn install --immutable --inline-builds
47+
env:
48+
# CI optimizations. Overrides yarnrc.yml options (or their defaults) in the CI action.
49+
YARN_ENABLE_GLOBAL_CACHE: 'false' # Use local cache folder to keep downloaded archives
50+
YARN_NM_MODE: 'hardlinks-local' # Hardlinks-(local|global) reduces io / node_modules size
51+
YARN_INSTALL_STATE_PATH: .yarn/ci-cache/install-state.gz # Very small speedup when lock does not change
52+
# Other environment variables
53+
HUSKY: '0' # By default do not run HUSKY install

.github/workflows/helm.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -58,10 +58,10 @@ on:
5858
type: string
5959
description: 'Environment name for rollback'
6060
secrets:
61-
aws-access-key-id:
61+
AWS_ACCESS_KEY_ID:
6262
description: 'AWS Access Key ID'
6363
required: false
64-
aws-secret-access-key:
64+
AWS_SECRET_ACCESS_KEY:
6565
description: 'AWS Secret Access Key'
6666
required: false
6767
AZURE_CREDENTIALS:
@@ -79,8 +79,8 @@ jobs:
7979
if: ${{ inputs.provider == 'aws' }}
8080
uses: aws-actions/configure-aws-credentials@v2
8181
with:
82-
aws-access-key-id: ${{ secrets.aws-access-key-id }}
83-
aws-secret-access-key: ${{ secrets.aws-secret-access-key }}
82+
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
83+
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
8484
aws-region: ${{ inputs.aws-region }}
8585

8686
- name: Install Azure CLI

.github/workflows/sst_workflow.yml

Lines changed: 110 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,65 +1,145 @@
1-
name: Shared workflow- SST APP
1+
name: Shared Workflow - SST Deploy
22

33
on:
44
workflow_call:
55
inputs:
66
app-env:
7-
description: 'Application environment'
7+
description: 'Application environment'
8+
required: true
9+
type: string
10+
preview:
11+
description: 'Create or destroy preview env'
812
required: false
913
type: string
14+
default: false
1015
working-directory:
11-
description: 'Working directory in the repository'
12-
required: true
16+
description: 'Working directory in repo'
17+
required: false
18+
type: string
19+
default: ./
20+
stack-name:
21+
description: 'Stack name'
22+
required: false
23+
default: ""
1324
type: string
25+
yarn-cache:
26+
description: 'Cache required or not for yarn install'
27+
type: string
28+
default: false
29+
deploy:
30+
description: 'Default deploy otherwise run diff command to detect changes in stacks'
31+
type: string
32+
default: true
33+
self-hosted:
34+
description: 'Deploy stack with github self hosted runner or not'
35+
type: string
36+
default: true
1437

1538
secrets:
16-
aws-access-key-id:
17-
description: 'AWS Access Key ID'
18-
required: true
19-
aws-secret-access-key:
20-
description: 'AWS Secret Access Key'
39+
token:
40+
description: 'GitHub Token'
41+
required: false
42+
env-vars:
43+
description: 'Environment-variables to store in .env file'
44+
required: false
45+
build-role:
46+
description: 'Assume role arn'
2147
required: true
2248

49+
2350
jobs:
24-
deploy:
25-
runs-on: ubuntu-20.04
26-
environment:
27-
name: ${{ github.head_ref }}
28-
url: ${{ env.API_ENDPOINT_URL }}
51+
setup:
52+
runs-on: ubuntu-latest
53+
outputs:
54+
runner: ${{ steps.step1.outputs.runner }}
55+
steps:
56+
- name: Check branch
57+
id: step1
58+
run: |
59+
if [ ${{ inputs.self-hosted }} == 'true' ]; then
60+
echo "runner=${{ inputs.app-env }}" >> "$GITHUB_OUTPUT"
61+
else
62+
echo "runner=ubuntu-latest" >> "$GITHUB_OUTPUT"
63+
fi
64+
sst-deploy:
65+
needs: [setup]
66+
runs-on: ${{ needs.setup.outputs.runner }}
67+
environment:
68+
name: ${{ (((github.event.action == 'opened' || github.event.action == 'synchronize') && inputs.preview == 'true') || (github.event.pull_request.merged == true && inputs.preview == 'false' && inputs.app-env == 'staging') || (inputs.app-env == 'production' && startsWith(github.ref, 'refs/tags/v'))) && ((inputs.preview == 'true' && (inputs.stack-name != '' && github.head_ref-inputs.stack-name || github.head_ref) || inputs.app-env)) || '' }}
69+
url: ${{ ((github.event.action == 'opened' && inputs.preview == 'true') || (github.event.action == 'synchronize' && inputs.preview == 'true') || (github.event.pull_request.merged == true && inputs.preview == 'false' && inputs.app-env == 'staging') || (inputs.app-env == 'production' && startsWith(github.ref, 'refs/tags/v'))) && env.API_ENDPOINT_URL }}
2970
defaults:
3071
run:
3172
working-directory: ${{ inputs.working-directory }}
3273

33-
name: Deploy SST APP
74+
name: Run sst-deploy
3475
steps:
3576
- name: Checkout git repo
3677
uses: actions/checkout@v3
3778

38-
- name: Configure AWS Credentials
39-
uses: aws-actions/configure-aws-credentials@v2
79+
- name: update environment variable in .env file
80+
run: |
81+
if [ -n "${{ secrets.env-vars }}" ]; then
82+
echo -e "${{ secrets.env-vars }}" > ./.env
83+
fi
84+
85+
- name: Configure AWS Creds via role
86+
uses: aws-actions/configure-aws-credentials@v1-node16
4087
with:
41-
aws-access-key-id: ${{ secrets.aws-access-key-id }}
42-
aws-secret-access-key: ${{ secrets.aws-secret-access-key }}
43-
aws-region: us-east-2
88+
aws-region: us-west-2
89+
role-to-assume: ${{ secrets.build-role }}
90+
role-duration-seconds: 900
91+
role-skip-session-tagging: true
92+
93+
- name: Install yarn
94+
run: sudo npm install -g yarn
4495

45-
- name: Install dependencies (yarn install)
46-
run: yarn install
47-
48-
- name: Extract branch name
96+
- name: Install dependencies
97+
if: ${{ inputs.yarn-cache != 'true' }}
98+
run: yarn install --frozen-lockfile
99+
100+
- name: Install dependencies with yarn cache
101+
if: ${{ inputs.yarn-cache == 'true' }}
102+
uses: ./.github/actions/yarn-nm-install
103+
104+
- name: Set branch name
49105
run: |
50-
BRANCH_NAME=$(echo "${{ github.head_ref }}" | cut -d'/' -f3)
106+
BRANCH_NAME=$(echo "${{ github.head_ref }}" | cut -d'|' -f2)
51107
echo "BRANCH_NAME=${BRANCH_NAME}"
52108
SLUG_BRANCH_NAME=$(echo "${BRANCH_NAME}" | sed 's/[^[:alnum:]]/-/g' | tr -s '-' | tr A-Z a-z)
53109
echo "SLUG_BRANCH_NAME=${SLUG_BRANCH_NAME}"
54110
echo "GITHUB_HEAD_REF_SLUG=${SLUG_BRANCH_NAME}" >> $GITHUB_ENV
55111
112+
- name: check diffrence in deployed and local stacks
113+
if: ${{ inputs.deploy != 'true' }}
114+
run: yarn sst diff --stage ${{ inputs.app-env }}
115+
56116
- name: Deploy and get API endpoint
57-
if: ${{ (github.event.action == 'opened' || github.event.action == 'synchronize' && inputs.app-env == 'preview') || ( github.event.pull_request.merged == true && (inputs.app-env == 'prod' || inputs.app-env == 'stage')) }}
117+
if: ${{ inputs.deploy == 'true' && ((github.event.action == 'opened' && inputs.preview == 'true') || (github.event.action == 'synchronize' && inputs.preview == 'true') || (github.event.pull_request.merged == true && inputs.preview == 'false' && inputs.app-env == 'staging') || (inputs.app-env == 'production' && startsWith(github.ref, 'refs/tags/v'))) }}
58118
run: |
59-
api_endpoint=$(yarn sst deploy --stage pr-${{ github.event.number }}-${{ env.GITHUB_HEAD_REF_SLUG }} | egrep "ApiEndpoint|SiteUrl" | awk '{print $2}')
119+
if [[ ${{ inputs.preview }} == true ]]; then
120+
if [[ -n "${{ inputs.stack-name }}" ]]; then
121+
yarn sst deploy --stage pr-${{ github.event.number }}-${{ env.GITHUB_HEAD_REF_SLUG }} ${{ inputs.stack-name }} | tee deploy-output.log
122+
else
123+
yarn sst deploy --stage pr-${{ github.event.number }}-${{ env.GITHUB_HEAD_REF_SLUG }} | tee deploy-output.log
124+
fi
125+
else
126+
if [[ -n "${{ inputs.stack-name }}" ]]; then
127+
yarn sst deploy --stage ${{ inputs.app-env }} ${{ inputs.stack-name }} | tee deploy-output.log
128+
else
129+
yarn sst deploy --stage ${{ inputs.app-env }} | tee deploy-output.log
130+
fi
131+
fi
132+
api_endpoint=$(cat deploy-output.log | egrep "ApiEndpoint|SiteUrl" | awk '{print $2}')
60133
echo "API endpoint: $api_endpoint"
61134
echo "API_ENDPOINT_URL=$api_endpoint" >> $GITHUB_ENV
62-
63-
- name: Destroy SST App for Preview app environment
64-
if: ${{ ( github.event.action == 'labeled' && github.event.label.name == 'destroy' && inputs.app-env == 'preview' ) || (github.event.action == 'closed' && inputs.app-env == 'preview' || github.event.pull_request.merged == true && inputs.app-env == 'preview') }}
135+
136+
- name: Destroy preview env
137+
if: ${{ ( github.event.action == 'labeled' && github.event.label.name == 'destroy' && inputs.preview == 'true' ) || (github.event.action == 'closed' && inputs.preview == 'true' || github.event.pull_request.merged == true && inputs.preview == 'true' ) }}
65138
run: yarn sst remove --stage pr-${{ github.event.number }}-${{ env.GITHUB_HEAD_REF_SLUG }}
139+
140+
- name: Cleanup preview env deployment
141+
if: ${{ ( github.event.action == 'labeled' && github.event.label.name == 'destroy' && inputs.preview == 'true' ) || (github.event.action == 'closed' && inputs.preview == 'true' || github.event.pull_request.merged == true && inputs.preview == 'true' ) }}
142+
uses: strumwolf/[email protected]
143+
with:
144+
token: ${{ secrets.token }}
145+
environment: ${{ github.head_ref }}

docs/sst.md

Lines changed: 38 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,44 +1,50 @@
11
## [SST Workflow](https://github.com/clouddrove/github-shared-workflows/blob/master/.github/workflows/sst_workflow.yml)
22

3-
This workflow is used to deploy serverless stack (SST) application on AWS environment. Workflows have been added in `.github/workflows/sst_workflow.yml`.
3+
This workflow is used to deploy or destroy serverless stack (SST) application on AWS environment. Workflows have been added in `.github/workflows/sst_workflow.yml`.
44

55
#### Usage
6-
Below workflow can be used to deploy SST in preview environment when pull request generated and it destroys the preview environment when pull request closed, merged and labeled as destroy, similarly staging and production is deployed using there defined branches.
6+
The following workflow can be used to deploy the SST application in the staging environment when a pull request is generated on the base branch named "master". It will deploy the SST application in the production environment when a new tag is released. Additionally, it will destroy the preview environment when a pull request is closed, merged, and labeled as "destroy".
77

8-
```yaml
9-
name: SST Workflow
10-
11-
on:
12-
pull_request:
13-
types: [closed, merged, labeled]
14-
workflow_dispatch:
15-
jobs:
16-
preview:
17-
uses: clouddrove/github-shared-workflows/.github/workflows/sst_workflow.yml@master
18-
secrets:
19-
AWS_ACCESS_KEY_ID: # AWS Access Key ID for preview
20-
AWS_SECRET_ACCESS_KEY: # AWS Secret Access Key for preview
21-
with:
22-
app-env: # preview
23-
working-directory: # specify your working folder from repo
8+
Inputs:
9+
| Input name | Type | Required | Default | Comment |
10+
|---|---|---|---|---|
11+
| app-env | string | true | | Staging or Production |
12+
| preview | string | false | false | If true SST deployed in preview environment |
13+
| working-directory | string | false | ./ | SST code location path |
14+
| stack-name | string | false | | Specify stack name for deployment |
15+
| yarn-cache | string | false | false | Yarn stores packages in global cache |
16+
| deploy | string | false | true | Plan app stacks or deploy. |
17+
| self-hosted | string | false | true | Deploy stack with github runner or without it. |
2418

25-
staging:
26-
if: ${{ github.base_ref == 'stage' }}
19+
Secrets:
20+
| Secret name | Required | Comment |
21+
|---|---|---|
22+
| token | false | GitHub token for environment deletion |
23+
| env-vars | false | Stack environment variables |
24+
| build-role | true | | AWS authentication role |
25+
26+
```yaml
27+
staging-workflow:
28+
if: ${{ github.event.pull_request.base.ref == 'master' }}
2729
uses: clouddrove/github-shared-workflows/.github/workflows/sst_workflow.yml@master
28-
secrets:
29-
AWS_ACCESS_KEY_ID: # AWS Access Key ID for Stage
30-
AWS_SECRET_ACCESS_KEY: # AWS Secret Access Key for stage
3130
with:
32-
app-env: # stage
33-
working-directory: # specify your working folder from repo
31+
app-env: staging
3432

35-
production:
36-
if: ${{ github.base_ref == 'master' }}
33+
production-workflow:
34+
if: startsWith(github.event.ref, 'refs/tags/v')
3735
uses: clouddrove/github-shared-workflows/.github/workflows/sst_workflow.yml@master
38-
secrets:
39-
AWS_ACCESS_KEY_ID: # AWS Access Key ID for prod
40-
AWS_SECRET_ACCESS_KEY: # AWS Secret Access Key for prod
4136
with:
42-
app-env: # prod
43-
working-directory: # specify your working folder from repo
37+
app-env: production
4438
```
39+
40+
41+
##### Path: `clouddrove/github-shared-workflows/.github/workflows/sst_workflow.yml@master`
42+
43+
Should be used with `on: pull_request`. Includes the following:
44+
1. Adds SST Deployed application link into the description of a pull request.
45+
2. Appends Pull Request number and head branch name for the stage name when the preview environment is set to true.
46+
47+
Handles the following branch naming styles :
48+
- `feature-123`
49+
- `feature_123`
50+
- `feature-123/feature-description`

0 commit comments

Comments
 (0)