from flask import Flask, request, jsonify, send_file, send_from_directory
from flask_cors import CORS
import os
from werkzeug.utils import secure_filename
import json
from datetime import datetime
import shutil

app = Flask(__name__, static_folder='static', template_folder='templates')
CORS(app)

# Configuración
UPLOAD_FOLDER = 'uploads'
ALLOWED_EXTENSIONS = {
    'txt', 'pdf', 'png', 'jpg', 'jpeg', 'gif', 'zip', 'rar', 
    'exe', 'apk', 'json', 'xml', 'csv', 'py', 'js', 'html', 
    'css', 'doc', 'docx', 'xls', 'xlsx', 'sql', 'db', 'ini', 
    'conf', 'msi', 'dll', 'bat', 'sh', 'tar', 'gz', '7z'
}
MAX_CONTENT_LENGTH = 1000 * 1024 * 1024  # 1GB max

app.config['UPLOAD_FOLDER'] = UPLOAD_FOLDER
app.config['MAX_CONTENT_LENGTH'] = MAX_CONTENT_LENGTH

# Crear carpeta uploads si no existe
if not os.path.exists(UPLOAD_FOLDER):
    os.makedirs(UPLOAD_FOLDER)

# Crear carpetas específicas para cada versión de MIG
carpetas_mig = [
    'uploads/MIG_DAVID_GALLO',
    'uploads/MIG_MAYORIA',
    'uploads/MIG_SERVIEXPRESS',
    'uploads/MIG_UPDATER'
]

for carpeta in carpetas_mig:
    if not os.path.exists(carpeta):
        os.makedirs(carpeta)
        print(f"✓ Carpeta creada: {carpeta}")

def allowed_file(filename):
    return '.' in filename and filename.rsplit('.', 1)[1].lower() in ALLOWED_EXTENSIONS

# Ruta principal - servir index.html
@app.route('/')
def index():
    return send_from_directory('templates', 'index.html')

# Servir archivos estáticos
@app.route('/static/<path:path>')
def send_static(path):
    return send_from_directory('static', path)

# API: Listar carpetas y archivos
@app.route('/api/list', methods=['GET'])
def list_files():
    try:
        folder = request.args.get('folder', '')
        path = os.path.join(UPLOAD_FOLDER, folder)
        
        if not os.path.exists(path):
            return jsonify({'error': 'Carpeta no encontrada'}), 404
        
        items = []
        for item in os.listdir(path):
            try:
                item_path = os.path.join(path, item)
                is_dir = os.path.isdir(item_path)
                size = os.path.getsize(item_path) if not is_dir else 0
                modified = datetime.fromtimestamp(os.path.getmtime(item_path)).strftime('%Y-%m-%d %H:%M:%S')
                
                items.append({
                    'name': item,
                    'type': 'folder' if is_dir else 'file',
                    'size': size,
                    'modified': modified,
                    'path': os.path.join(folder, item).replace('\\', '/')
                })
            except Exception as e:
                print(f"Error procesando {item}: {str(e)}")
                continue
        
        return jsonify({'items': items, 'current_path': folder})
    except Exception as e:
        return jsonify({'error': str(e)}), 500

# API: Crear carpeta
@app.route('/api/create-folder', methods=['POST'])
def create_folder():
    try:
        data = request.get_json(force=True)
        folder_name = secure_filename(data.get('name', ''))
        parent_path = data.get('parent', '')
        
        if not folder_name:
            return jsonify({'error': 'Nombre de carpeta inválido'}), 400
        
        new_folder_path = os.path.join(UPLOAD_FOLDER, parent_path, folder_name)
        
        os.makedirs(new_folder_path, exist_ok=True)
        return jsonify({
            'message': 'Carpeta creada exitosamente', 
            'path': os.path.join(parent_path, folder_name).replace('\\', '/')
        })
    except Exception as e:
        return jsonify({'error': str(e)}), 500

# API: Subir archivo
@app.route('/api/upload', methods=['POST'])
def upload_file():
    try:
        if 'file' not in request.files:
            return jsonify({'error': 'No se encontró el archivo'}), 400
        
        file = request.files['file']
        folder = request.form.get('folder', '')
        
        if file.filename == '':
            return jsonify({'error': 'No se seleccionó ningún archivo'}), 400
        
        if file:
            filename = secure_filename(file.filename)
            upload_path = os.path.join(UPLOAD_FOLDER, folder)
            
            if not os.path.exists(upload_path):
                os.makedirs(upload_path)
            
            file_path = os.path.join(upload_path, filename)
            file.save(file_path)
            
            return jsonify({
                'message': 'Archivo subido exitosamente',
                'filename': filename,
                'path': os.path.join(folder, filename).replace('\\', '/')
            })
        
        return jsonify({'error': 'Error al procesar el archivo'}), 400
    except Exception as e:
        return jsonify({'error': f'Error al subir archivo: {str(e)}'}), 500

# API: Descargar archivo (ENDPOINT PARA EL POS)
@app.route('/api/download/<path:filepath>', methods=['GET'])
def download_file(filepath):
    try:
        file_path = os.path.join(UPLOAD_FOLDER, filepath)
        
        if not os.path.exists(file_path):
            return jsonify({'error': 'Archivo no encontrado'}), 404
        
        return send_file(file_path, as_attachment=True)
    except Exception as e:
        return jsonify({'error': str(e)}), 500

# API: Eliminar archivo o carpeta
@app.route('/api/delete', methods=['DELETE'])
def delete_item():
    try:
        data = request.get_json(force=True)
        item_path = data.get('path', '')
        
        full_path = os.path.join(UPLOAD_FOLDER, item_path)
        
        if not os.path.exists(full_path):
            return jsonify({'error': 'Elemento no encontrado'}), 404
        
        if os.path.isdir(full_path):
            shutil.rmtree(full_path)
        else:
            os.remove(full_path)
        
        return jsonify({'message': 'Elemento eliminado exitosamente'})
    except Exception as e:
        return jsonify({'error': str(e)}), 500

# API: Obtener información del servidor (para el POS)
@app.route('/api/info', methods=['GET'])
def server_info():
    return jsonify({
        'server': 'UpdaterMIG',
        'version': '1.0',
        'status': 'online',
        'timestamp': datetime.now().isoformat()
    })

# API: Listar todos los archivos disponibles para descarga (para el POS)
@app.route('/api/available-files', methods=['GET'])
def available_files():
    try:
        all_files = []
        
        for root, dirs, files in os.walk(UPLOAD_FOLDER):
            for file in files:
                try:
                    file_path = os.path.join(root, file)
                    rel_path = os.path.relpath(file_path, UPLOAD_FOLDER).replace('\\', '/')
                    size = os.path.getsize(file_path)
                    modified = datetime.fromtimestamp(os.path.getmtime(file_path)).isoformat()
                    
                    all_files.append({
                        'name': file,
                        'path': rel_path,
                        'size': size,
                        'modified': modified,
                        'download_url': f'/api/download/{rel_path}'
                    })
                except Exception as e:
                    print(f"Error procesando archivo {file}: {str(e)}")
                    continue
        
        return jsonify({'files': all_files, 'total': len(all_files)})
    except Exception as e:
        return jsonify({'error': str(e)}), 500

if __name__ == '__main__':
    # Importar configuración si existe
    try:
        from config import HOST, PORT, DEBUG
    except ImportError:
        HOST = '0.0.0.0'
        PORT = 98
        DEBUG = False
    
    print("=" * 60)
    print(f"🚀 UpdaterMIG Server Starting...")
    print(f"   Host: {HOST}")
    print(f"   Port: {PORT}")
    print(f"   Debug: {DEBUG}")
    print(f"   Upload Folder: {UPLOAD_FOLDER}")
    print("=" * 60)
    
    app.run(debug=DEBUG, host=HOST, port=PORT)