This commit is contained in:
2026-05-07 18:50:15 +09:30
parent 1682fda5e7
commit 80d0502608
2 changed files with 271 additions and 174 deletions
-174
View File
@@ -1,174 +0,0 @@
stages:
- build
- build-sonar
- test
- docker
- deploy
variables:
DOCKER_IMAGE: ${CI_REGISTRY_IMAGE}:${CI_COMMIT_SHORT_SHA}
DOCKER_IMAGE_LATEST: ${CI_REGISTRY_IMAGE}:latest
DOCKER_DRIVER: overlay2
DOCKER_TLS_CERTDIR: ""
SONAR_USER_HOME: "${CI_PROJECT_DIR}/.sonar"
GIT_DEPTH: "0"
# Build stage - compile Java and frontend
build:java:
stage: build
image: eclipse-temurin:21-jdk
services:
- postgres:17-alpine
variables:
POSTGRES_DB: mtgsearch_build
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
DB_URL: jdbc:postgresql://postgres:5432/mtgsearch_build
DB_USER: postgres
DB_PASSWORD: postgres
before_script:
- apt-get update && apt-get install -y curl
- curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
- apt-get install -y nodejs
script:
- chmod +x ./gradlew
- ./gradlew clean build -x test --build-cache
artifacts:
paths:
- backend/build/libs/
- frontend/dist/
expire_in: 1 day
cache:
key: ${CI_COMMIT_REF_SLUG}
paths:
- .gradle/
- frontend/node_modules/
# Test stage - run unit and integration tests
test:unit:
stage: test
image: eclipse-temurin:21-jdk
needs:
- build:java
script:
- chmod +x ./gradlew
- ./gradlew test --build-cache
artifacts:
reports:
junit: backend/build/test-results/test/**/*.xml
paths:
- backend/build/reports/
expire_in: 30 days
cache:
key: ${CI_COMMIT_REF_SLUG}
paths:
- .gradle/
# Integration tests with Postgres
test:integration:
stage: test
image: eclipse-temurin:21-jdk
services:
- postgres:17-alpine
variables:
POSTGRES_DB: mtgsearch_test
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
SPRING_DATASOURCE_URL: jdbc:postgresql://postgres:5432/mtgsearch_test
script:
- chmod +x ./gradlew
- ./gradlew integrationTest --build-cache
only:
- main
- merge_requests
cache:
key: ${CI_COMMIT_REF_SLUG}
paths:
- .gradle/
# Code quality checks
test:quality:
stage: test
image: eclipse-temurin:21-jdk
script:
- chmod +x ./gradlew
- ./gradlew check -x test
allow_failure: true
only:
- merge_requests
build-sonar:
stage: build-sonar
image: gradle:9.4.1-jdk21-jammy
cache:
policy: pull-push
key: "sonar-cache-$CI_COMMIT_REF_SLUG"
paths:
- "${SONAR_USER_HOME}/cache"
- sonar-scanner/
script: gradle sonar
allow_failure: true
rules:
- if: $CI_PIPELINE_SOURCE == 'merge_request_event'
- if: $CI_COMMIT_BRANCH == 'master'
- if: $CI_COMMIT_BRANCH == 'main'
- if: $CI_COMMIT_BRANCH == 'develop'
# Docker build and push
docker:build:
stage: docker
image: docker:latest
services:
- docker:dind
needs:
- build:java
before_script:
- docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
script:
- docker build -t $DOCKER_IMAGE .
- docker push $DOCKER_IMAGE
- docker tag $DOCKER_IMAGE $DOCKER_IMAGE_LATEST
- docker push $DOCKER_IMAGE_LATEST
only:
- main
- develop
- tags
# Deploy to staging (example - configure for your environment)
deploy:staging:
stage: deploy
image: alpine:latest
before_script:
- apk add --no-cache curl jq
script:
- echo "Deploying to staging environment..."
- |
curl -X POST "${STAGING_DEPLOY_WEBHOOK}" \
-H "Content-Type: application/json" \
-d '{"image":"'"${DOCKER_IMAGE}"'"}'
environment:
name: staging
url: https://staging-mtgsearch.example.com
only:
- develop
when: manual
# Deploy to production (example - configure for your environment)
deploy:production:
stage: deploy
image: alpine:latest
before_script:
- apk add --no-cache curl jq
script:
- echo "Deploying to production..."
- |
curl -X POST "${PROD_DEPLOY_WEBHOOK}" \
-H "Content-Type: application/json" \
-d '{"image":"'"${DOCKER_IMAGE}"'"}'
environment:
name: production
url: https://mtgsearch.example.com
only:
- tags
- main
when: manual
Vendored
+271
View File
@@ -0,0 +1,271 @@
pipeline {
agent any
options {
timestamps()
timeout(time: 1, unit: 'HOURS')
buildDiscarder(logRotator(numToKeepStr: '10'))
}
parameters {
booleanParam(name: 'DEPLOY_TO_STAGING', defaultValue: false, description: 'Deploy to staging')
booleanParam(name: 'DEPLOY_TO_PRODUCTION', defaultValue: false, description: 'Deploy to production')
}
environment {
// Docker registry configuration
REGISTRY = credentials('docker-registry-url')
REGISTRY_USER = credentials('docker-registry-user')
REGISTRY_PASSWORD = credentials('docker-registry-password')
DOCKER_IMAGE = "${REGISTRY}/${GIT_COMMIT.take(8)}"
DOCKER_IMAGE_LATEST = "${REGISTRY}:latest"
// Database configuration for builds
DB_URL = "jdbc:postgresql://postgres:5432/mtgsearch_build"
DB_USER = "postgres"
DB_PASSWORD = "postgres"
POSTGRES_DB = "mtgsearch_build"
// SonarQube configuration
SONAR_USER_HOME = "${WORKSPACE}/.sonar"
GIT_DEPTH = "0"
// Build cache
GRADLE_USER_HOME = "${WORKSPACE}/.gradle"
}
stages {
stage('Build Java & Frontend') {
agent {
docker {
image 'eclipse-temurin:21-jdk'
args '--network=host'
}
}
steps {
script {
echo "Building Java and Frontend..."
}
sh '''
apt-get update && apt-get install -y curl
curl -fsSL https://deb.nodesource.com/setup_20.x | bash -
apt-get install -y nodejs
chmod +x ./gradlew
./gradlew clean build -x test --build-cache
'''
}
post {
success {
archiveArtifacts artifacts: 'backend/build/libs/**/*.jar,frontend/dist/**/*', fingerprint: true
}
}
}
stage('Run Unit Tests') {
agent {
docker {
image 'eclipse-temurin:21-jdk'
args '--network=host'
}
}
steps {
script {
echo "Running unit tests..."
}
sh '''
chmod +x ./gradlew
./gradlew test --build-cache
'''
}
post {
always {
junit 'backend/build/test-results/test/**/*.xml'
publishHTML([
reportDir: 'backend/build/reports',
reportFiles: 'index.html',
reportName: 'Test Report'
])
}
}
}
stage('Run Integration Tests') {
agent {
docker {
image 'eclipse-temurin:21-jdk'
args '--network=host'
}
}
when {
anyOf {
branch 'main'
branch 'develop'
branch 'master'
}
}
steps {
script {
echo "Running integration tests..."
}
sh '''
chmod +x ./gradlew
./gradlew integrationTest --build-cache
'''
}
post {
always {
junit 'backend/build/test-results/integrationTest/**/*.xml'
}
}
}
stage('Code Quality Checks') {
agent {
docker {
image 'eclipse-temurin:21-jdk'
args '--network=host'
}
}
when {
changeRequest()
}
steps {
script {
echo "Running code quality checks..."
}
sh '''
chmod +x ./gradlew
./gradlew check -x test
'''
}
post {
failure {
echo "Quality checks failed - continuing pipeline with warning"
}
}
}
stage('SonarQube Analysis') {
agent {
docker {
image 'gradle:9.4.1-jdk21-jammy'
args '--network=host'
}
}
when {
anyOf {
changeRequest()
branch 'main'
branch 'master'
branch 'develop'
}
}
steps {
script {
echo "Running SonarQube analysis..."
}
withSonarQubeEnv('SonarQube') {
sh 'gradle sonar'
}
}
post {
failure {
echo "SonarQube analysis failed - continuing pipeline with warning"
}
}
}
stage('Build Docker Image') {
agent {
docker {
image 'docker:latest'
args '-v /var/run/docker.sock:/var/run/docker.sock'
}
}
when {
anyOf {
branch 'main'
branch 'develop'
branch 'master'
tag "*"
}
}
steps {
script {
echo "Building Docker image..."
}
sh '''
docker login -u ${REGISTRY_USER} -p ${REGISTRY_PASSWORD} ${REGISTRY}
docker build -t ${DOCKER_IMAGE} .
docker push ${DOCKER_IMAGE}
docker tag ${DOCKER_IMAGE} ${DOCKER_IMAGE_LATEST}
docker push ${DOCKER_IMAGE_LATEST}
docker logout ${REGISTRY}
'''
}
}
stage('Deploy to Staging') {
when {
allOf {
branch 'develop'
expression { params.DEPLOY_TO_STAGING == true }
}
}
steps {
script {
echo "Deploying to staging environment..."
input(id: 'DeployToStaging', message: 'Deploy to staging?', ok: 'Deploy')
}
sh '''
curl -X POST "${STAGING_DEPLOY_WEBHOOK}" \
-H "Content-Type: application/json" \
-d '{"image":"${DOCKER_IMAGE}"}'
echo "Deployment to staging triggered"
'''
}
}
stage('Deploy to Production') {
when {
anyOf {
allOf {
branch 'main'
expression { params.DEPLOY_TO_PRODUCTION == true }
}
tag "*"
}
}
steps {
script {
echo "Deploying to production environment..."
input(id: 'DeployToProd', message: 'Deploy to production?', ok: 'Deploy')
}
sh '''
curl -X POST "${PROD_DEPLOY_WEBHOOK}" \
-H "Content-Type: application/json" \
-d '{"image":"${DOCKER_IMAGE}"}'
echo "Deployment to production triggered"
'''
}
}
}
post {
always {
cleanWs()
}
failure {
script {
echo "Pipeline failed! Check logs for details."
// You can add notification logic here
}
}
success {
script {
echo "Pipeline completed successfully!"
// You can add notification logic here
}
}
}
}