# app/models/escrow.py

from flask_login import UserMixin
from datetime import datetime
from app.extensions import db, login_manager
from werkzeug.security import generate_password_hash, check_password_hash
import random
import string


class SystemBankAccount(db.Model):
    """حساب‌های بانکی سامانه (نوگاه)"""
    __tablename__ = 'system_bank_accounts'
    __table_args__ = {'extend_existing': True}
    
    id = db.Column(db.Integer, primary_key=True)
    bank_name = db.Column(db.String(100), nullable=False)
    account_number = db.Column(db.String(50), unique=True, nullable=False)
    account_owner = db.Column(db.String(100), nullable=False, default='سامانه نوگاه')
    shaba_number = db.Column(db.String(50), nullable=True)
    card_number = db.Column(db.String(20), nullable=True)
    
    # نوع حساب
    account_type = db.Column(db.String(20), default='escrow')  # escrow, salary, commission
    
    # وضعیت
    is_active = db.Column(db.Boolean, default=True)
    is_default = db.Column(db.Boolean, default=False)  # حساب پیش‌فرض برای واریز
    
    # توضیحات
    description = db.Column(db.Text, nullable=True)
    
    # تاریخ‌ها
    created_at = db.Column(db.DateTime, default=datetime.utcnow)
    updated_at = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow)
    
    # ========== روابط ==========
    
    # رابطه با EscrowAccount (یک به یک)
    escrow_account = db.relationship(
        'EscrowAccount',
        backref='system_account_ref',
        uselist=False,
        foreign_keys='EscrowAccount.system_account_id'  # مشخص کردن کلید خارجی
    )
    
    # رابطه با BankCheckBook
    check_books = db.relationship(
        'BankCheckBook',
        foreign_keys='BankCheckBook.system_account_id',
        backref='system_account_ref',
        lazy='dynamic'
    )
    
    # رابطه با Deposit
    deposits_to_account = db.relationship(
        'Deposit',
        foreign_keys='Deposit.destination_account_id',
        backref='destination_account_ref',
        lazy='dynamic'
    )
    
    def __repr__(self):
        return f'<SystemBankAccount {self.bank_name} - {self.account_number}>'

# app/models/escrow.py

class EscrowAccount(db.Model):
    """صندوق امانی مرکزی سامانه (نوگاه) - یک صندوق برای کل سیستم"""
    __tablename__ = 'escrow_accounts'
    __table_args__ = {'extend_existing': True}
    
    id = db.Column(db.Integer, primary_key=True)
    
    # ======== ستون‌های اطلاعات بانکی ========
    system_account_id = db.Column(db.Integer, db.ForeignKey('system_bank_accounts.id'), nullable=True)
    
    # اطلاعات بانکی مستقیم
    bank_name = db.Column(db.String(100), nullable=False, default='صندوق امانی پروژه')
    bank_branch = db.Column(db.String(100), nullable=True)
    account_number = db.Column(db.String(50), nullable=False)
    
    # ======== اضافه کردن فیلدهای جدید ========
    shaba_number = db.Column(db.String(50), nullable=True)  # شماره شبا
    card_number = db.Column(db.String(20), nullable=True)   # شماره کارت
    
    # موجودی کل
    balance = db.Column(db.Float, default=0)
    total_deposited = db.Column(db.Float, default=0)
    total_released = db.Column(db.Float, default=0)
    total_fees = db.Column(db.Float, default=0)
    
    # وضعیت
    status = db.Column(db.String(20), default='active')
    is_active = db.Column(db.Boolean, default=True)
    
    # ارز
    currency = db.Column(db.String(10), default='IRR')
    
    # توضیحات
    description = db.Column(db.Text, nullable=True)
    
    # زمان‌ها
    created_at = db.Column(db.DateTime, default=datetime.utcnow)
    updated_at = db.Column(db.DateTime, default=datetime.utcnow, onupdate=datetime.utcnow)
    created_by = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    
    # ========== روابط ==========
    
    # رابطه با SystemBankAccount
    system_account = db.relationship(
        'SystemBankAccount',
        foreign_keys=[system_account_id],
        backref='escrow_account_ref'
    )
    
    # رابطه با Creator
    creator = db.relationship(
        'User',
        foreign_keys=[created_by],
        backref='created_escrow'
    )
    
    # رابطه با Deposit
    deposits = db.relationship(
        'Deposit',
        foreign_keys='Deposit.escrow_id',
        backref='escrow_ref',
        lazy='dynamic'
    )
    
    # رابطه با EscrowTransaction
    transactions = db.relationship(
        'EscrowTransaction',
        foreign_keys='EscrowTransaction.escrow_id',
        backref='escrow_ref',
        lazy='dynamic'
    )
    
    # ========== متدها ==========
    
    @classmethod
    def get_active_escrow(cls):
        """دریافت صندوق امانی فعال"""
        return cls.query.filter_by(is_active=True).first()
    
    def deposit(self, amount, tracking_code, employer_id, project_id=None,
                source_bank=None, source_account=None, receipt_image=None, 
                description=None, created_by=None):
        """واریز به صندوق امانی مرکزی"""
        self.balance += amount
        self.total_deposited += amount
        
        transaction = EscrowTransaction(
            escrow_id=self.id,
            project_id=project_id,
            transaction_type='deposit',
            amount=amount,
            tracking_code=tracking_code,
            employer_id=employer_id,
            source_bank=source_bank,
            source_account=source_account,
            receipt_image=receipt_image,
            description=description,
            created_by=created_by,
            status='completed',
            completed_at=datetime.utcnow()
        )
        db.session.add(transaction)
        return transaction
    
    def withdraw(self, amount, check_number, employee_id, project_id=None,
                 bank_check_id=None, description=None, created_by=None):
        """برداشت از صندوق امانی (صدور چک)"""
        if self.balance < amount:
            raise ValueError(f"موجودی کافی نیست. موجودی: {self.balance} - درخواست: {amount}")
        
        self.balance -= amount
        self.total_released += amount
        
        transaction = EscrowTransaction(
            escrow_id=self.id,
            project_id=project_id,
            transaction_type='withdraw',
            amount=amount,
            check_number=check_number,
            employee_id=employee_id,
            bank_check_id=bank_check_id,
            description=description,
            created_by=created_by,
            status='completed',
            completed_at=datetime.utcnow()
        )
        db.session.add(transaction)
        return transaction
    
    def add_fee(self, amount, fee_type, fee_percentage, project_id=None,
                description=None, created_by=None):
        """افزودن کارمزد"""
        self.balance -= amount
        self.total_fees += amount
        
        transaction = EscrowTransaction(
            escrow_id=self.id,
            project_id=project_id,
            transaction_type='fee',
            amount=amount,
            fee_type=fee_type,
            fee_percentage=fee_percentage,
            description=description,
            created_by=created_by,
            status='completed',
            completed_at=datetime.utcnow()
        )
        db.session.add(transaction)
        return transaction
    
    def get_transactions(self, project_id=None, limit=100):
        """دریافت آخرین تراکنش‌ها"""
        query = EscrowTransaction.query.filter_by(escrow_id=self.id)
        if project_id:
            query = query.filter_by(project_id=project_id)
        return query.order_by(
            EscrowTransaction.created_at.desc()
        ).limit(limit).all()
    
    def get_project_balance(self, project_id):
        """دریافت موجودی اختصاصی یک پروژه"""
        total_deposits = db.session.query(db.func.sum(EscrowTransaction.amount)).filter(
            EscrowTransaction.escrow_id == self.id,
            EscrowTransaction.project_id == project_id,
            EscrowTransaction.transaction_type == 'deposit',
            EscrowTransaction.status == 'completed'
        ).scalar() or 0
        
        total_withdrawals = db.session.query(db.func.sum(EscrowTransaction.amount)).filter(
            EscrowTransaction.escrow_id == self.id,
            EscrowTransaction.project_id == project_id,
            EscrowTransaction.transaction_type.in_(['withdraw', 'fee']),
            EscrowTransaction.status == 'completed'
        ).scalar() or 0
        
        return total_deposits - total_withdrawals
    
    def get_deposits_total(self, project_id=None):
        """مجموع واریزها"""
        query = db.session.query(db.func.sum(EscrowTransaction.amount)).filter(
            EscrowTransaction.escrow_id == self.id,
            EscrowTransaction.transaction_type == 'deposit',
            EscrowTransaction.status == 'completed'
        )
        if project_id:
            query = query.filter(EscrowTransaction.project_id == project_id)
        return query.scalar() or 0
    
    def get_withdrawals_total(self, project_id=None):
        """مجموع برداشت‌ها"""
        query = db.session.query(db.func.sum(EscrowTransaction.amount)).filter(
            EscrowTransaction.escrow_id == self.id,
            EscrowTransaction.transaction_type == 'withdraw',
            EscrowTransaction.status == 'completed'
        )
        if project_id:
            query = query.filter(EscrowTransaction.project_id == project_id)
        return query.scalar() or 0
    
    def get_fees_total(self, project_id=None):
        """مجموع کارمزدها"""
        query = db.session.query(db.func.sum(EscrowTransaction.amount)).filter(
            EscrowTransaction.escrow_id == self.id,
            EscrowTransaction.transaction_type == 'fee',
            EscrowTransaction.status == 'completed'
        )
        if project_id:
            query = query.filter(EscrowTransaction.project_id == project_id)
        return query.scalar() or 0
    
    def get_available_balance(self, project_id=None):
        """دریافت موجودی قابل استفاده"""
        if project_id:
            return self.get_project_balance(project_id)
        return self.balance
    
    def to_dict(self, project_id=None):
        """تبدیل به دیکشنری برای JSON"""
        return {
            'id': self.id,
            'system_account_id': self.system_account_id,
            'bank_name': self.bank_name,
            'bank_branch': self.bank_branch,
            'account_number': self.account_number,
            'shaba_number': self.shaba_number,
            'card_number': self.card_number,
            'balance': self.balance,
            'balance_formatted': f"{self.balance:,.0f}",
            'total_deposited': self.total_deposited,
            'total_deposited_formatted': f"{self.total_deposited:,.0f}",
            'total_released': self.total_released,
            'total_released_formatted': f"{self.total_released:,.0f}",
            'total_fees': self.total_fees,
            'total_fees_formatted': f"{self.total_fees:,.0f}",
            'available_balance': self.get_available_balance(project_id),
            'available_balance_formatted': f"{self.get_available_balance(project_id):,.0f}",
            'status': self.status,
            'is_active': self.is_active,
            'description': self.description,
            'created_at': self.created_at.strftime('%Y-%m-%d %H:%M:%S'),
            'created_by': self.creator.fullname if self.creator else None
        }
    
    def __repr__(self):
        return f'<EscrowAccount {self.bank_name} - {self.account_number} Balance:{self.balance}>'
    

class EscrowTransaction(db.Model):
    """تراکنش‌های صندوق امانی سامانه"""
    __tablename__ = 'escrow_transactions'
    __table_args__ = {'extend_existing': True}
    
    id = db.Column(db.Integer, primary_key=True)
    escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=False)
    project_id = db.Column(db.Integer, db.ForeignKey('projects.id'), nullable=True)  # پروژه مرتبط
    
    # نوع تراکنش
    transaction_type = db.Column(db.String(20), nullable=False)  # deposit, withdraw, transfer, fee, refund
    
    # مبلغ تراکنش
    amount = db.Column(db.Float, nullable=False)
    
    # اطلاعات واریز (برای نوع deposit)
    tracking_code = db.Column(db.String(100), nullable=True)
    employer_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    source_bank = db.Column(db.String(100), nullable=True)
    source_account = db.Column(db.String(50), nullable=True)
    receipt_image = db.Column(db.String(200), nullable=True)
    
    # اطلاعات برداشت (برای نوع withdraw)
    check_number = db.Column(db.String(50), nullable=True)
    employee_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    bank_check_id = db.Column(db.Integer, db.ForeignKey('bank_checks.id'), nullable=True)
    
    # اطلاعات انتقال (برای نوع transfer)
    from_escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=True)
    to_escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=True)
    
    # اطلاعات کارمزد (برای نوع fee)
    fee_type = db.Column(db.String(50), nullable=True)
    fee_percentage = db.Column(db.Float, nullable=True)
    
    # اطلاعات برگشت (برای نوع refund)
    refund_reason = db.Column(db.Text, nullable=True)
    original_transaction_id = db.Column(db.Integer, db.ForeignKey('escrow_transactions.id'), nullable=True)
    
    # وضعیت تراکنش
    status = db.Column(db.String(20), default='pending')  # pending, completed, failed, cancelled
    
    # توضیحات
    description = db.Column(db.Text, nullable=True)
    
    # زمان‌ها
    created_at = db.Column(db.DateTime, default=datetime.utcnow)
    completed_at = db.Column(db.DateTime, nullable=True)
    
    # ثبت کننده
    created_by = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    
    # ========== روابط ==========
    
    # رابطه با EscrowAccount
    escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[escrow_id],
        backref='transactions_ref'
    )
    
    # رابطه با Project
    project = db.relationship(
        'Project',
        foreign_keys=[project_id],
        backref='escrow_transactions'
    )
    
    # رابطه با Employer (User)
    employer = db.relationship(
        'User',
        foreign_keys=[employer_id],
        backref='escrow_deposits_ref'
    )
    
    # رابطه با Employee (User)
    employee = db.relationship(
        'User',
        foreign_keys=[employee_id],
        backref='escrow_withdrawals_ref'
    )
    
    # رابطه با BankCheck
    bank_check = db.relationship(
        'BankCheck',
        foreign_keys=[bank_check_id],
        backref='escrow_transaction_ref'
    )
    
    # رابطه با From Escrow
    from_escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[from_escrow_id],
        backref='transfers_out_ref'
    )
    
    # رابطه با To Escrow
    to_escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[to_escrow_id],
        backref='transfers_in_ref'
    )
    
    # رابطه با Creator (User)
    creator = db.relationship(
        'User',
        foreign_keys=[created_by],
        backref='escrow_transactions_created'
    )
    
    # رابطه با Original Transaction (خود ارجاعی)
    original_transaction = db.relationship(
        'EscrowTransaction',
        foreign_keys=[original_transaction_id],
        remote_side=[id],
        backref='refunds_ref'
    )
    
    # ========== متدها ==========
    
    def complete(self):
        """تکمیل تراکنش"""
        self.status = 'completed'
        self.completed_at = datetime.utcnow()
    
    def fail(self, reason=None):
        """خطا در تراکنش"""
        self.status = 'failed'
        if reason:
            self.description = reason
    
    def cancel(self, reason=None):
        """لغو تراکنش"""
        self.status = 'cancelled'
        if reason:
            self.description = reason
    
    @classmethod
    def create_deposit(cls, escrow_id, amount, tracking_code, employer_id, project_id=None,
                       source_bank=None, source_account=None, receipt_image=None, 
                       description=None, created_by=None):
        """ایجاد تراکنش واریز"""
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='deposit',
            amount=amount,
            tracking_code=tracking_code,
            employer_id=employer_id,
            source_bank=source_bank,
            source_account=source_account,
            receipt_image=receipt_image,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_withdraw(cls, escrow_id, amount, check_number, employee_id, project_id=None,
                        bank_check_id=None, description=None, created_by=None):
        """ایجاد تراکنش برداشت (صدور چک)"""
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='withdraw',
            amount=amount,
            check_number=check_number,
            employee_id=employee_id,
            bank_check_id=bank_check_id,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_fee(cls, escrow_id, amount, fee_type, fee_percentage, project_id=None,
                   description=None, created_by=None):
        """ایجاد تراکنش کارمزد"""
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='fee',
            amount=amount,
            fee_type=fee_type,
            fee_percentage=fee_percentage,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_transfer(cls, from_escrow_id, to_escrow_id, amount, project_id=None,
                        description=None, created_by=None):
        """ایجاد تراکنش انتقال بین صندوق‌ها"""
        withdraw_transaction = cls(
            escrow_id=from_escrow_id,
            project_id=project_id,
            transaction_type='transfer',
            amount=amount,
            from_escrow_id=from_escrow_id,
            to_escrow_id=to_escrow_id,
            description=f'انتقال به صندوق {to_escrow_id} - {description or ""}',
            created_by=created_by,
            status='completed'
        )
        
        deposit_transaction = cls(
            escrow_id=to_escrow_id,
            project_id=project_id,
            transaction_type='transfer',
            amount=amount,
            from_escrow_id=from_escrow_id,
            to_escrow_id=to_escrow_id,
            description=f'انتقال از صندوق {from_escrow_id} - {description or ""}',
            created_by=created_by,
            status='completed'
        )
        
        return withdraw_transaction, deposit_transaction
    
    @classmethod
    def create_refund(cls, original_transaction_id, escrow_id, amount, reason, project_id=None,
                      description=None, created_by=None):
        """ایجاد تراکنش برگشت وجه"""
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='refund',
            amount=amount,
            refund_reason=reason,
            original_transaction_id=original_transaction_id,
            description=description,
            created_by=created_by,
            status='pending'
        )
        return transaction
    
    def get_type_display(self):
        """نمایش نوع تراکنش به فارسی"""
        type_map = {
            'deposit': 'واریز',
            'withdraw': 'برداشت',
            'transfer': 'انتقال',
            'fee': 'کارمزد',
            'refund': 'برگشت'
        }
        return type_map.get(self.transaction_type, self.transaction_type)
    
    def get_status_display(self):
        """نمایش وضعیت به فارسی"""
        status_map = {
            'pending': 'در انتظار',
            'completed': 'تکمیل شده',
            'failed': 'خطا',
            'cancelled': 'لغو شده'
        }
        return status_map.get(self.status, self.status)
    
    def to_dict(self):
        """تبدیل تراکنش به دیکشنری برای JSON"""
        return {
            'id': self.id,
            'project_id': self.project_id,
            'project_name': self.project.name if self.project else None,
            'type': self.transaction_type,
            'type_display': self.get_type_display(),
            'amount': self.amount,
            'amount_formatted': f"{self.amount:,.0f}",
            'status': self.status,
            'status_display': self.get_status_display(),
            'tracking_code': self.tracking_code,
            'check_number': self.check_number,
            'employer_name': self.employer.fullname if self.employer else None,
            'employee_name': self.employee.fullname if self.employee else None,
            'description': self.description,
            'created_at': self.created_at.strftime('%Y-%m-%d %H:%M:%S'),
            'completed_at': self.completed_at.strftime('%Y-%m-%d %H:%M:%S') if self.completed_at else None
        }
    
    def __repr__(self):
        return f'<EscrowTransaction {self.id} - {self.transaction_type} - {self.amount}>'
    
# app/models/escrow.py

class EscrowTransaction(db.Model):
    """تراکنش‌های صندوق امانی سامانه"""
    __tablename__ = 'escrow_transactions'
    __table_args__ = {'extend_existing': True}
    
    id = db.Column(db.Integer, primary_key=True)
    escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=False)
    project_id = db.Column(db.Integer, db.ForeignKey('projects.id'), nullable=True)
    
    # نوع تراکنش
    transaction_type = db.Column(db.String(20), nullable=False)
    
    # مبلغ تراکنش
    amount = db.Column(db.Float, nullable=False)
    
    # اطلاعات واریز
    tracking_code = db.Column(db.String(100), nullable=True)
    employer_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    source_bank = db.Column(db.String(100), nullable=True)
    source_account = db.Column(db.String(50), nullable=True)
    receipt_image = db.Column(db.String(200), nullable=True)
    
    # اطلاعات برداشت
    check_number = db.Column(db.String(50), nullable=True)
    employee_id = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    bank_check_id = db.Column(db.Integer, db.ForeignKey('bank_checks.id'), nullable=True)
    
    # اطلاعات انتقال
    from_escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=True)
    to_escrow_id = db.Column(db.Integer, db.ForeignKey('escrow_accounts.id'), nullable=True)
    
    # اطلاعات کارمزد
    fee_type = db.Column(db.String(50), nullable=True)
    fee_percentage = db.Column(db.Float, nullable=True)
    
    # اطلاعات برگشت
    refund_reason = db.Column(db.Text, nullable=True)
    original_transaction_id = db.Column(db.Integer, db.ForeignKey('escrow_transactions.id'), nullable=True)
    
    # وضعیت تراکنش
    status = db.Column(db.String(20), default='pending')
    
    # توضیحات
    description = db.Column(db.Text, nullable=True)
    
    # زمان‌ها
    created_at = db.Column(db.DateTime, default=datetime.utcnow)
    completed_at = db.Column(db.DateTime, nullable=True)
    
    # ثبت کننده
    created_by = db.Column(db.Integer, db.ForeignKey('users.id'), nullable=True)
    
    # ========== روابط ==========
    
    # رابطه با EscrowAccount
    escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[escrow_id],
        backref='transactions_ref'
    )
    
    # رابطه با Project
    project = db.relationship(
        'Project',
        foreign_keys=[project_id],
        backref='escrow_transactions'
    )
    
    # رابطه با Employer (User)
    employer = db.relationship(
        'User',
        foreign_keys=[employer_id],
        backref='escrow_deposits_ref'
    )
    
    # رابطه با Employee (User)
    employee = db.relationship(
        'User',
        foreign_keys=[employee_id],
        backref='escrow_withdrawals_ref'
    )
    
    # رابطه با BankCheck
    bank_check = db.relationship(
        'BankCheck',
        foreign_keys=[bank_check_id],
        backref='escrow_transaction_ref'
    )
    
    # رابطه با From Escrow
    from_escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[from_escrow_id],
        backref='transfers_out_ref'
    )
    
    # رابطه با To Escrow
    to_escrow = db.relationship(
        'EscrowAccount',
        foreign_keys=[to_escrow_id],
        backref='transfers_in_ref'
    )
    
    # ======== اصلاح نام رابطه با Creator ========
    # تغییر نام به escrow_transactions_created_by_ref
    creator = db.relationship(
        'User',
        foreign_keys=[created_by],
        backref='escrow_transactions_created_by_ref'  # تغییر نام
    )
    
    # رابطه با Original Transaction (خود ارجاعی)
    original_transaction = db.relationship(
        'EscrowTransaction',
        foreign_keys=[original_transaction_id],
        remote_side=[id],
        backref='refunds_ref'
    )
    
    # ========== متدها ==========
    
    def complete(self):
        self.status = 'completed'
        self.completed_at = datetime.utcnow()
    
    def fail(self, reason=None):
        self.status = 'failed'
        if reason:
            self.description = reason
    
    def cancel(self, reason=None):
        self.status = 'cancelled'
        if reason:
            self.description = reason
    
    @classmethod
    def create_deposit(cls, escrow_id, amount, tracking_code, employer_id, project_id=None,
                       source_bank=None, source_account=None, receipt_image=None, 
                       description=None, created_by=None):
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='deposit',
            amount=amount,
            tracking_code=tracking_code,
            employer_id=employer_id,
            source_bank=source_bank,
            source_account=source_account,
            receipt_image=receipt_image,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_withdraw(cls, escrow_id, amount, check_number, employee_id, project_id=None,
                        bank_check_id=None, description=None, created_by=None):
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='withdraw',
            amount=amount,
            check_number=check_number,
            employee_id=employee_id,
            bank_check_id=bank_check_id,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_fee(cls, escrow_id, amount, fee_type, fee_percentage, project_id=None,
                   description=None, created_by=None):
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='fee',
            amount=amount,
            fee_type=fee_type,
            fee_percentage=fee_percentage,
            description=description,
            created_by=created_by,
            status='completed'
        )
        transaction.completed_at = datetime.utcnow()
        return transaction
    
    @classmethod
    def create_transfer(cls, from_escrow_id, to_escrow_id, amount, project_id=None,
                        description=None, created_by=None):
        withdraw_transaction = cls(
            escrow_id=from_escrow_id,
            project_id=project_id,
            transaction_type='transfer',
            amount=amount,
            from_escrow_id=from_escrow_id,
            to_escrow_id=to_escrow_id,
            description=f'انتقال به صندوق {to_escrow_id} - {description or ""}',
            created_by=created_by,
            status='completed'
        )
        
        deposit_transaction = cls(
            escrow_id=to_escrow_id,
            project_id=project_id,
            transaction_type='transfer',
            amount=amount,
            from_escrow_id=from_escrow_id,
            to_escrow_id=to_escrow_id,
            description=f'انتقال از صندوق {from_escrow_id} - {description or ""}',
            created_by=created_by,
            status='completed'
        )
        
        return withdraw_transaction, deposit_transaction
    
    @classmethod
    def create_refund(cls, original_transaction_id, escrow_id, amount, reason, project_id=None,
                      description=None, created_by=None):
        transaction = cls(
            escrow_id=escrow_id,
            project_id=project_id,
            transaction_type='refund',
            amount=amount,
            refund_reason=reason,
            original_transaction_id=original_transaction_id,
            description=description,
            created_by=created_by,
            status='pending'
        )
        return transaction
    
    def get_type_display(self):
        type_map = {
            'deposit': 'واریز',
            'withdraw': 'برداشت',
            'transfer': 'انتقال',
            'fee': 'کارمزد',
            'refund': 'برگشت'
        }
        return type_map.get(self.transaction_type, self.transaction_type)
    
    def get_status_display(self):
        status_map = {
            'pending': 'در انتظار',
            'completed': 'تکمیل شده',
            'failed': 'خطا',
            'cancelled': 'لغو شده'
        }
        return status_map.get(self.status, self.status)
    
    def to_dict(self):
        return {
            'id': self.id,
            'project_id': self.project_id,
            'project_name': self.project.name if self.project else None,
            'type': self.transaction_type,
            'type_display': self.get_type_display(),
            'amount': self.amount,
            'amount_formatted': f"{self.amount:,.0f}",
            'status': self.status,
            'status_display': self.get_status_display(),
            'tracking_code': self.tracking_code,
            'check_number': self.check_number,
            'employer_name': self.employer.fullname if self.employer else None,
            'employee_name': self.employee.fullname if self.employee else None,
            'description': self.description,
            'created_at': self.created_at.strftime('%Y-%m-%d %H:%M:%S'),
            'completed_at': self.completed_at.strftime('%Y-%m-%d %H:%M:%S') if self.completed_at else None,
            'creator_name': self.creator.fullname if self.creator else None
        }
    
    def __repr__(self):
        return f'<EscrowTransaction {self.id} - {self.transaction_type} - {self.amount}>'