#!/usr/bin/env python
# -*- coding: utf-8 -*-

"""
VWED任务系统服务管理工具
用于管理VWED服务的启动、停止、状态检查等操作
"""

import os
import sys
import time
import signal
import psutil
import argparse
import subprocess
from pathlib import Path


class VWEDServiceManager:
    """VWED服务管理器"""
    
    def __init__(self):
        self.service_name = "VWED_Task_System.exe"
        self.pid_file = Path("vwed_service.pid")
        self.log_file = Path("vwed_service.log")
        self.config_file = Path("config.ini")
    
    def start_service(self, headless=True, wait_for_start=True):
        """启动服务"""
        if self.is_running():
            print("服务已在运行中")
            return True
        
        print("启动VWED服务...")
        
        # 构建启动命令
        cmd = [self.service_name]
        if headless:
            cmd.append("--headless")
        
        try:
            # 启动服务进程
            if headless:
                # 后台模式，重定向输出到日志文件
                with open(self.log_file, 'a', encoding='utf-8') as log_f:
                    process = subprocess.Popen(
                        cmd,
                        stdout=log_f,
                        stderr=subprocess.STDOUT,
                        cwd=Path.cwd(),
                        creationflags=subprocess.CREATE_NO_WINDOW if sys.platform == "win32" else 0
                    )
            else:
                # 前台模式
                process = subprocess.Popen(cmd, cwd=Path.cwd())
            
            # 记录PID
            with open(self.pid_file, 'w') as f:
                f.write(str(process.pid))
            
            print(f"服务已启动 (PID: {process.pid})")
            
            if wait_for_start:
                # 等待服务完全启动
                print("等待服务启动完成...")
                for i in range(30):  # 最多等待30秒
                    if self._check_service_port():
                        print("服务启动成功，可以访问 http://localhost:8000")
                        return True
                    time.sleep(1)
                
                print("警告: 服务可能未完全启动，请检查日志文件")
            
            return True
            
        except FileNotFoundError:
            print(f"错误: 找不到可执行文件 {self.service_name}")
            return False
        except Exception as e:
            print(f"启动服务失败: {e}")
            return False
    
    def stop_service(self, force=False):
        """停止服务"""
        if not self.is_running():
            print("服务未运行")
            self._cleanup_pid_file()
            return True
        
        try:
            pid = self._get_pid()
            if pid:
                print(f"正在停止服务 (PID: {pid})...")
                
                try:
                    process = psutil.Process(pid)
                    
                    if not force:
                        # 优雅关闭
                        process.terminate()
                        # 等待进程结束
                        try:
                            process.wait(timeout=10)
                            print("服务已优雅停止")
                        except psutil.TimeoutExpired:
                            print("优雅停止超时，强制停止服务...")
                            process.kill()
                            print("服务已强制停止")
                    else:
                        # 强制关闭
                        process.kill()
                        print("服务已强制停止")
                        
                except psutil.NoSuchProcess:
                    print("进程不存在，清理PID文件")
                
                self._cleanup_pid_file()
                return True
                
        except Exception as e:
            print(f"停止服务失败: {e}")
            return False
    
    def restart_service(self, headless=True):
        """重启服务"""
        print("重启服务...")
        if self.is_running():
            if not self.stop_service():
                return False
            
            # 等待进程完全停止
            time.sleep(2)
        
        return self.start_service(headless)
    
    def service_status(self, show_logs=True):
        """检查服务状态"""
        print("检查VWED服务状态...")
        print("-" * 50)
        
        # 检查进程状态
        if self.is_running():
            pid = self._get_pid()
            try:
                process = psutil.Process(pid)
                print(f"✓ 服务正在运行")
                print(f"  PID: {pid}")
                print(f"  内存使用: {process.memory_info().rss / 1024 / 1024:.1f} MB")
                print(f"  CPU使用率: {process.cpu_percent():.1f}%")
                print(f"  运行时间: {time.time() - process.create_time():.0f} 秒")
            except psutil.NoSuchProcess:
                print("✗ 进程不存在，清理PID文件")
                self._cleanup_pid_file()
                return False
        else:
            print("✗ 服务未运行")
        
        # 检查端口状态
        if self._check_service_port():
            print("✓ 服务端口 8000 可访问")
            print("  访问地址: http://localhost:8000")
        else:
            print("✗ 服务端口 8000 不可访问")
        
        # 检查配置文件
        if self.config_file.exists():
            print("✓ 配置文件存在")
        else:
            print("✗ 配置文件不存在")
        
        # 显示最近日志
        if show_logs and self.log_file.exists():
            print("\n最近的日志内容:")
            print("-" * 30)
            try:
                with open(self.log_file, 'r', encoding='utf-8') as f:
                    lines = f.readlines()
                    for line in lines[-10:]:  # 显示最后10行
                        print(line.strip())
            except Exception as e:
                print(f"读取日志失败: {e}")
        
        return self.is_running()
    
    def is_running(self):
        """检查服务是否运行中"""
        pid = self._get_pid()
        if not pid:
            return False
        
        try:
            return psutil.pid_exists(pid)
        except:
            return False
    
    def _get_pid(self):
        """获取服务PID"""
        if not self.pid_file.exists():
            return None
        
        try:
            with open(self.pid_file, 'r') as f:
                return int(f.read().strip())
        except (ValueError, FileNotFoundError):
            return None
    
    def _cleanup_pid_file(self):
        """清理PID文件"""
        if self.pid_file.exists():
            try:
                self.pid_file.unlink()
            except:
                pass
    
    def _check_service_port(self):
        """检查服务端口是否可访问"""
        try:
            import socket
            with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as s:
                s.settimeout(1)
                result = s.connect_ex(('localhost', 8000))
                return result == 0
        except:
            return False


def main():
    """主函数"""
    parser = argparse.ArgumentParser(description='VWED任务系统服务管理工具')
    parser.add_argument('action', choices=['start', 'stop', 'restart', 'status', 'logs'],
                       help='操作: start(启动), stop(停止), restart(重启), status(状态), logs(查看日志)')
    parser.add_argument('--headless', action='store_true',
                       help='后台模式运行（适用于start和restart）')
    parser.add_argument('--force', action='store_true',
                       help='强制停止服务（适用于stop）')
    parser.add_argument('--no-wait', action='store_true',
                       help='启动后不等待服务完全启动（适用于start）')
    
    args = parser.parse_args()
    
    manager = VWEDServiceManager()
    
    try:
        if args.action == 'start':
            success = manager.start_service(
                headless=args.headless, 
                wait_for_start=not args.no_wait
            )
            sys.exit(0 if success else 1)
            
        elif args.action == 'stop':
            success = manager.stop_service(force=args.force)
            sys.exit(0 if success else 1)
            
        elif args.action == 'restart':
            success = manager.restart_service(headless=args.headless)
            sys.exit(0 if success else 1)
            
        elif args.action == 'status':
            is_running = manager.service_status()
            sys.exit(0 if is_running else 1)
            
        elif args.action == 'logs':
            if manager.log_file.exists():
                try:
                    with open(manager.log_file, 'r', encoding='utf-8') as f:
                        print(f.read())
                except Exception as e:
                    print(f"读取日志失败: {e}")
                    sys.exit(1)
            else:
                print("日志文件不存在")
                sys.exit(1)
                
    except KeyboardInterrupt:
        print("\n操作被用户中断")
        sys.exit(1)
    except Exception as e:
        print(f"操作失败: {e}")
        sys.exit(1)


if __name__ == "__main__":
    main()