#![recursion_limit = "256"] mod admin; mod ai_generation_drafts; mod ai_tasks; mod api_response; mod app; mod asset_billing; mod assets; mod auth; mod auth_me; mod auth_payload; mod auth_public_user; mod auth_session; mod auth_sessions; mod big_fish; mod big_fish_agent_turn; mod big_fish_draft_compiler; mod character_animation_assets; mod character_visual_assets; mod config; mod creation_agent_anchor_templates; mod creation_agent_chat; mod creation_agent_document_input; mod creation_agent_llm_turn; mod custom_world; mod custom_world_agent_entities; mod custom_world_agent_turn; mod custom_world_ai; mod custom_world_asset_prompts; mod custom_world_foundation_draft; mod custom_world_result_prompts; mod custom_world_rpg_draft_prompts; mod error_middleware; mod health; mod http_error; mod legacy_generated_assets; mod llm; mod login_options; mod logout; mod logout_all; mod match3d; mod password_entry; mod password_management; mod phone_auth; mod profile_identity; mod prompt; mod puzzle; mod puzzle_agent_turn; mod refresh_session; mod request_context; mod response_headers; mod runtime_browse_history; mod runtime_chat; mod runtime_chat_plain; mod runtime_inventory; mod runtime_profile; mod runtime_save; mod runtime_settings; mod runtime_story; mod session_client; mod state; mod story_battles; mod story_sessions; mod wechat_auth; mod wechat_provider; use shared_logging::init_tracing; use tokio::net::TcpListener; use tracing::info; use crate::{app::build_router, config::AppConfig, state::AppState}; #[tokio::main] async fn main() -> Result<(), std::io::Error> { // 运行本地开发与联调时,优先从仓库根目录的 .env / .env.local 加载变量,避免手工逐项导出 OSS 配置。 let _ = dotenvy::from_filename(".env"); let _ = dotenvy::from_filename(".env.local"); // 统一先从配置对象读取监听地址,避免后续把环境变量读取散落到入口和路由层。 let config = AppConfig::from_env(); init_tracing(&config.log_filter)?; let bind_address = config.bind_socket_addr(); let listener = TcpListener::bind(bind_address).await?; let state = AppState::try_restore_auth_store_from_spacetime(config) .await .map_err(|error| std::io::Error::other(format!("初始化应用状态失败:{error}")))?; let router = build_router(state); info!(%bind_address, "api-server 已完成 tracing 初始化并开始监听"); axum::serve(listener, router).await }