#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
SQLAlchemy数据库模型
定义所有数据库表的结构，用于Flask-Migrate自动迁移
"""

from flask_sqlalchemy import SQLAlchemy
from datetime import datetime
import json

db = SQLAlchemy()

class User(db.Model):
    """用户管理表"""
    __tablename__ = 'users'
    
    user_id = db.Column(db.Integer, primary_key=True, comment='用户ID')
    username = db.Column(db.String(50), unique=True, nullable=False, comment='用户名')
    password_hash = db.Column(db.String(255), nullable=False, comment='密码哈希')
    user_type = db.Column(db.String(20), default='user', comment='用户类型')
    clinic_access = db.Column(db.JSON, comment='诊所访问权限')
    created_at = db.Column(db.DateTime, default=datetime.utcnow, comment='创建时间')
    updated_at = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow, comment='更新时间')
    is_active = db.Column(db.Boolean, default=True, comment='是否激活')
    last_login = db.Column(db.DateTime, comment='最后登录时间')
    
    # 索引
    __table_args__ = (
        db.Index('idx_user_type', 'user_type'),
        db.Index('idx_is_active', 'is_active'),
        {'comment': '用户管理表'}
    )
    
    def __repr__(self):
        return f'<User {self.username}>'

class Clinic(db.Model):
    """诊所信息表"""
    __tablename__ = 'clinics'
    
    clinic_id = db.Column(db.Integer, primary_key=True, comment='诊所ID')
    clinic_name = db.Column(db.String(100), nullable=False, comment='诊所名称')
    clinic_code = db.Column(db.String(50), unique=True, nullable=False, comment='诊所代码')
    clinic_address = db.Column(db.String(255), comment='诊所地址')
    clinic_phone = db.Column(db.String(20), comment='诊所电话')
    created_at = db.Column(db.DateTime, default=datetime.utcnow, comment='创建时间')
    updated_at = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow, comment='更新时间')
    is_active = db.Column(db.Boolean, default=True, comment='是否激活')
    
    # 关系
    patients = db.relationship('Patient', backref='clinic', lazy=True)
    
    # 索引
    __table_args__ = (
        db.Index('idx_is_active', 'is_active'),
        {'comment': '诊所信息表'}
    )
    
    def __repr__(self):
        return f'<Clinic {self.clinic_name}>'

class Patient(db.Model):
    """患者信息表"""
    __tablename__ = 'patients'
    
    patient_id = db.Column(db.Integer, primary_key=True, comment='患者ID')
    case_number = db.Column(db.String(50), unique=True, nullable=False, comment='病历号')
    patient_name = db.Column(db.String(100), comment='患者姓名')
    patient_phone = db.Column(db.String(20), comment='患者电话')
    gender = db.Column(db.String(10), comment='性别')
    age = db.Column(db.Integer, comment='年龄')
    clinic_id = db.Column(db.Integer, db.ForeignKey('clinics.clinic_id'), comment='诊所ID')
    clinic_name = db.Column(db.String(100), comment='诊所名称')
    diagnosis = db.Column(db.JSON, comment='诊断信息')
    treatment_date = db.Column(db.Date, comment='治疗日期')
    created_at = db.Column(db.DateTime, default=datetime.utcnow, comment='创建时间')
    updated_at = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow, comment='更新时间')
    
    # 关系
    callback_records = db.relationship('CallbackRecord', backref='patient', lazy=True, cascade='all, delete-orphan')
    
    # 索引
    __table_args__ = (
        db.Index('idx_patient_name', 'patient_name'),
        db.Index('idx_clinic_name', 'clinic_name'),
        db.Index('idx_treatment_date', 'treatment_date'),
        {'comment': '患者信息表'}
    )
    
    def to_dict(self):
        """转换为字典格式，兼容原有的JSON数据格式"""
        base_dict = {
            '姓名': self.patient_name,
            '年龄': self.age,
            '性别': self.gender,
            '病历号': self.case_number,
            '电话': self.patient_phone,
            '门诊名称': self.clinic_name,
            '诊断信息': self.diagnosis,
            '治疗日期': self.treatment_date.isoformat() if self.treatment_date else None,
            '创建时间': self.created_at.isoformat() if self.created_at else None,
            '更新时间': self.updated_at.isoformat() if self.updated_at else None
        }

        # 展开diagnosis JSON字段中的内容，使其与原JSON文件格式兼容
        if self.diagnosis and isinstance(self.diagnosis, dict):
            # 直接将diagnosis中的所有字段添加到返回字典中
            base_dict.update(self.diagnosis)

        return base_dict

    def __repr__(self):
        return f'<Patient {self.patient_name} ({self.case_number})>'

class CallbackRecord(db.Model):
    """回访记录表"""
    __tablename__ = 'callback_records'
    
    record_id = db.Column(db.Integer, primary_key=True, comment='记录ID')
    case_number = db.Column(db.String(50), db.ForeignKey('patients.case_number'), nullable=False, comment='病历号')
    callback_methods = db.Column(db.JSON, nullable=False, comment='回访方式（JSON格式）')
    callback_record = db.Column(db.Text, nullable=False, comment='回访记录内容')
    callback_result = db.Column(db.String(50), nullable=False, comment='回访结果（成功/不成功/放弃回访）')
    next_appointment_time = db.Column(db.Text, comment='下次预约时间')
    failure_reason = db.Column(db.Text, comment='不成功的原因')
    abandon_reason = db.Column(db.Text, comment='放弃回访的原因')
    ai_feedback_type = db.Column(db.String(100), comment='AI错误反馈类型')
    failure_reason_note = db.Column(db.Text, comment='不成功备注')
    abandon_reason_note = db.Column(db.Text, comment='放弃回访备注')
    ai_feedback_note = db.Column(db.Text, comment='AI反馈备注')
    callback_status = db.Column(db.String(50), nullable=False, default='已回访', comment='回访状态')
    operator = db.Column(db.String(100), nullable=False, comment='操作员')
    create_time = db.Column(db.DateTime, default=datetime.utcnow, comment='创建时间')
    update_time = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow, comment='更新时间')
    
    # 索引
    __table_args__ = (
        db.Index('idx_case_number', 'case_number'),
        db.Index('idx_create_time', 'create_time'),
        db.Index('idx_operator', 'operator'),
        db.Index('idx_callback_result', 'callback_result'),
        {'comment': '回访记录表'}
    )
    
    @property
    def callback_success(self):
        """为了向后兼容，提供callback_success属性"""
        return self.callback_result == "成功"
    
    def to_dict(self):
        """转换为字典格式"""
        return {
            'record_id': self.record_id,
            'case_number': self.case_number,
            'callback_methods': self.callback_methods if isinstance(self.callback_methods, list) else json.loads(self.callback_methods or '[]'),
            'callback_record': self.callback_record,
            'callback_result': self.callback_result,
            'callback_success': self.callback_success,
            'callback_status': self.callback_status,
            'next_appointment_time': self.next_appointment_time,
            'failure_reason': self.failure_reason,
            'abandon_reason': self.abandon_reason,
            'ai_feedback_type': self.ai_feedback_type,
            'failure_reason_note': self.failure_reason_note,
            'abandon_reason_note': self.abandon_reason_note,
            'ai_feedback_note': self.ai_feedback_note,
            'operator': self.operator,
            'operator_name': self.operator,  # 前端期望的字段名
            'create_time': self.create_time.isoformat() if self.create_time else None,
            'update_time': self.update_time.isoformat() if self.update_time else None
        }
    
    def __repr__(self):
        return f'<CallbackRecord {self.case_number} - {self.callback_result}>'

class OperationLog(db.Model):
    """操作日志表"""
    __tablename__ = 'operation_logs'

    log_id = db.Column(db.Integer, primary_key=True, comment='日志ID')
    user_id = db.Column(db.Integer, comment='用户ID')
    username = db.Column(db.String(50), comment='用户名')
    operation = db.Column(db.String(100), nullable=False, comment='操作类型')
    target_type = db.Column(db.String(50), comment='目标类型')
    target_id = db.Column(db.String(100), comment='目标ID')
    operation_details = db.Column(db.JSON, comment='操作详情')
    ip_address = db.Column(db.String(45), comment='IP地址')
    user_agent = db.Column(db.String(255), comment='用户代理')
    created_at = db.Column(db.DateTime, default=datetime.utcnow, comment='创建时间')

    # 索引
    __table_args__ = (
        db.Index('idx_user_id', 'user_id'),
        db.Index('idx_operation', 'operation'),
        db.Index('idx_created_at', 'created_at'),
        {'comment': '操作日志表'}
    )

    def __repr__(self):
        return f'<OperationLog {self.username} - {self.operation}>'

# 数据库初始化函数
def init_db(app):
    """初始化数据库"""
    db.init_app(app)
    
    with app.app_context():
        # 创建所有表
        db.create_all()
        
        # 默认数据插入由 app.py 中的 insert_default_data() 处理

# 默认数据插入功能已移至 app.py 中的 insert_default_data() 函数
# 避免重复插入门诊数据
