#!/usr/bin/env python3
"""
Jenkins配置脚本 - 配置凭证和创建流水线任务
"""

import requests
import json
import base64
import sys
from urllib.parse import quote

# Jenkins配置
JENKINS_URL = "http://localhost:8099"
JENKINS_USER = "fzxadmin"
JENKINS_PASSWORD = "FzxAdmin@2026"

# Git配置
GIT_URL = "https://codeup.aliyun.com/69c68bacfa2a62bc85952a67/FzxBdsh.git"

# 镜像仓库配置
REGISTRY_HOST = "8.140.221.49:5000"

def get_crumb():
    """获取CSRF crumb"""
    response = requests.get(f"{JENKINS_URL}/crumbIssuer/api/json", auth=(JENKINS_USER, JENKINS_PASSWORD))
    if response.status_code == 200:
        return response.json()
    return None

def create_username_password_credential(credential_id, username, password, description):
    """创建用户名密码凭证"""
    crumb = get_crumb()
    if not crumb:
        print("❌ 无法获取CSRF crumb")
        return False
    
    # 先删除已存在的凭证
    try:
        requests.post(
            f"{JENKINS_URL}/credentials/store/system/domain/_/doDelete",
            data={"credential_id": credential_id},
            auth=(JENKINS_USER, JENKINS_PASSWORD),
            headers={"Jenkins-Crumb": crumb["crumbRequestField"]}
        )
    except:
        pass
    
    # 创建新凭证
    payload = {
        "": "com.cloudbees.plugins.credentials.impl.UsernamePasswordCredentialsImpl",
        "scope": "GLOBAL",
        "id": credential_id,
        "username": username,
        "password": password,
        "description": description,
        "$class": "com.cloudbees.plugins.credentials.impl.UsernamePasswordCredentialsImpl"
    }
    
    response = requests.post(
        f"{JENKINS_URL}/credentials/store/system/domain/_/createCredentials",
        data=payload,
        auth=(JENKINS_USER, JENKINS_PASSWORD),
        headers={"Jenkins-Crumb": crumb["crumbRequestField"]}
    )
    
    if response.status_code in [200, 303]:
        print(f"✅ 凭证 {credential_id} 创建成功")
        return True
    else:
        print(f"❌ 凭证 {credential_id} 创建失败: {response.status_code}")
        return False

def create_secret_text_credential(credential_id, secret, description):
    """创建密钥文本凭证"""
    crumb = get_crumb()
    if not crumb:
        print("❌ 无法获取CSRF crumb")
        return False
    
    # 先删除已存在的凭证
    try:
        requests.post(
            f"{JENKINS_URL}/credentials/store/system/domain/_/doDelete",
            data={"credential_id": credential_id},
            auth=(JENKINS_USER, JENKINS_PASSWORD),
            headers={"Jenkins-Crumb": crumb["crumbRequestField"]}
        )
    except:
        pass
    
    # Base64编码密钥
    secret_b64 = base64.b64encode(secret.encode()).decode()
    
    payload = {
        "": "org.jenkinsci.plugins.plainstyle.impl.StringCredentialsImpl",
        "scope": "GLOBAL",
        "id": credential_id,
        "secret": secret_b64,
        "description": description,
        "$class": "org.jenkinsci.plugins.plainstyle.impl.StringCredentialsImpl"
    }
    
    response = requests.post(
        f"{JENKINS_URL}/credentials/store/system/domain/_/createCredentials",
        data=payload,
        auth=(JENKINS_USER, JENKINS_PASSWORD),
        headers={"Jenkins-Crumb": crumb["crumbRequestField"]}
    )
    
    if response.status_code in [200, 303]:
        print(f"✅ 密钥凭证 {credential_id} 创建成功")
        return True
    else:
        print(f"❌ 密钥凭证 {credential_id} 创建失败: {response.status_code}")
        return False

def create_job(job_name, config_xml):
    """创建或更新Jenkins任务"""
    # URL编码任务名称
    encoded_job_name = quote(job_name, safe='')
    
    # 先尝试获取crumb
    try:
        crumb = get_crumb()
        if not crumb:
            print("⚠️  无法获取CSRF crumb，尝试不使用crumb创建任务...")
            crumb = {"crumbRequestField": "Jenkins-Crumb", "crumb": ""}
    except Exception as e:
        print(f"⚠️  获取crumb失败: {e}")
        crumb = {"crumbRequestField": "Jenkins-Crumb", "crumb": ""}
    
    # 检查任务是否存在
    response = requests.get(
        f"{JENKINS_URL}/job/{encoded_job_name}/config.xml",
        auth=(JENKINS_USER, JENKINS_PASSWORD)
    )
    
    if response.status_code == 200:
        # 任务已存在，需要更新
        print(f"📝 任务 {job_name} 已存在，正在更新...")
        url = f"{JENKINS_URL}/job/{encoded_job_name}/config.xml"
    else:
        # 任务不存在，需要创建
        print(f"🆕 创建任务 {job_name}...")
        url = f"{JENKINS_URL}/createItem?name={quote(job_name, safe='')}"
    
    response = requests.post(
        url,
        data=config_xml.encode('utf-8'),
        auth=(JENKINS_USER, JENKINS_PASSWORD),
        headers={
            "Jenkins-Crumb": crumb["crumbRequestField"],
            "Content-Type": "application/xml; charset=utf-8"
        }
    )
    
    if response.status_code in [200, 201, 302]:
        print(f"✅ 任务 {job_name} {'更新' if response.status_code == 200 else '创建'}成功")
        return True
    else:
        print(f"❌ 任务 {job_name} {'更新' if response.status_code == 200 else '创建'}失败: {response.status_code}")
        print(f"   响应: {response.text[:200]}")
        return False

def create_pipeline_job():
    """创建主流水线任务"""
    
    config = """<?xml version='1.1' encoding='UTF-8'?>
<flow-definition plugin="workflow-job">
  <description>主流水线 - 构建和部署所有服务到阿里云开发环境</description>
  <keepDependencies>false</keepDependencies>
  <properties>
    <jenkins.model.BuildDiscarderProperty>
      <daysToKeep>7</daysToKeep>
      <numToKeep>5</numToKeep>
      <artifactDaysToKeep>7</artifactDaysToKeep>
      <artifactNumToKeep>3</artifactNumToKeep>
    </jenkins.model.BuildDiscarderProperty>
    <jenkins.triggers.ReverseBuildTrigger>
      <spec></spec>
      <upstreamProjects></upstreamProjects>
    </jenkins.triggers.ReverseBuildTrigger>
  </properties>
  <definition class="org.jenkinsci.plugins.workflow.cps.CpsScmFlowDefinition" plugin="workflow-cps">
    <scm class="hudson.plugins.git.GitSCM" plugin="git">
      <configVersion>2</configVersion>
      <userRemoteConfigs>
        <hudson.plugins.git.UserRemoteConfig>
          <url>{git_url}</url>
          <credentialsId>aliyun-codeup-https</credentialsId>
        </hudson.plugins.git.UserRemoteConfig>
      </userRemoteConfigs>
      <branches>
        <hudson.plugins.git.BranchSpec>
          <name>*/develop</name>
        </hudson.plugins.git.BranchSpec>
      </branches>
    </scm>
    <scriptPath>Jenkinsfile</scriptPath>
    <lightweight>true</lightweight>
  </definition>
  <triggers/>
  <disabled>false</disabled>
</flow-definition>""".format(git_url=GIT_URL)
    
    return create_job("Fzx-Platform-Pipeline", config)

def create_build_job():
    """创建构建任务"""
    
    config = """<?xml version='1.1' encoding='UTF-8'?>
<project>
  <description>构建任务 - 编译打包后端微服务和前端应用</description>
  <keepDependencies>false</keepDependencies>
  <properties>
    <jenkins.model.BuildDiscarderProperty>
      <daysToKeep>7</daysToKeep>
      <numToKeep>5</numToKeep>
      <artifactDaysToKeep>7</artifactDaysToKeep>
      <artifactNumToKeep>3</artifactNumToKeep>
    </jenkins.model.BuildDiscarderProperty>
  </properties>
  <scm class="hudson.plugins.git.GitSCM">
    <configVersion>2</configVersion>
    <userRemoteConfigs>
      <hudson.plugins.git.UserRemoteConfig>
        <url>{git_url}</url>
        <credentialsId>aliyun-codeup-https</credentialsId>
      </hudson.plugins.git.UserRemoteConfig>
    </userRemoteConfigs>
    <branches>
      <hudson.plugins.git.BranchSpec>
        <name>*/develop</name>
      </hudson.plugins.git.BranchSpec>
    </branches>
  </scm>
  <canRoam>true</canRoam>
  <disabled>false</disabled>
  <blockBuildWhenDownstreamBuilding>false</blockBuildWhenDownstreamBuilding>
  <blockBuildWhenUpstreamBuilding>false</blockBuildWhenUpstreamBuilding>
  <triggers/>
  <concurrentBuild>false</concurrentBuild>
  <builders>
    <hudson.tasks.Shell>
      <command>#!/bin/bash
set -e

echo "========================================"
echo "开始构建 Fzx 本地生活平台"
echo "========================================"

# 准备构建目录
BUILD_DIR="/tmp/jenkins-build-$$"
mkdir -p "$BUILD_DIR"

# 复制代码到构建目录
cp -r /var/jenkins/workspace/Fzx-Build/* "$BUILD_DIR/" 2>/dev/null || {
    echo "首次构建，初始化工作目录..."
    mkdir -p /var/jenkins/workspace/Fzx-Build
}

# 进入项目目录
cd "$BUILD_DIR"

# 设置Maven版本
export VERSION="v1.0.0-build-$(date +%Y%m%d%H%M%S)"
echo "构建版本: $VERSION"

# 安装依赖到本地Maven仓库
echo "安装依赖到Maven仓库..."
mvn install -DskipTests -N || true

# 构建common-service
echo "构建 common-service..."
cd services/common-service && mvn clean install -DskipTests && cd ../..

# 并行构建其他服务
echo "构建其他微服务..."
for service in api-gateway auth-service user-service map-service order-service merchant-service platform-service product-service rider-service upload-service marketing-service; do
    echo "构建 $service..."
    cd services/$service
    mvn clean package -DskipTests
    cd ../..
done

# 构建前端应用
echo "构建前端应用..."
if [ -d "frontend/user_app" ]; then
    cd frontend/user_app
    flutter pub get
    flutter build web
    cd ../..
fi

if [ -d "frontend/rider_app" ]; then
    cd frontend/rider_app
    flutter pub get
    flutter build web
    cd ../..
fi

echo "========================================"
echo "构建完成！"
echo "========================================"
</command>
    </hudson.tasks.Shell>
  </builders>
  <publishers/>
  <buildWrappers/>
</project>""".format(git_url=GIT_URL)
    
    return create_job("Fzx-Build", config)

def create_deploy_job():
    """创建部署任务"""
    
    config = """<?xml version='1.1' encoding='UTF-8'?>
<project>
  <description>部署任务 - 部署服务到阿里云开发环境</description>
  <keepDependencies>false</keepDependencies>
  <properties>
    <jenkins.model.BuildDiscarderProperty>
      <daysToKeep>7</daysToKeep>
      <numToKeep>5</numToKeep>
      <artifactDaysToKeep>7</artifactDaysToKeep>
      <artifactNumToKeep>3</artifactNumToKeep>
    </jenkins.model.BuildDiscarderProperty>
  </properties>
  <scm class="hudson.plugins.git.GitSCM">
    <configVersion>2</configVersion>
    <userRemoteConfigs>
      <hudson.plugins.git.UserRemoteConfig>
        <url>{git_url}</url>
        <credentialsId>aliyun-codeup-https</credentialsId>
      </hudson.plugins.git.UserRemoteConfig>
    </userRemoteConfigs>
    <branches>
      <hudson.plugins.git.BranchSpec>
        <name>*/develop</name>
      </hudson.plugins.git.BranchSpec>
    </branches>
  </scm>
  <canRoam>true</canRoam>
  <disabled>false</disabled>
  <blockBuildWhenDownstreamBuilding>false</blockBuildWhenDownstreamBuilding>
  <blockBuildWhenUpstreamBuilding>false</blockBuildWhenUpstreamBuilding>
  <triggers/>
  <concurrentBuild>false</concurrentBuild>
  <builders>
    <hudson.tasks.Shell>
      <command>#!/bin/bash
set -e

echo "========================================"
echo "开始部署到阿里云开发环境"
echo "========================================"

# 部署配置
DEPLOY_HOST="8.140.221.49"
DEPLOY_USER="root"
SSH_KEY="/var/lib/jenkins/.ssh/id_rsa"

# 部署函数
deploy_service() {{
    local service=$1
    echo "部署 $service..."
    
    ssh -i "$SSH_KEY" -o StrictHostKeyChecking=no "$DEPLOY_USER@$DEPLOY_HOST" "
        cd /opt/Fzxpodman/infrastructure/compose
        podman-compose -f podman-compose.aliyun-dev.yml up -d --build $service
    " || echo "$service 部署失败"
}}

# 部署后端服务
echo "部署后端微服务..."
for service in api-gateway auth-service user-service map-service order-service merchant-service platform-service product-service rider-service upload-service marketing-service; do
    deploy_service "$service"
done

# 重启基础设施服务
echo "重启基础设施服务..."
ssh -i "$SSH_KEY" -o StrictHostKeyChecking=no "$DEPLOY_USER@$DEPLOY_HOST" "
    cd /opt/Fzxpodman/infrastructure/compose
    podman-compose -f podman-compose.aliyun-dev.yml restart nginx nacos
"

echo "========================================"
echo "部署完成！"
echo "========================================"
</command>
    </hudson.tasks.Shell>
  </builders>
  <publishers/>
  <buildWrappers/>
</project>""".format(git_url=GIT_URL)
    
    return create_job("Fzx-Deploy", config)

def main():
    print("="*50)
    print("Jenkins配置开始")
    print("="*50)
    
    # 1. 创建凭证（需要用户提供Git用户名和密码或Token）
    # 这里先创建一个占位配置
    print("\n⚠️  请提供Git凭证信息：")
    print("   1. 阿里云Codeup用户名")
    print("   2. 阿里云Codeup密码或AccessToken")
    print("\n   或者手动在Jenkins管理界面配置凭证：")
    print("   - 路径: Jenkins > Manage Jenkins > Manage Credentials")
    print("   - 添加 Username/Password 类型的凭证")
    print("   - ID: aliyun-codeup-https")
    
    # 2. 创建流水线任务
    print("\n" + "="*50)
    print("创建Jenkins任务")
    print("="*50)
    
    create_pipeline_job()
    create_build_job()
    create_deploy_job()
    
    print("\n" + "="*50)
    print("Jenkins配置完成")
    print("="*50)
    print("\n下一步:")
    print("1. 配置Git凭证（如果还没有）")
    print("2. 访问 http://jenkins.fengzhongxing.com 查看任务")
    print("3. 触发 Fzx-Build 任务开始构建")

if __name__ == "__main__":
    main()
