#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
自动化部署脚本
功能：更新mkdocs.yml -> Git提交推送 -> 服务器拉取并重启
"""

import os
import sys
import json
import subprocess
import argparse
from pathlib import Path

# 颜色输出
class Colors:
    RED = '\033[91m'
    GREEN = '\033[92m'
    YELLOW = '\033[93m'
    CYAN = '\033[96m'
    RESET = '\033[0m'

def print_info(msg):
    print(f"{Colors.CYAN}{msg}{Colors.RESET}")

def print_success(msg):
    print(f"{Colors.GREEN}✓ {msg}{Colors.RESET}")

def print_error(msg):
    print(f"{Colors.RED}✗ {msg}{Colors.RESET}")

def print_warning(msg):
    print(f"{Colors.YELLOW}⚠ {msg}{Colors.RESET}")

def run_command(cmd, check=True, shell=False):
    """执行命令"""
    try:
        if isinstance(cmd, str):
            cmd = cmd.split()
        result = subprocess.run(
            cmd,
            check=check,
            shell=shell,
            capture_output=True,
            text=True,
            encoding='utf-8'
        )
        return result.returncode == 0, result.stdout, result.stderr
    except subprocess.CalledProcessError as e:
        return False, e.stdout, e.stderr
    except Exception as e:
        return False, "", str(e)

def load_config():
    """加载配置文件"""
    config_file = Path("deploy_config.json")
    if config_file.exists():
        try:
            with open(config_file, 'r', encoding='utf-8') as f:
                return json.load(f)
        except Exception as e:
            print_warning(f"加载配置文件失败: {e}")
    return {}

def step1_update_mkdocs(script_path="add_docs_to_mkdocs.py"):
    """步骤1: 更新mkdocs.yml"""
    print_info("=" * 50)
    print_info("步骤1: 更新mkdocs.yml")
    print_info("=" * 50)
    
    if not Path(script_path).exists():
        print_error(f"找不到脚本: {script_path}")
        return False
    
    success, stdout, stderr = run_command([sys.executable, script_path])
    if success:
        print_success("mkdocs.yml更新成功")
        if stdout:
            print(stdout)
        return True
    else:
        print_error("更新mkdocs.yml失败")
        if stderr:
            print_error(stderr)
        return False

def step2_git_operations(commit_message, branch="master", remote="origin"):
    """步骤2: Git操作"""
    print_info("")
    print_info("=" * 50)
    print_info("步骤2: Git提交和推送")
    print_info("=" * 50)
    
    # 检查是否有变更
    print_info("检查Git状态...")
    success, stdout, _ = run_command(["git", "status", "--porcelain"])
    if not stdout.strip():
        print_info("没有文件变更，跳过Git操作")
        return True
    
    print_info("发现以下变更:")
    success, stdout, _ = run_command(["git", "status", "--short"])
    print(stdout)
    
    # 添加文件
    print_info("添加文件到Git...")
    success, _, stderr = run_command(["git", "add", "."])
    if not success:
        print_error("Git add 失败")
        if stderr:
            print_error(stderr)
        return False
    print_success("文件已添加到暂存区")
    
    # 提交
    print_info("提交变更...")
    success, _, stderr = run_command(["git", "commit", "-m", commit_message])
    if not success:
        print_error("Git commit 失败")
        if stderr:
            print_error(stderr)
        return False
    print_success("变更已提交")
    
    # 推送
    print_info("推送到远程仓库...")
    success, _, stderr = run_command(["git", "push", remote, branch])
    if not success:
        print_error("Git push 失败")
        if stderr:
            print_error(stderr)
        return False
    print_success("代码已推送到远程仓库")
    
    return True

def step3_server_operations(server_user, server_host, server_path):
    """步骤3: 服务器操作"""
    print_info("")
    print_info("=" * 50)
    print_info("步骤3: 服务器拉取代码并重启服务")
    print_info("=" * 50)
    
    if not server_user or not server_host:
        print_info("未配置服务器信息，跳过服务器操作")
        print_info("")
        print_info("使用方法:")
        print_info("  python deploy.py --server-user <用户> --server-host <地址>")
        print_info("")
        print_info("或手动执行:")
        print_info(f"  ssh user@host 'cd {server_path} && git pull origin master && docker-compose restart'")
        return True
    
    print_info(f"连接到服务器: {server_user}@{server_host}")
    print_info(f"执行命令: cd {server_path} && git pull origin master && docker-compose restart")
    
    remote_cmd = f"cd {server_path} && git pull origin master && docker-compose restart"
    ssh_cmd = ["ssh", f"{server_user}@{server_host}", remote_cmd]
    
    success, stdout, stderr = run_command(ssh_cmd)
    if success:
        print_success("服务器代码已更新，服务已重启")
        if stdout:
            print(stdout)
        return True
    else:
        print_error("服务器操作失败")
        if stderr:
            print_error(stderr)
        print_warning("提示: 请确保已配置SSH密钥，或手动执行服务器命令")
        return False

def main():
    parser = argparse.ArgumentParser(description="自动化部署脚本")
    parser.add_argument(
        "-m", "--message",
        default="更新文档",
        help="Git提交信息（默认: 更新文档）"
    )
    parser.add_argument(
        "--server-user",
        help="服务器用户名"
    )
    parser.add_argument(
        "--server-host",
        help="服务器地址"
    )
    parser.add_argument(
        "--server-path",
        default="~/devops/mkdocs",
        help="服务器路径（默认: ~/devops/mkdocs）"
    )
    parser.add_argument(
        "--skip-mkdocs",
        action="store_true",
        help="跳过mkdocs.yml更新"
    )
    parser.add_argument(
        "--skip-git",
        action="store_true",
        help="跳过Git操作"
    )
    parser.add_argument(
        "--skip-server",
        action="store_true",
        help="跳过服务器操作"
    )
    
    args = parser.parse_args()
    
    # 加载配置
    config = load_config()
    server_config = config.get("server", {})
    git_config = config.get("git", {})
    
    # 使用配置或参数
    server_user = args.server_user or server_config.get("user", "")
    server_host = args.server_host or server_config.get("host", "")
    server_path = args.server_path or server_config.get("path", "~/devops/mkdocs")
    branch = git_config.get("branch", "master")
    remote = git_config.get("remote", "origin")
    
    try:
        # 步骤1: 更新mkdocs.yml
        if not args.skip_mkdocs:
            if not step1_update_mkdocs():
                sys.exit(1)
        
        # 步骤2: Git操作
        if not args.skip_git:
            if not step2_git_operations(args.message, branch, remote):
                sys.exit(1)
        
        # 步骤3: 服务器操作
        if not args.skip_server:
            if not step3_server_operations(server_user, server_host, server_path):
                sys.exit(1)
        
        print_info("")
        print_info("=" * 50)
        print_success("部署完成！")
        print_info("=" * 50)
        
    except KeyboardInterrupt:
        print_error("\n操作已取消")
        sys.exit(1)
    except Exception as e:
        print_error(f"发生错误: {e}")
        sys.exit(1)

if __name__ == "__main__":
    main()
