# -*- coding: utf-8 -*-
import json

import requests
from requests.auth import HTTPBasicAuth

from const import JENKINS_BASE_URL, JENKINS_DEFAULT_JOB, JENKINS_TOKEN, JENKINS_USER
from logger import logger


class JenkinsRequest(object):
    def __init__(self, jenkins_url=None, username=None, password=None):
        if jenkins_url:
            self.base_url = jenkins_url.rstrip('/')
            use_username = username or JENKINS_USER or 'jenkins'
            use_password = password or JENKINS_TOKEN or 'jenkins'
            self.auth = HTTPBasicAuth(use_username, use_password)
        else:
            self.base_url = JENKINS_BASE_URL.rstrip('/')
            self.auth = HTTPBasicAuth(JENKINS_USER, JENKINS_TOKEN) if JENKINS_USER and JENKINS_TOKEN else None
        self.session = requests.Session()
        self.session.auth = self.auth
        logger.info(f'Jenkins配置: base_url={self.base_url}, username={use_username if jenkins_url else JENKINS_USER}')

    def get_crumb(self):
        if not self.base_url:
            return {}
        
        crumb_url = f'{self.base_url}/crumbIssuer/api/json'
        try:
            response = self.session.get(crumb_url, timeout=30)
            if response.status_code != 200:
                logger.warning(f'获取Jenkins crumb失败：status={response.status_code}')
                return {}
            crumb_data = response.json()
            if crumb_data.get('crumbRequestField') and crumb_data.get('crumb'):
                logger.info(f'成功获取Jenkins crumb: {crumb_data["crumbRequestField"]}')
                return {crumb_data['crumbRequestField']: crumb_data['crumb']}
        except Exception as err:
            logger.warning(f'获取Jenkins crumb失败：{err}')
        return {}

    def build_with_parameters(self, params, job_name=None):
        job_name = job_name or JENKINS_DEFAULT_JOB
        if not self.base_url or not job_name:
            return False, 'Jenkins配置不完整', {}
        
        url = f'{self.base_url}/job/{job_name}/buildWithParameters'
        headers = self.get_crumb()
        headers.update({'Content-Type': 'application/x-www-form-urlencoded'})
        
        logger.info(f'Jenkins构建请求: url={url}, params={json.dumps(params, ensure_ascii=False)}')
        
        try:
            response = self.session.post(url, data=params, headers=headers, timeout=60)
            if response.status_code not in (200, 201, 202):
                logger.error(f'Jenkins触发失败：status={response.status_code}, body={response.text[:500]}')
                
                if response.status_code == 403 and 'crumb' in response.text:
                    logger.info('Crumb失效，尝试重新获取并重试...')
                    headers = self.get_crumb()
                    headers.update({'Content-Type': 'application/x-www-form-urlencoded'})
                    response = self.session.post(url, data=params, headers=headers, timeout=60)
                    
                    if response.status_code not in (200, 201, 202):
                        logger.error(f'Jenkins触发失败(重试后)：status={response.status_code}')
                        return False, f'Jenkins触发失败：{response.status_code}', {}
            
            location = response.headers.get('Location', '')
            queue_id = None
            if '/queue/item/' in location:
                try:
                    queue_id = int(location.rstrip('/').split('/')[-1])
                except Exception:
                    queue_id = None
            
            logger.info(f'Jenkins构建成功：queue_id={queue_id}, location={location}')
            return True, '', {'job_name': job_name, 'queue_id': queue_id, 'location': location}
            
        except Exception as err:
            logger.error(f'Jenkins请求异常：{err}, params={json.dumps(params, ensure_ascii=False)}')
            return False, str(err), {}