# Incheon GIS Platform CI/CD
# - Push to develop: build only
# - Scheduled deploy: "0 18 * * *" (03:00 KST), "10 3 * * *" (12:10 KST) with SCHEDULE_TYPE=deploy
# - Scheduled cleanup: "0 16 * * 0" (01:00 KST Sunday) with SCHEDULE_TYPE=cleanup

variables:
  MAVEN_OPTS: "-Dmaven.repo.local=$CI_PROJECT_DIR/.m2/repository"
  MAVEN_CLI_OPTS: "--batch-mode --errors --fail-at-end --show-version"
  DEPLOY_HOST: "10.100.232.211"
  DEPLOY_USER: "incheon"
  DEPLOY_PATH: "/home/incheon/env/apps/incheon-geo-platform"
  APP_NAME: "incheon-geo-platform"
  APP_PORT: "8080"

cache:
  key: build-cache
  paths:
    - .m2/repository/
    - target/

stages:
  - build
  - deploy
  - verify
  - notify

build:
  stage: build
  image: eclipse-temurin:17-jdk-jammy
  script:
    - echo "WAR build started"
    - ./mvnw $MAVEN_CLI_OPTS clean package -DskipTests
    - WAR_FILE=$(find target -name "*.war" | head -1)
    - WAR_SIZE=$(du -h "$WAR_FILE" | cut -f1)
    - echo "Build completed $WAR_FILE ($WAR_SIZE)"
    - echo "WAR_FILE=$WAR_FILE" > build.env
    - echo "WAR_SIZE=$WAR_SIZE" >> build.env
  artifacts:
    reports:
      dotenv: build.env
    expire_in: 1 hour
  rules:
    - if: $CI_COMMIT_BRANCH == "develop"
    - if: $CI_COMMIT_BRANCH == "main"
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "deploy"

deploy-dev:
  stage: deploy
  image: ubuntu:22.04
  before_script:
    - apt-get update && apt-get install -y openssh-client rsync
    - eval $(ssh-agent -s)
    - echo "$SSH_PRIVATE_KEY" | base64 -d > /tmp/ssh_key
    - chmod 600 /tmp/ssh_key
    - ssh-add /tmp/ssh_key
    - mkdir -p ~/.ssh
    - chmod 700 ~/.ssh
    - ssh-keyscan -H $DEPLOY_HOST >> ~/.ssh/known_hosts
    - chmod 644 ~/.ssh/known_hosts
  script:
    - echo "Deploy started"
    - echo "Target $DEPLOY_USER@$DEPLOY_HOST:$DEPLOY_PATH"
    - echo "Check app status before deploy"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "$DEPLOY_PATH/status-app.sh" || echo "App not running"
    - echo "Upload WAR file"
    - find target -name "*.war" -type f
    - WAR_FILE=$(find target -name "*.war" -type f | head -1)
    - echo "Using WAR file $WAR_FILE"
    - ls -la "$WAR_FILE"
    - scp "$WAR_FILE" $DEPLOY_USER@$DEPLOY_HOST:$DEPLOY_PATH/app.war.new
    - echo "Deploy application"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && if [ -f app.war ]; then cp app.war backup/app.war.\$(date +%Y%m%d_%H%M%S); fi"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && mv app.war.new app.war"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && ./stop-app.sh"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && ./start-app.sh"
    - echo "Deploy completed"
  after_script:
    - ssh-agent -k
  environment:
    name: development
    url: http://10.100.232.211:8080
  rules:
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "deploy"

verify-deployment:
  stage: verify
  image: ubuntu:22.04
  before_script:
    - apt-get update && apt-get install -y curl openssh-client
    - eval $(ssh-agent -s)
    - echo "$SSH_PRIVATE_KEY" | base64 -d > /tmp/ssh_key
    - chmod 600 /tmp/ssh_key
    - ssh-add /tmp/ssh_key
    - mkdir -p ~/.ssh
    - chmod 700 ~/.ssh
    - ssh-keyscan -H $DEPLOY_HOST >> ~/.ssh/known_hosts
  script:
    - echo "Verify deployment started"
    - echo "Check application process"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "$DEPLOY_PATH/status-app.sh"
    - echo "Check port $APP_PORT listening"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "ss -tlnp | grep :$APP_PORT || echo 'Port not listening'"
    - echo "Check HTTP response"
    - for i in {1..30}; do curl -f -s http://10.100.232.211:8080 > /dev/null && echo "HTTP OK after ${i}s" && break || echo "Waiting HTTP ${i}/30"; sleep 1; done
    - echo "Check recent logs"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "tail -20 $DEPLOY_PATH/app.log"
    - echo "Deployment verification completed"
  dependencies:
    - deploy-dev
  rules:
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "deploy"

notify-success:
  stage: notify
  image: alpine:latest
  script:
    - echo "Deploy success notification"
    - echo "$APP_NAME deployment completed successfully"
    - echo "URL http://10.100.232.211:8080"
    - echo "WAR size $WAR_SIZE"
    - echo "Deploy time $(date)"
  dependencies:
    - verify-deployment
  when: on_success
  rules:
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "deploy"

notify-failure:
  stage: notify
  image: alpine:latest
  script:
    - echo "Deploy failure notification"
    - echo "$APP_NAME deployment failed"
    - echo "Please check logs"
  when: on_failure
  rules:
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "deploy"

cleanup:
  stage: notify
  image: ubuntu:22.04
  before_script:
    - apt-get update && apt-get install -y openssh-client
    - eval $(ssh-agent -s)
    - echo "$SSH_PRIVATE_KEY" | base64 -d > /tmp/ssh_key
    - chmod 600 /tmp/ssh_key
    - ssh-add /tmp/ssh_key
    - mkdir -p ~/.ssh
    - chmod 700 ~/.ssh
    - ssh-keyscan -H $DEPLOY_HOST >> ~/.ssh/known_hosts
  script:
    - echo "Server cleanup started"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && find backup/ -name '*.war.*' -mtime +7 -delete 2>/dev/null || true"
    - ssh $DEPLOY_USER@$DEPLOY_HOST "cd $DEPLOY_PATH && if [ -f app.log ] && [ \$(stat -f%z app.log 2>/dev/null || stat -c%s app.log) -gt 104857600 ]; then gzip -c app.log > log/app.log.\$(date +%Y%m%d_%H%M%S).gz && > app.log; fi"
    - echo "Cleanup completed"
  rules:
    - if: $CI_PIPELINE_SOURCE == "schedule" && $SCHEDULE_TYPE == "cleanup"
