#!/usr/bin/env python3
"""
Security Migration Script
Migrates existing SHA-256 passwords to bcrypt
MUST be run after upgrading to bcrypt-based authentication
"""

import sys
import os
sys.path.insert(0, os.path.dirname(__file__))

from postgresql_models import SessionLocal, User
import bcrypt
import logging

logging.basicConfig(level=logging.INFO)
logger = logging.getLogger(__name__)

def migrate_passwords():
    """
    Migrate all SHA-256 passwords to bcrypt
    This should be run ONCE after upgrading to bcrypt
    """
    db = SessionLocal()
    try:
        users = db.query(User).all()
        logger.info(f"Found {len(users)} users to check")
        
        migrated = 0
        for user in users:
            # Check if password is already bcrypt (starts with $2b$)
            if user.password_hash.startswith('$2b$') or user.password_hash.startswith('$2a$'):
                logger.info(f"User {user.username} already using bcrypt - skipping")
                continue
            
            # Check if this is a SHA-256 hash (64 hex characters)
            if len(user.password_hash) == 64 and all(c in '0123456789abcdef' for c in user.password_hash):
                logger.warning(f"User {user.username} has SHA-256 hash - CANNOT migrate automatically")
                logger.warning(f"  User must reset password or admin must set new password")
                logger.warning(f"  To set new password: user.set_password('new_password')")
            else:
                logger.warning(f"User {user.username} has unknown hash format: {user.password_hash[:20]}...")
        
        logger.info(f"Migration complete. {migrated} passwords migrated.")
        logger.warning("")
        logger.warning("IMPORTANT: Users with SHA-256 passwords must reset their passwords!")
        logger.warning("  Option 1: Users can request password reset")
        logger.warning("  Option 2: Admin can manually set new passwords using user.set_password()")
        
    except Exception as e:
        logger.error(f"Migration failed: {e}")
        db.rollback()
        return 1
    finally:
        db.close()
    
    return 0

def create_default_admin(username='admin', password=None):
    """
    Create a default admin user with bcrypt password
    Use this to create the first admin account
    """
    db = SessionLocal()
    try:
        # Check if user exists
        existing = db.query(User).filter(User.username == username).first()
        if existing:
            logger.error(f"User {username} already exists")
            return 1
        
        if not password:
            logger.error("Password is required")
            return 1
        
        # Create new admin user
        admin = User(
            username=username,
            role='admin',
            permissions='view,edit,modify,settings',
            active=True
        )
        admin.set_password(password)
        
        db.add(admin)
        db.commit()
        
        logger.info(f"✓ Admin user '{username}' created successfully with bcrypt password")
        return 0
        
    except Exception as e:
        logger.error(f"Failed to create admin: {e}")
        db.rollback()
        return 1
    finally:
        db.close()

if __name__ == '__main__':
    import argparse
    
    parser = argparse.ArgumentParser(description='Security migration tool')
    parser.add_argument('--migrate', action='store_true', help='Migrate SHA-256 passwords to bcrypt')
    parser.add_argument('--create-admin', action='store_true', help='Create default admin user')
    parser.add_argument('--username', default='admin', help='Username for new admin')
    parser.add_argument('--password', help='Password for new admin')
    
    args = parser.parse_args()
    
    if args.create_admin:
        if not args.password:
            print("ERROR: --password required when creating admin")
            sys.exit(1)
        sys.exit(create_default_admin(args.username, args.password))
    
    if args.migrate:
        sys.exit(migrate_passwords())
    
    parser.print_help()
    sys.exit(1)
