import os
import json
from flask import Flask, request, session, current_app
from flask_sqlalchemy import SQLAlchemy
from flask_login import LoginManager
from sqlalchemy import event
from sqlalchemy.engine import Engine

db = SQLAlchemy()
login_manager = LoginManager()

@event.listens_for(Engine, "connect")
def set_sqlite_pragma(dbapi_connection, connection_record):
    if dbapi_connection.__class__.__module__ == "sqlite3":
        cursor = dbapi_connection.cursor()
        cursor.execute("PRAGMA journal_mode=WAL")
        cursor.execute("PRAGMA synchronous=NORMAL")
        cursor.close()

# Load all i18n jsons
i18n_dict = {}

def load_i18n(app):
    global i18n_dict
    i18n_dir = os.path.join(app.root_path, 'assets', 'i18n')
    if os.path.exists(i18n_dir):
        for f in os.listdir(i18n_dir):
            if f.endswith('.json'):
                lang_code = f.replace('.json', '')
                with open(os.path.join(i18n_dir, f), 'r', encoding='utf-8') as jf:
                    i18n_dict[lang_code] = json.load(jf)

def get_locale():
    # 用户手动选择的语言保存在 cookie 中优先
    lang = request.cookies.get('lang')
    if lang in i18n_dict:
        return lang
    
    # Check accept_languages with our available dict keys
    best_match = request.accept_languages.best_match(list(i18n_dict.keys()))
    return best_match if best_match else 'en'

def _t(key):
    lang = get_locale()
    # Fallback to english if language missing or key missing
    if lang in i18n_dict and key in i18n_dict[lang]:
        return i18n_dict[lang][key]
    if 'en' in i18n_dict and key in i18n_dict['en']:
        return i18n_dict['en'][key]
    return key # fallback to the key itself

def create_app():
    app = Flask(__name__, static_url_path='/assets', static_folder='assets')
    app.config['SECRET_KEY'] = 'your-secret-key-change-it-in-production'
    app.config['SESSION_COOKIE_NAME'] = 'aio_session'  # Prevent collision with OctoPrint's 'session' cookie
    app.config['REMEMBER_COOKIE_NAME'] = 'aio_remember'
    app.config['SQLALCHEMY_DATABASE_URI'] = 'sqlite:///../instance/aio_3d.db'
    app.config['SQLALCHEMY_ENGINE_OPTIONS'] = {'connect_args': {'timeout': 15}}
    app.config['UPLOAD_FOLDER'] = os.path.abspath(os.path.join(app.root_path, '..', 'uploads'))
    
    os.makedirs(app.config['UPLOAD_FOLDER'], exist_ok=True)
    
    load_i18n(app)
    
    db.init_app(app)
    login_manager.init_app(app)
    
    # Inject translation function into jinja
    @app.context_processor
    def inject_i18n():
        return dict(_=_t)
    
    login_manager.login_view = 'auth.login'
    
    with app.app_context():
        from . import models
        db.create_all()
        
    from .routes.main_routes import main_bp
    from .routes.auth_routes import auth_bp
    from .routes.admin_routes import admin_bp
    from .routes.printer_routes import printer_bp
    app.register_blueprint(main_bp)
    app.register_blueprint(auth_bp)
    app.register_blueprint(admin_bp)
    app.register_blueprint(printer_bp)

    return app
