Add SonarQube setup script

This commit is contained in:
2026-03-28 16:35:10 +01:00
parent abe0bcd22f
commit 90865d0b4c

219
setup-sonarqube.sh Normal file
View File

@@ -0,0 +1,219 @@
#!/bin/bash
set -euo pipefail
# =============================================================================
# SonarQube Community Edition Setup Script
# Target: Debian 13 LXC container on Proxmox
# Installs: PostgreSQL 17, Java 17, SonarQube 26.3.0
# =============================================================================
SONAR_VERSION="26.3.0.120487"
SONAR_URL="https://binaries.sonarsource.com/Distribution/sonarqube/sonarqube-${SONAR_VERSION}.zip"
SONAR_HOME="/opt/sonarqube"
SONAR_USER="sonar"
DB_USER="sonarqube"
DB_PASS="sq_$(head -c 16 /dev/urandom | base64 | tr -dc 'a-zA-Z0-9' | head -c 20)"
DB_NAME="sonarqube"
ADMIN_PASS="CameleerSQ2026!"
echo "=============================="
echo " SonarQube Setup Starting"
echo "=============================="
echo ""
# --- Step 1: Kernel parameters ---
echo "[1/8] Configuring kernel parameters..."
cat > /etc/sysctl.d/99-sonarqube.conf <<'SYSCTL'
vm.max_map_count=524288
fs.file-max=131072
SYSCTL
sysctl -p /etc/sysctl.d/99-sonarqube.conf
cat > /etc/security/limits.d/99-sonarqube.conf <<'LIMITS'
sonar - nofile 131072
sonar - nproc 8192
LIMITS
# --- Step 2: Install packages ---
echo "[2/8] Installing PostgreSQL and Java 17..."
export DEBIAN_FRONTEND=noninteractive
apt-get update -qq
apt-get install -y -qq postgresql openjdk-17-jre-headless unzip curl > /dev/null 2>&1
echo " PostgreSQL $(pg_config --version) installed"
echo " Java $(java -version 2>&1 | head -1) installed"
# --- Step 3: Configure PostgreSQL ---
echo "[3/8] Configuring PostgreSQL database..."
systemctl enable --now postgresql
su - postgres -c "psql -c \"CREATE USER ${DB_USER} WITH PASSWORD '${DB_PASS}';\"" 2>/dev/null || true
su - postgres -c "psql -c \"CREATE DATABASE ${DB_NAME} OWNER ${DB_USER};\"" 2>/dev/null || true
su - postgres -c "psql -c \"GRANT ALL PRIVILEGES ON DATABASE ${DB_NAME} TO ${DB_USER};\""
echo " Database '${DB_NAME}' ready"
# --- Step 4: Create sonar user ---
echo "[4/8] Creating sonar system user..."
id ${SONAR_USER} &>/dev/null || useradd -r -m -d /home/${SONAR_USER} -s /bin/bash ${SONAR_USER}
# --- Step 5: Download and install SonarQube ---
echo "[5/8] Downloading SonarQube ${SONAR_VERSION} (~900MB, this may take a few minutes)..."
cd /tmp
if [ ! -f "sonarqube-${SONAR_VERSION}.zip" ]; then
curl -# -L -o "sonarqube-${SONAR_VERSION}.zip" "${SONAR_URL}"
fi
echo " Extracting..."
rm -rf /tmp/sonarqube-${SONAR_VERSION}
unzip -q "sonarqube-${SONAR_VERSION}.zip" -d /tmp/
rm -rf ${SONAR_HOME}
mv "/tmp/sonarqube-${SONAR_VERSION}" "${SONAR_HOME}"
chown -R ${SONAR_USER}:${SONAR_USER} ${SONAR_HOME}
# --- Step 6: Configure SonarQube ---
echo "[6/8] Configuring SonarQube..."
SONAR_CONF="${SONAR_HOME}/conf/sonar.properties"
# Database
sed -i 's|^#sonar.jdbc.username=.*|sonar.jdbc.username='"${DB_USER}"'|' "${SONAR_CONF}"
sed -i 's|^#sonar.jdbc.password=.*|sonar.jdbc.password='"${DB_PASS}"'|' "${SONAR_CONF}"
sed -i 's|^#sonar.jdbc.url=jdbc:postgresql.*|sonar.jdbc.url=jdbc:postgresql://localhost:5432/'"${DB_NAME}"'|' "${SONAR_CONF}"
# Web server
sed -i 's|^#sonar.web.host=.*|sonar.web.host=0.0.0.0|' "${SONAR_CONF}"
sed -i 's|^#sonar.web.port=.*|sonar.web.port=9000|' "${SONAR_CONF}"
# Elasticsearch (use temp dir inside sonar home)
mkdir -p "${SONAR_HOME}/temp"
chown -R ${SONAR_USER}:${SONAR_USER} "${SONAR_HOME}"
# --- Step 7: Create systemd service ---
echo "[7/8] Creating systemd service..."
cat > /etc/systemd/system/sonarqube.service <<EOF
[Unit]
Description=SonarQube
After=network.target postgresql.service
Requires=postgresql.service
[Service]
Type=forking
User=${SONAR_USER}
Group=${SONAR_USER}
ExecStart=${SONAR_HOME}/bin/linux-x86-64/sonar.sh start
ExecStop=${SONAR_HOME}/bin/linux-x86-64/sonar.sh stop
LimitNOFILE=131072
LimitNPROC=8192
Restart=on-failure
RestartSec=10
[Install]
WantedBy=multi-user.target
EOF
systemctl daemon-reload
systemctl enable sonarqube
systemctl start sonarqube
# --- Step 8: Wait for SonarQube and configure projects ---
echo "[8/8] Waiting for SonarQube to start (this can take 2-5 minutes)..."
SONAR_API="http://localhost:9000/api"
for i in $(seq 1 60); do
STATUS=$(curl -sf "${SONAR_API}/system/status" 2>/dev/null | tr -d '{}' | tr ',' '\n' | grep '"status"' | cut -d'"' -f4 || echo "STARTING")
if [ "${STATUS}" = "UP" ]; then
break
fi
echo " ... ${STATUS} (attempt ${i}/60)"
sleep 10
done
STATUS=$(curl -sf "${SONAR_API}/system/status" 2>/dev/null | tr -d '{}' | tr ',' '\n' | grep '"status"' | cut -d'"' -f4 || echo "UNKNOWN")
if [ "${STATUS}" != "UP" ]; then
echo "ERROR: SonarQube did not start. Check: journalctl -u sonarqube"
echo " Also check: ${SONAR_HOME}/logs/"
exit 1
fi
echo ""
echo " SonarQube is UP!"
echo ""
# Change default admin password
echo "Changing admin password..."
curl -sf -u admin:admin -X POST "${SONAR_API}/users/change_password" \
-d "login=admin&previousPassword=admin&password=${ADMIN_PASS}" || echo " (password may already be changed)"
# Create projects
echo "Creating projects..."
PROJECTS=("cameleer3:cameleer3:main" "cameleer3-server:cameleer3-server:main" "design-system:design-system:main" "cameleer-build-images:cameleer-build-images:main")
for proj_info in "${PROJECTS[@]}"; do
IFS=':' read -r key name branch <<< "${proj_info}"
curl -sf -u admin:"${ADMIN_PASS}" -X POST "${SONAR_API}/projects/create" \
-d "project=${key}&name=${name}&mainBranch=${branch}" > /dev/null 2>&1 || true
echo " Created project: ${name}"
done
# Generate a global analysis token
echo ""
echo "Generating analysis token..."
TOKEN_RESPONSE=$(curl -sf -u admin:"${ADMIN_PASS}" -X POST "${SONAR_API}/user_tokens/generate" \
-d "name=cameleer-scanner&type=GLOBAL_ANALYSIS" 2>/dev/null || echo "")
TOKEN=$(echo "${TOKEN_RESPONSE}" | tr ',' '\n' | grep '"token"' | cut -d'"' -f4)
# Also enable SSH for future access
echo "Enabling SSH root login..."
sed -i 's/^#\?PermitRootLogin.*/PermitRootLogin yes/' /etc/ssh/sshd_config
systemctl restart sshd 2>/dev/null || true
# --- Done ---
echo ""
echo "======================================================"
echo " SonarQube Setup Complete!"
echo "======================================================"
echo ""
echo " URL: http://sonarqube.siegeln.internal:9000"
echo " Admin user: admin"
echo " Admin password: ${ADMIN_PASS}"
echo ""
echo " DB user: ${DB_USER}"
echo " DB password: ${DB_PASS}"
echo " DB name: ${DB_NAME}"
echo ""
if [ -n "${TOKEN}" ]; then
echo " Scanner Token: ${TOKEN}"
echo " (type: GLOBAL_ANALYSIS, name: cameleer-scanner)"
fi
echo ""
echo " Projects created:"
echo " - cameleer3 (Java)"
echo " - cameleer3-server (Java)"
echo " - design-system (TypeScript)"
echo " - cameleer-build-images (Dockerfile)"
echo ""
echo " SSH root login has been enabled."
echo ""
echo "======================================================"
echo ""
echo " SCAN COMMANDS:"
echo ""
echo " Java (Maven) projects:"
echo " mvn sonar:sonar \\"
echo " -Dsonar.host.url=http://sonarqube.siegeln.internal:9000 \\"
echo " -Dsonar.token=${TOKEN} \\"
echo " -Dsonar.projectKey=<cameleer3|cameleer3-server>"
echo ""
echo " TypeScript/JS projects:"
echo " npx sonar-scanner \\"
echo " -Dsonar.host.url=http://sonarqube.siegeln.internal:9000 \\"
echo " -Dsonar.token=${TOKEN} \\"
echo " -Dsonar.projectKey=design-system \\"
echo " -Dsonar.sources=src"
echo ""
echo " Generic projects:"
echo " npx sonar-scanner \\"
echo " -Dsonar.host.url=http://sonarqube.siegeln.internal:9000 \\"
echo " -Dsonar.token=${TOKEN} \\"
echo " -Dsonar.projectKey=cameleer-build-images \\"
echo " -Dsonar.sources=."
echo "======================================================"