169 lines
5.8 KiB
Groovy
169 lines
5.8 KiB
Groovy
pipeline {
|
|
agent any
|
|
|
|
environment {
|
|
PYTHON_VERSION = '3.11'
|
|
NODE_VERSION = '18'
|
|
SUT_URL = 'http://localhost'
|
|
}
|
|
|
|
options {
|
|
timeout(time: 30, unit: 'MINUTES')
|
|
buildDiscarder(logRotator(numToKeepStr: '10'))
|
|
disableConcurrentBuilds()
|
|
}
|
|
|
|
stages {
|
|
stage('Checkout') {
|
|
steps {
|
|
echo 'One does not simply skip the checkout stage...'
|
|
checkout scm
|
|
}
|
|
}
|
|
|
|
stage('Setup Environment') {
|
|
steps {
|
|
echo 'Preparing the Fellowship environment...'
|
|
sh '''
|
|
# Create a Python virtual environment (PEP 668 compliant)
|
|
python3 -m venv venv
|
|
. venv/bin/activate
|
|
python3 -m pip install --upgrade pip setuptools wheel
|
|
echo "✓ Virtual environment ready"
|
|
'''
|
|
}
|
|
}
|
|
|
|
stage('Install Dependencies') {
|
|
parallel {
|
|
stage('Backend Deps') {
|
|
steps {
|
|
echo 'Installing backend dependencies for the Fellowship...'
|
|
sh '''
|
|
. venv/bin/activate
|
|
pip install -r sut/backend/requirements.txt
|
|
pip install -r tests/requirements.txt
|
|
'''
|
|
}
|
|
}
|
|
stage('Frontend Deps') {
|
|
steps {
|
|
echo 'Installing frontend dependencies...'
|
|
sh '''
|
|
cd sut/frontend
|
|
npm ci --prefer-offline || npm install
|
|
'''
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
stage('Lint') {
|
|
steps {
|
|
echo 'The Eye of Sauron watches for code style violations...'
|
|
sh '''
|
|
. venv/bin/activate
|
|
pip install flake8 --quiet
|
|
# E9/F63/F7/F82 = syntax & fatal errors — these must fail the build.
|
|
# Warnings (E1xx, W) are informational only for this tutorial pipeline.
|
|
flake8 sut/backend tests/*.py \
|
|
--count --select=E9,F63,F7,F82 \
|
|
--show-source --statistics
|
|
'''
|
|
}
|
|
}
|
|
|
|
stage('Unit Tests') {
|
|
steps {
|
|
echo 'Running unit tests across the Fellowship...'
|
|
sh '''
|
|
. venv/bin/activate
|
|
mkdir -p reports
|
|
PYTHONPATH=sut/backend python -m pytest \
|
|
tests/backend/services/test_bargaining_algorithm.py \
|
|
tests/backend/services/test_bargaining_config.py \
|
|
tests/backend/services/test_shop_service.py \
|
|
tests/backend/services/test_negotiation_logger.py \
|
|
-v --tb=short \
|
|
--junitxml=reports/unit-tests.xml \
|
|
--no-header \
|
|
--override-ini="addopts=--strict-markers --tb=short -v"
|
|
'''
|
|
}
|
|
post {
|
|
always {
|
|
junit allowEmptyResults: true, testResults: 'reports/unit-tests.xml'
|
|
}
|
|
}
|
|
}
|
|
|
|
stage('Build Frontend') {
|
|
steps {
|
|
echo 'Forging the frontend in the fires of Mount Doom...'
|
|
sh '''
|
|
cd sut/frontend
|
|
npm run build
|
|
'''
|
|
}
|
|
}
|
|
|
|
stage('Integration Tests') {
|
|
steps {
|
|
echo 'The quest continues — running integration tests...'
|
|
sh '''
|
|
. venv/bin/activate
|
|
mkdir -p reports
|
|
PYTHONPATH=sut/backend python -m pytest \
|
|
tests/backend/services/test_bargaining_algorithm.py \
|
|
tests/backend/services/test_bargaining_config.py \
|
|
tests/backend/services/test_shop_service.py \
|
|
tests/backend/services/test_negotiation_logger.py \
|
|
-v --tb=short \
|
|
--junitxml=reports/integration-tests.xml \
|
|
--no-header \
|
|
--override-ini="addopts=--strict-markers --tb=short -v" \
|
|
-m "not realstack"
|
|
'''
|
|
}
|
|
post {
|
|
always {
|
|
junit allowEmptyResults: true, testResults: 'reports/integration-tests.xml'
|
|
}
|
|
}
|
|
}
|
|
|
|
stage('Deploy') {
|
|
when {
|
|
branch 'main'
|
|
}
|
|
steps {
|
|
echo 'Deploying the Fellowship SUT to the land of Docker...'
|
|
sh '''
|
|
cp caddy/Caddyfile.local caddy/Caddyfile
|
|
docker compose down --remove-orphans || true
|
|
docker compose up -d --build
|
|
'''
|
|
}
|
|
}
|
|
}
|
|
|
|
post {
|
|
always {
|
|
echo 'The journey is complete — collecting artifacts...'
|
|
archiveArtifacts artifacts: 'reports/**/*.xml', allowEmptyArchive: true
|
|
}
|
|
success {
|
|
echo 'The Fellowship has succeeded! The quest is complete.'
|
|
}
|
|
failure {
|
|
echo 'The Fellowship has failed! Sauron grows stronger...'
|
|
mail to: 'fellowship@middle-earth.local',
|
|
subject: "Build Failed: ${env.JOB_NAME} [${env.BUILD_NUMBER}]",
|
|
body: "The Ring has been lost. Build ${env.BUILD_URL} has failed."
|
|
}
|
|
unstable {
|
|
echo 'The quest is unstable — some tests did not pass.'
|
|
}
|
|
}
|
|
}
|