Skip to content

feat: adds queries for create, search, remove data from elastic search #44

feat: adds queries for create, search, remove data from elastic search

feat: adds queries for create, search, remove data from elastic search #44

Workflow file for this run

name: Full CI/CD Pipeline
on:
push:
branches:
- main
pull_request:
branches:
- main
workflow_dispatch:
permissions:
id-token: write
contents: read
env:
AWS_REGION: us-east-1
ECR_REPOSITORY: nestjs-app
IMAGE_TAG: latest
jobs:
terraform:
name: Deploy Staging Infrastructure with Terraform
runs-on: ubuntu-latest
defaults:
run:
working-directory: infrastructure/staging
env:
TF_VAR_ami_id: ${{ secrets.TF_VAR_AMI_ID }}
TF_VAR_aws_region: ${{ secrets.TF_VAR_AWS_REGION }}
TF_VAR_instance_type: ${{ secrets.TF_VAR_INSTANCE_TYPE }}
TF_VAR_key_name: ${{ secrets.TF_VAR_KEY_NAME }}
TF_VAR_security_group_name: ${{ secrets.TF_VAR_SECURITY_GROUP_NAME }}
TF_VAR_subnet_id: ${{ secrets.TF_VAR_SUBNET_ID }}
TF_VAR_vpc_id: ${{ secrets.TF_VAR_VPC_ID }}
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Configure AWS Credentials via OIDC
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ secrets.AWS_ROLE_TO_ASSUME }}
aws-region: ${{ secrets.TF_VAR_AWS_REGION }}
- name: Setup Terraform
uses: hashicorp/setup-terraform@v3
with:
terraform_version: 1.8.2
- name: Terraform Init
run: terraform init -input=false
- name: Terraform Validate
run: terraform validate
- name: Terraform Plan with Retry
run: |
for i in {1..5}; do
terraform plan -input=false -no-color && break || sleep 10
done
- name: Terraform Apply (on push to main)
if: github.event_name == 'push'
run: terraform apply -auto-approve -input=false
test-ssh-connection:
name: Test SSH to EC2
runs-on: ubuntu-latest
needs: terraform
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Test SSH Connection
uses: appleboy/ssh-action@v1.0.0
with:
host: ${{ secrets.EC2_PUBLIC_IP }}
username: ec2-user
key: ${{ secrets.EC2_SSH_KEY }}
script: |
echo "📁 Creating and fixing permissions on target directory..."
sudo mkdir -p /home/ec2-user/twitter-backend-node/
sudo chown -R ec2-user:ec2-user /home/ec2-user/twitter-backend-node/
sudo chmod -R u+rwX /home/ec2-user/twitter-backend-node/
echo "✅ Directory ready"
nodejs-ci:
name: Node.js CI
runs-on: ubuntu-latest
needs: test-ssh-connection
services:
mysql:
image: mysql:8.0
env:
MYSQL_DATABASE: yoodb_test
MYSQL_ROOT_PASSWORD: rootpass
MYSQL_USER: yooadmin
MYSQL_PASSWORD: yoopass
ports:
- 3306:3306
options: >-
--health-cmd="mysqladmin ping -h 127.0.0.1 -uroot -prootpass"
--health-interval=10s
--health-timeout=5s
--health-retries=5
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Set up Node.js
uses: actions/setup-node@v4
with:
node-version: '20'
- name: Install dependencies
run: npm install
- name: Wait for MySQL
run: |
until mysqladmin ping -h 127.0.0.1 -uroot -prootpass --silent; do
echo "Waiting for database connection..."
sleep 3
done
- name: Cache node modules
uses: actions/cache@v4
env:
cache-name: cache-node-modules
with:
path: ~/.npm
key: ${{ runner.os }}-build-${{ env.cache-name }}-${{ hashFiles('**/package-lock.json') }}
restore-keys: |
${{ runner.os }}-build-${{ env.cache-name }}-
${{ runner.os }}-build-
${{ runner.os }}-
- name: Run CI
run: npm ci
- name: Build Application
run: npm run build
docker-build-and-push:
name: Build and Push Docker Image to ECR
runs-on: ubuntu-latest
needs: nodejs-ci
steps:
- name: Checkout source code
uses: actions/checkout@v4
- name: Configure AWS credentials using OIDC
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ secrets.AWS_ROLE_TO_ASSUME }}
aws-region: ${{ env.AWS_REGION }}
- name: Login to Amazon ECR
uses: aws-actions/amazon-ecr-login@v2
- name: Get AWS Account ID
id: aws-account
run: |
echo "AWS_ACCOUNT_ID=$(aws sts get-caller-identity --query 'Account' --output text)" >> $GITHUB_ENV
- name: Build Docker image
run: |
docker build -t $ECR_REPOSITORY:$IMAGE_TAG .
- name: Tag Docker image
run: |
docker tag $ECR_REPOSITORY:$IMAGE_TAG $AWS_ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com/$ECR_REPOSITORY:$IMAGE_TAG
- name: Push Docker image to ECR
run: |
docker push $AWS_ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com/$ECR_REPOSITORY:$IMAGE_TAG
inject-env-vars:
name: Inject Env Vars from AWS Secrets Manager
runs-on: ubuntu-latest
needs: terraform
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Inject environment variables from Secrets Manager
uses: appleboy/ssh-action@v1.0.0
with:
host: ${{ secrets.EC2_PUBLIC_IP }}
username: ec2-user
key: ${{ secrets.EC2_SSH_PRIVATE_KEY }}
script: |
SECRET_NAME="prod/nestjs-app/envs"
REGION="us-east-1"
ENV_PATH="/home/ec2-user/twitter-backend-node/docker/.env"
sudo mkdir -p /home/ec2-user/twitter-backend-node/docker/
# Create folder if it doesn't exist
sudo mkdir -p "$(dirname "$ENV_PATH")"
# Fetch secrets and create .env file
sudo aws secretsmanager get-secret-value \
--secret-id $SECRET_NAME \
--region $REGION \
--query SecretString \
--output text > "$ENV_PATH"
sudo chown ec2-user:ec2-user "$ENV_PATH"
echo "✅ Secret written to $ENV_PATH"
deploy-to-ec2:
name: Deploy Docker Image to EC2
runs-on: ubuntu-latest
needs: docker-build-and-push
steps:
- name: Checkout repository
uses: actions/checkout@v4
- name: Configure AWS credentials using OIDC
uses: aws-actions/configure-aws-credentials@v4
with:
role-to-assume: ${{ secrets.AWS_ROLE_TO_ASSUME }}
aws-region: ${{ env.AWS_REGION }}
- name: 'Debug: Show current directory files'
run: |
echo "🔍 Listing current workspace files"
ls -la
echo "🔍 Listing docker/ directory files"
ls -la docker/
- name: Fix all permissions
run: chmod -R a+r docker/
- name: Upload docker-compose file to EC2
uses: appleboy/scp-action@v0.1.7
with:
host: ${{ secrets.EC2_PUBLIC_IP }}
username: ec2-user
key: ${{ secrets.EC2_SSH_PRIVATE_KEY }}
source: docker/docker-compose-prod.yml
target: /home/ec2-user/twitter-backend-node/
- name: Confirm docker-compose file is present on EC2
uses: appleboy/ssh-action@v1.0.0
with:
host: ${{ secrets.EC2_PUBLIC_IP }}
username: ec2-user
key: ${{ secrets.EC2_SSH_PRIVATE_KEY }}
script: |
echo "🔍 Verifying uploaded docker-compose file..."
ls -la /home/ec2-user/twitter-backend-node/
if [ -f /home/ec2-user/twitter-backend-node/docker/docker-compose-prod.yml ]; then
echo "✅ docker-compose-prod.yml is present"
else
echo "❌ docker-compose-prod.yml is missing"
exit 1
fi
- name: Deploy to EC2 via SSH
uses: appleboy/ssh-action@v1.0.0
with:
host: ${{ secrets.EC2_PUBLIC_IP }}
username: ec2-user
key: ${{ secrets.EC2_SSH_PRIVATE_KEY }}
script: |
echo "🚀 Starting Docker Compose deployment"
echo "🔧 Ensuring jq is installed..."
if ! command -v jq &> /dev/null; then
sudo yum install -y jq
echo "✅ jq installed"
else
echo "✅ jq already installed"
fi
export AWS_REGION=${{ env.AWS_REGION }}
export AWS_SECRETSMANAGER_PROD_NESTJS_ENV_PATH=${{ secrets.AWS_SECRETSMANAGER_PROD_NESTJS_ENV_PATH }}
export AWS_ACCOUNT_ID=$(aws sts get-caller-identity --query 'Account' --output text)
echo "🔑 Logging in to ECR"
aws ecr get-login-password --region $AWS_REGION | docker login --username AWS --password-stdin $AWS_ACCOUNT_ID.dkr.ecr.$AWS_REGION.amazonaws.com
cd /home/ec2-user/twitter-backend-node
echo "📄 Writing secrets to .env"
aws secretsmanager get-secret-value \
--secret-id $AWS_SECRETSMANAGER_PROD_NESTJS_ENV_PATH \
--region $AWS_REGION \
--query SecretString \
--output text | jq -r 'to_entries[] | "\(.key)=\(.value)"' > docker/.env
echo "📦 Pulling and launching containers"
docker-compose -f docker/docker-compose-prod.yml pull
docker-compose -f docker/docker-compose-prod.yml up -d --remove-orphans
echo "✅ Deployment complete"