pipeline { agent any environment { // Tag images with the build number so they are unique APP_FRONTEND_NAME = "chore-app-frontend" APP_BACKEND_NAME = "chore-app-backend" IMAGE_FRONTEND_NAME = "${APP_FRONTEND_NAME}:${env.BUILD_ID}" IMAGE_BACKEND_NAME = "${APP_BACKEND_NAME}:${env.BUILD_ID}" CONTAINER_FRONTEND_NAME = "${APP_FRONTEND_NAME}" CONTAINER_BACKEND_NAME = "${APP_BACKEND_NAME}" NETWORK_NAME = "chore-app-net" } stages { stage('Checkout') { steps { // Pulls code from your configured Git repo checkout scm } } stage('Set Version') { steps { script { // Extract BASE_VERSION from Python file using grep env.BASE_VERSION = sh( script: "grep '^BASE_VERSION' config/version.py | cut -d'\"' -f2", returnStdout: true ).trim() echo "BASE_VERSION set to: ${env.BASE_VERSION}" } } } stage('Build Frontend (Vue) App') { steps { dir('web/vue-app') { sh """docker build --build-arg APP_BUILD=${BUILD_NUMBER} -t ${APP_FRONTEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} .""" } } } stage('Build Backend (Flask) App') { steps { dir('.') { sh """docker build --build-arg APP_BUILD=${BUILD_NUMBER} -t ${APP_BACKEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} .""" } } } stage('Deploy') { steps { echo 'Stopping and removing old containers...' sh "docker stop ${CONTAINER_FRONTEND_NAME} || true" sh "docker rm ${CONTAINER_FRONTEND_NAME} || true" sh "docker stop ${CONTAINER_BACKEND_NAME} || true" sh "docker rm ${CONTAINER_BACKEND_NAME} || true" echo 'Cleaning up and creating network...' sh "docker network rm -f ${NETWORK_NAME} || true" sh "docker network create ${NETWORK_NAME}" echo "Starting new containers" sh """ docker run -d \\ --name ${CONTAINER_FRONTEND_NAME} \\ --network ${NETWORK_NAME} \\ -p 443:443 \\ ${APP_FRONTEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} """ sh """ docker run -d \\ --name ${CONTAINER_BACKEND_NAME} \\ --network ${NETWORK_NAME} \\ -e BUILD_NUMBER=${BUILD_NUMBER} \\ -v ${CONTAINER_BACKEND_NAME}_data:/app/data \\ ${APP_BACKEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} """ echo 'Deployment complete!' } } stage('Cleanup') { steps { echo 'Removing old/dangling Docker images...' // Remove all images that are not associated with a container // This targets the untagged images created by previous builds sh 'docker system prune -a -f' // OPTIONAL: Remove images older than a certain time (e.g., 24 hours) // This is useful if you want to keep the most recent successful images // for quick rollback, but remove others. // sh 'docker image prune -a -f --filter "until=24h"' echo 'Docker images pruned.' // Optional: Stop old containers and run the new ones // Note: In production, you would push to a registry (DockerHub) instead sh "echo 'Build Complete. Images ready: ${IMAGE_FRONTEND_NAME} and ${IMAGE_BACKEND_NAME}'" } } stage('Tag Latest') { steps { echo 'Tagging deployed images as latest...' sh "docker tag ${APP_FRONTEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} ${APP_FRONTEND_NAME}:latest" sh "docker tag ${APP_BACKEND_NAME}:${BASE_VERSION}-${BUILD_NUMBER} ${APP_BACKEND_NAME}:latest" } } } }