use fully_pub::fully_pub; use tower_http::services::ServeDir; use anyhow::{Result, Context, anyhow}; use log::info; use minijinja::{context, Environment}; use sqlx::{Pool, Sqlite}; use crate::{models::config::Config, router::build_router}; fn build_templating_env(config: &Config) -> Environment<'static> { let mut templating_env = Environment::new(); let _ = templating_env .add_template("layouts/base.html", include_str!("./templates/layouts/base.html")); let _ = templating_env .add_template("pages/home.html", include_str!("./templates/pages/home.html")); // TODO: better loading with embed https://docs.rs/minijinja-embed/latest/minijinja_embed/ templating_env.add_global("gl", context! { instance => context! { version => "1.243".to_string() } }); templating_env } #[derive(Debug)] #[fully_pub] /// HTTP server arguments pub struct ServerConfig { listen_host: String, listen_port: u32, assets_path: String } #[derive(Debug, Clone)] #[fully_pub] pub struct AppState { config: Config, db: Pool, templating_env: Environment<'static> } pub async fn start_http_server(server_config: ServerConfig, config: Config, db_pool: Pool) -> Result<()> { // build state let state = AppState { templating_env: build_templating_env(&config), config, db: db_pool }; // build routes let services = build_router() .nest_service( "/assets", ServeDir::new(server_config.assets_path) ) .with_state(state); let listen_addr = format!("{}:{}", server_config.listen_host, server_config.listen_port); info!("Starting web server on http://{}", &listen_addr); let listener = tokio::net::TcpListener::bind(listen_addr).await.unwrap(); axum::serve(listener, services).await.context("Axum serve")?; Ok(()) }