import os import gradio as gr from src.db.connection import resolve_db_path, get_conn from src.db.schema import init_schema from src.db.seed import seed_if_empty from src.services.scheduler_service import auto_close_if_needed from src.ui.login_ui import render_login from src.ui.rooms_ui import render_rooms_tab from src.ui.reservations_ui import render_reservations_tab from src.ui.payments_ui import render_payments_tab from src.ui.income_expense_ui import render_income_expense_tab from src.ui.closing_ui import render_closing_tab from src.ui.admin_ui import render_admin_tab def bootstrap(): db_path, persistent = resolve_db_path() conn = get_conn(db_path) try: init_schema(conn) seed_if_empty(conn) finally: conn.close() auto_close_if_needed( db_path=db_path, actor="system", note="Auto-close on startup", ) return db_path, persistent DB_PATH, IS_PERSISTENT = bootstrap() with gr.Blocks(title="Venus Hotel Front Desk") as demo: gr.Markdown("# 🏨 Venus Hotel Front Desk") if not IS_PERSISTENT: gr.Markdown("⚠️ Persistent storage is NOT enabled.") auth_state = gr.State(None) selected_room_state = gr.State(None) header_user = gr.Markdown("🔒 Not logged in") def update_header(auth): if not auth: return "🔒 Not logged in" return f"👤 Logged in as **{auth['username']}** ({auth['role']})" render_login(DB_PATH, auth_state) auth_state.change( update_header, inputs=[auth_state], outputs=[header_user], ) with gr.Tabs(): with gr.Tab("Rooms"): render_rooms_tab(DB_PATH, auth_state, selected_room_state) with gr.Tab("Reservations"): render_reservations_tab(DB_PATH, auth_state) with gr.Tab("Payments"): render_payments_tab(DB_PATH, auth_state) with gr.Tab("Income & Expenses"): render_income_expense_tab(DB_PATH, auth_state) with gr.Tab("Daily Closing"): render_closing_tab(DB_PATH, auth_state) with gr.Tab("Admin"): render_admin_tab(DB_PATH, auth_state) if __name__ == "__main__": demo.queue(default_concurrency_limit=16).launch( server_name="0.0.0.0", server_port=int(os.environ.get("PORT", 7860)), )