diff --git a/helpers/pagetop-build/README.md b/helpers/pagetop-build/README.md index 80d6bba..5af492b 100644 --- a/helpers/pagetop-build/README.md +++ b/helpers/pagetop-build/README.md @@ -83,33 +83,41 @@ Este código compila el archivo `main.scss` de la carpeta `static` del proyecto, llamado `main_styles` que contiene el archivo `styles.min.css` obtenido. -# 📦 Archivos generados +# 📦 Módulos generados Cada conjunto de recursos [`StaticFilesBundle`] genera un archivo en el directorio estándar [OUT_DIR](https://doc.rust-lang.org/cargo/reference/environment-variables.html#environment-variables-cargo-sets-for-build-scripts) -donde se incluye el código necesario para compilar el proyecto. Por ejemplo, para -`with_name("guides")` se genera un archivo llamado `guides.rs`. +donde se incluyen los recursos necesarios para compilar el proyecto. Por ejemplo, para +`with_name("guides")` se crea un archivo llamado `guides.rs`. -No hay ningún problema en generar más de un conjunto de recursos para cada proyecto siempre que se -usen nombres diferentes. +No hay ningún problema en generar más de un conjunto de recursos para cada proyecto. -Normalmente no habrá que acceder a estos módulos; sólo declarar el nombre del conjunto de recursos -en [`static_files_service!`](https://docs.rs/pagetop/latest/pagetop/macro.static_files_service.html) -para configurar un servicio web que sirva los archivos desde la ruta indicada. Por ejemplo: +Normalmente no habrá que acceder a estos módulos; bastará con incluirlos en el proyecto con +[`include_files!`](https://docs.rs/pagetop/latest/pagetop/macro.include_files.html), y luego con +[`include_files_service!`](https://docs.rs/pagetop/latest/pagetop/macro.include_files_service.html) +configurar un servicio web para servir los recursos desde la ruta indicada: ```rust,ignore use pagetop::prelude::*; +include_files!(guides); + pub struct MyExtension; impl Extension for MyExtension { // Servicio web que publica los recursos de `guides` en `/ruta/a/guides`. fn configure_service(&self, scfg: &mut service::web::ServiceConfig) { - static_files_service!(scfg, guides => "/ruta/a/guides"); + include_files_service!(scfg, guides => "/ruta/a/guides"); } } ``` +También se puede asignar el conjunto de recursos a una variable global; p.ej. `GUIDES`: + +```rust,ignore +include_files!(GUIDES => guides); +``` + # 🚧 Advertencia diff --git a/helpers/pagetop-build/src/lib.rs b/helpers/pagetop-build/src/lib.rs index c6e7236..09dec42 100644 --- a/helpers/pagetop-build/src/lib.rs +++ b/helpers/pagetop-build/src/lib.rs @@ -84,32 +84,40 @@ Este código compila el archivo `main.scss` de la carpeta `static` del proyecto, llamado `main_styles` que contiene el archivo `styles.min.css` obtenido. -# 📦 Archivos generados +# 📦 Módulos generados Cada conjunto de recursos [`StaticFilesBundle`] genera un archivo en el directorio estándar [OUT_DIR](https://doc.rust-lang.org/cargo/reference/environment-variables.html#environment-variables-cargo-sets-for-build-scripts) -donde se incluye el código necesario para compilar el proyecto. Por ejemplo, para -`with_name("guides")` se genera un archivo llamado `guides.rs`. +donde se incluyen los recursos necesarios para compilar el proyecto. Por ejemplo, para +`with_name("guides")` se crea un archivo llamado `guides.rs`. -No hay ningún problema en generar más de un conjunto de recursos para cada proyecto siempre que se -usen nombres diferentes. +No hay ningún problema en generar más de un conjunto de recursos para cada proyecto. -Normalmente no habrá que acceder a estos módulos; sólo declarar el nombre del conjunto de recursos -en [`static_files_service!`](https://docs.rs/pagetop/latest/pagetop/macro.static_files_service.html) -para configurar un servicio web que sirva los archivos desde la ruta indicada. Por ejemplo: +Normalmente no habrá que acceder a estos módulos; bastará con incluirlos en el proyecto con +[`include_files!`](https://docs.rs/pagetop/latest/pagetop/macro.include_files.html), y luego con +[`include_files_service!`](https://docs.rs/pagetop/latest/pagetop/macro.include_files_service.html) +configurar un servicio web para servir los recursos desde la ruta indicada: ```rust,ignore use pagetop::prelude::*; +include_files!(guides); + pub struct MyExtension; impl Extension for MyExtension { // Servicio web que publica los recursos de `guides` en `/ruta/a/guides`. fn configure_service(&self, scfg: &mut service::web::ServiceConfig) { - static_files_service!(scfg, guides => "/ruta/a/guides"); + include_files_service!(scfg, guides => "/ruta/a/guides"); } } ``` + +También se puede asignar el conjunto de recursos a una variable global; p.ej. `GUIDES`: + +```rust,ignore +include_files!(GUIDES => guides); +``` */ #![doc( diff --git a/src/config.rs b/src/config.rs index 27cf630..08067fe 100644 --- a/src/config.rs +++ b/src/config.rs @@ -110,13 +110,11 @@ //! } //! ``` -use crate::util; - use config::builder::DefaultState; use config::{Config, ConfigBuilder, File}; use std::env; -use std::path::PathBuf; +use std::path::{Path, PathBuf}; use std::sync::LazyLock; // Nombre del directorio de configuración por defecto. @@ -127,12 +125,25 @@ const DEFAULT_RUN_MODE: &str = "default"; /// Valores originales cargados desde los archivos de configuración como pares `clave = valor`. pub static CONFIG_VALUES: LazyLock> = LazyLock::new(|| { - // CONFIG_DIR (si existe) o DEFAULT_CONFIG_DIR. Si no se puede resolver, se usa tal cual. - let dir = env::var_os("CONFIG_DIR").unwrap_or_else(|| DEFAULT_CONFIG_DIR.into()); - let config_dir = util::resolve_absolute_dir(&dir).unwrap_or_else(|_| PathBuf::from(&dir)); + // Determina el directorio de configuración: + // - Usa CONFIG_DIR si está definido en el entorno (p.ej.: CONFIG_DIR=/etc/myapp ./myapp). + // - Si no, intenta DEFAULT_CONFIG_DIR dentro del proyecto (en CARGO_MANIFEST_DIR). + // - Si nada de esto aplica, entonces usa DEFAULT_CONFIG_DIR relativo al ejecutable. + let config_dir: PathBuf = if let Ok(env_dir) = env::var("CONFIG_DIR") { + env_dir.into() + } else if let Ok(manifest_dir) = env::var("CARGO_MANIFEST_DIR") { + let manifest_config = Path::new(&manifest_dir).join(DEFAULT_CONFIG_DIR); + if manifest_config.exists() { + manifest_config + } else { + DEFAULT_CONFIG_DIR.into() + } + } else { + DEFAULT_CONFIG_DIR.into() + }; - // Modo de ejecución según la variable de entorno PAGETOP_RUN_MODE. Si no está definida, se usa - // por defecto, DEFAULT_RUN_MODE (p.ej.: PAGETOP_RUN_MODE=production). + // Determina el modo de ejecución según la variable de entorno PAGETOP_RUN_MODE. Por defecto usa + // DEFAULT_RUN_MODE si no está definida (p.ej.: PAGETOP_RUN_MODE=production ./myapp). let rm = env::var("PAGETOP_RUN_MODE").unwrap_or_else(|_| DEFAULT_RUN_MODE.into()); Config::builder() diff --git a/src/core/extension/all.rs b/src/core/extension/all.rs index a243778..93b5c4b 100644 --- a/src/core/extension/all.rs +++ b/src/core/extension/all.rs @@ -1,7 +1,7 @@ use crate::core::action::add_action; use crate::core::extension::ExtensionRef; use crate::core::theme::all::THEMES; -use crate::{global, service, static_files_service, trace}; +use crate::{global, include_files, include_files_service, service, trace}; use parking_lot::RwLock; @@ -125,6 +125,8 @@ pub fn initialize_extensions() { // CONFIGURA LOS SERVICIOS ************************************************************************* +include_files!(assets); + pub fn configure_services(scfg: &mut service::web::ServiceConfig) { // Sólo compila durante el desarrollo, para evitar errores 400 en la traza de eventos. #[cfg(debug_assertions)] @@ -138,5 +140,7 @@ pub fn configure_services(scfg: &mut service::web::ServiceConfig) { extension.configure_service(scfg); } - static_files_service!(scfg, [&global::SETTINGS.dev.pagetop_static_dir, assets] => "/"); + include_files_service!( + scfg, assets => "/", [&global::SETTINGS.dev.pagetop_project_dir, "static"] + ); } diff --git a/src/global.rs b/src/global.rs index 8a03589..ea659b8 100644 --- a/src/global.rs +++ b/src/global.rs @@ -13,7 +13,7 @@ include_config!(SETTINGS: Settings => [ "app.startup_banner" => "Slant", // [dev] - "dev.pagetop_static_dir" => "", + "dev.pagetop_project_dir" => "", // [log] "log.enabled" => true, @@ -68,15 +68,11 @@ pub struct App { #[derive(Debug, Deserialize)] /// Sección `[Dev]` de la configuración. Forma parte de [`Settings`]. pub struct Dev { - /// Directorio desde el que servir los archivos estáticos de `PageTop`. - /// - /// Por defecto, los archivos se integran en el binario de la aplicación. Si aquí se indica una - /// ruta válida, ya sea absoluta o relativa al directorio del proyecto o del binario en - /// ejecución, se servirán desde el sistema de ficheros en su lugar. Esto es especialmente útil - /// en desarrollo, ya que evita recompilar el proyecto por cambios en estos archivos. - /// - /// Si la cadena está vacía, se ignora este ajuste. - pub pagetop_static_dir: String, + /// Los archivos estáticos requeridos por `PageTop` se integran por defecto en el binario + /// ejecutable. Sin embargo, durante el desarrollo puede resultar útil servirlos desde su propio + /// directorio para evitar recompilar cada vez que se modifican. En ese caso, este ajuste debe + /// indicar la ruta absoluta al directorio raíz del proyecto. + pub pagetop_project_dir: String, } #[derive(Debug, Deserialize)] diff --git a/src/html/assets/favicon.rs b/src/html/assets/favicon.rs index 1a8b29e..2af0173 100644 --- a/src/html/assets/favicon.rs +++ b/src/html/assets/favicon.rs @@ -12,7 +12,8 @@ use crate::AutoDefault; /// /// > **Nota** /// > Los archivos de los iconos deben estar disponibles en el servidor web de la aplicación. Pueden -/// > servirse usando [`static_files_service!`](crate::static_files_service). +/// > incluirse en el proyecto utilizando [`include_files!`](crate::include_files) y servirse con +/// > [`include_files_service!`](crate::include_files_service). /// /// # Ejemplo /// diff --git a/src/html/assets/javascript.rs b/src/html/assets/javascript.rs index db5754e..604e85a 100644 --- a/src/html/assets/javascript.rs +++ b/src/html/assets/javascript.rs @@ -30,7 +30,8 @@ enum Source { /// /// > **Nota** /// > Los archivos de los *scripts* deben estar disponibles en el servidor web de la aplicación. -/// > Pueden servirse usando [`static_files_service!`](crate::static_files_service). +/// > Pueden incluirse en el proyecto utilizando [`include_files!`](crate::include_files) y servirse +/// > con [`include_files_service!`](crate::include_files_service). /// /// # Ejemplo /// diff --git a/src/html/assets/stylesheet.rs b/src/html/assets/stylesheet.rs index bb60b01..72a79a1 100644 --- a/src/html/assets/stylesheet.rs +++ b/src/html/assets/stylesheet.rs @@ -55,7 +55,8 @@ impl TargetMedia { /// /// > **Nota** /// > Las hojas de estilo CSS deben estar disponibles en el servidor web de la aplicación. Pueden -/// > servirse usando [`static_files_service!`](crate::static_files_service). +/// > incluirse en el proyecto utilizando [`include_files!`](crate::include_files) y servirse con +/// > [`include_files_service!`](crate::include_files_service). /// /// # Ejemplo /// diff --git a/src/lib.rs b/src/lib.rs index 90ea462..d50a448 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -103,8 +103,7 @@ pub use pagetop_macros::{builder_fn, html, main, test, AutoDefault}; pub use pagetop_statics::{resource, StaticResource}; -/// Contenedor para un conjunto de recursos embebidos. -#[derive(AutoDefault)] +/// Conjunto de recursos asociados a `$STATIC` en [`include_files!`](crate::include_files). pub struct StaticResources { bundle: HashMap<&'static str, StaticResource>, } diff --git a/src/prelude.rs b/src/prelude.rs index 9072dec..6bacaf3 100644 --- a/src/prelude.rs +++ b/src/prelude.rs @@ -15,8 +15,7 @@ pub use crate::include_config; // crate::locale pub use crate::include_locales; // crate::service -#[allow(deprecated)] -pub use crate::{include_files, include_files_service, static_files_service}; +pub use crate::{include_files, include_files_service}; // crate::core::action pub use crate::actions_boxed; diff --git a/src/service.rs b/src/service.rs index 288e1eb..47f1420 100644 --- a/src/service.rs +++ b/src/service.rs @@ -15,9 +15,6 @@ pub use pagetop_statics::ResourceFiles; #[doc(hidden)] pub use actix_web::test; -/// **Obsoleto desde la versión 0.3.0**: usar [`static_files_service!`](crate::static_files_service) -/// en su lugar. -/// /// Incluye en código un conjunto de recursos previamente preparado con `build.rs`. /// /// # Formas de uso @@ -42,7 +39,6 @@ pub use actix_web::test; /// /// include_files!(STATIC_ASSETS => assets); /// ``` -#[deprecated(since = "0.3.0", note = "Use `static_files_service!` instead")] #[macro_export] macro_rules! include_files { // Forma 1: incluye un conjunto de recursos por nombre. @@ -67,9 +63,6 @@ macro_rules! include_files { }; } -/// **Obsoleto desde la versión 0.3.0**: usar [`static_files_service!`](crate::static_files_service) -/// en su lugar. -/// /// Configura un servicio web para publicar los recursos embebidos con [`include_files!`]. /// /// El código expandido de la macro decide durante el arranque de la aplicación si debe servir los @@ -111,7 +104,6 @@ macro_rules! include_files { /// // También desde el directorio actual de ejecución. /// include_files_service!(cfg, assets => "/public", ["", "static"]); /// ``` -#[deprecated(since = "0.3.0", note = "Use `static_files_service!` instead")] #[macro_export] macro_rules! include_files_service { ( $scfg:ident, $bundle:ident => $route:expr $(, [$root:expr, $relative:expr])? ) => {{ @@ -145,114 +137,3 @@ macro_rules! include_files_service { } }}; } - -/// Configura un servicio web para publicar archivos estáticos. -/// -/// La macro ofrece tres modos para configurar el servicio: -/// -/// - **Sistema de ficheros o embebido** (`[$path, $bundle]`): trata de servir los archivos desde -/// `$path`; y si es una cadena vacía, no existe o no es un directorio, entonces usará el conjunto -/// de recursos `$bundle` integrado en el binario. -/// - **Sólo embebido** (`[$bundle]`): sirve siempre desde el conjunto de recursos `$bundle` -/// integrado en el binario. -/// - **Sólo sistema de ficheros** (`$path`): sin usar corchetes, sirve únicamente desde el sistema -/// de ficheros si existe; en otro caso no registra el servicio. -/// -/// # Argumentos -/// -/// * `$scfg` – Instancia de [`ServiceConfig`](crate::service::web::ServiceConfig) donde aplicar la -/// configuración. -/// * `$path` – Ruta al directorio local con los archivos estáticos. -/// * `$bundle` – Nombre del conjunto de recursos que esta macro integra en el binario. -/// * `$route` – Ruta URL base desde la que se servirán los archivos. -/// -/// # Ejemplos -/// -/// ```rust,ignore -/// use pagetop::prelude::*; -/// -/// pub struct MyExtension; -/// -/// impl Extension for MyExtension { -/// fn configure_service(&self, scfg: &mut service::web::ServiceConfig) { -/// // Forma 1) Sistema de ficheros o embebido. -/// static_files_service!(scfg, ["/var/www/static", assets] => "/public"); -/// -/// // Forma 2) Siempre embebido. -/// static_files_service!(scfg, [assets] => "/public"); -/// -/// // Forma 3) Sólo sistema de ficheros (no requiere `assets`). -/// static_files_service!(scfg, "/var/www/static" => "/public"); -/// } -/// } -/// ``` -#[macro_export] -macro_rules! static_files_service { - // Forma 1: primero intenta servir desde el sistema de ficheros; si falla, sirve embebido. - ( $scfg:ident, [$path:expr, $bundle:ident] => $route:expr $(,)? ) => {{ - let span = $crate::trace::debug_span!( - "Configuring static files (file system or embedded)", - mode = "fs_or_embedded", - route = $route, - ); - let _ = span.in_scope(|| { - let mut serve_embedded: bool = true; - if !::std::path::Path::new(&$path).as_os_str().is_empty() { - if let Ok(absolute) = $crate::util::resolve_absolute_dir($path) { - $scfg.service($crate::service::ActixFiles::new($route, absolute)); - serve_embedded = false; - } - } - if serve_embedded { - $crate::util::paste! { - mod [] { - include!(concat!(env!("OUT_DIR"), "/", stringify!($bundle), ".rs")); - } - $scfg.service($crate::service::ResourceFiles::new( - $route, - []::$bundle(), - )); - } - } - }); - }}; - // Forma 2: sirve siempre embebido. - ( $scfg:ident, [$bundle:ident] => $route:expr $(,)? ) => {{ - let span = $crate::trace::debug_span!( - "Configuring static files (using embedded only)", - mode = "embedded", - route = $route, - ); - let _ = span.in_scope(|| { - $crate::util::paste! { - mod [] { - include!(concat!(env!("OUT_DIR"), "/", stringify!($bundle), ".rs")); - } - $scfg.service($crate::service::ResourceFiles::new( - $route, - []::$bundle(), - )); - } - }); - }}; - // Forma 3: intenta servir desde el sistema de ficheros. - ( $scfg:ident, $path:expr => $route:expr $(,)? ) => {{ - let span = $crate::trace::debug_span!( - "Configuring static files (file system only)", - mode = "fs", - route = $route, - ); - let _ = span.in_scope(|| match $crate::util::resolve_absolute_dir($path) { - Ok(absolute) => { - $scfg.service($crate::service::ActixFiles::new($route, absolute)); - } - Err(e) => { - $crate::trace::warn!( - "Static dir not found or invalid for route `{}`: {:?} ({e})", - $route, - $path, - ); - } - }); - }}; -} diff --git a/src/util.rs b/src/util.rs index 21537c5..b605125 100644 --- a/src/util.rs +++ b/src/util.rs @@ -2,44 +2,35 @@ use crate::trace; -use std::env; use std::io; use std::path::{Path, PathBuf}; // FUNCIONES ÚTILES ******************************************************************************** -/// Resuelve y valida la ruta de un directorio existente, devolviendo una ruta absoluta. +/// Devuelve la ruta absoluta a un directorio existente. /// -/// - Si la ruta es relativa, se resuelve respecto al directorio del proyecto según la variable de -/// entorno `CARGO_MANIFEST_DIR` (si existe) o, en su defecto, respecto al directorio actual de -/// trabajo. -/// - Normaliza y valida la ruta final (resuelve `.`/`..` y enlaces simbólicos). -/// - Devuelve error si la ruta no existe o no es un directorio. +/// * Si `relative_path` es una ruta absoluta, entonces se ignora `root_path`. +/// * Si la ruta final es relativa, se convierte en absoluta respecto al directorio actual. +/// * Devuelve error si la ruta no existe o no es un directorio. /// -/// # Ejemplos +/// # Ejemplo /// /// ```rust,no_run /// use pagetop::prelude::*; /// -/// // Ruta relativa, se resuelve respecto a CARGO_MANIFEST_DIR o al directorio actual (`cwd`). -/// println!("{:#?}", util::resolve_absolute_dir("documents")); -/// -/// // Ruta absoluta, se normaliza y valida tal cual. -/// println!("{:#?}", util::resolve_absolute_dir("/var/www")); +/// let root = "/home/user"; +/// let rel = "documents"; +/// println!("{:#?}", util::absolute_dir(root, rel)); /// ``` -pub fn resolve_absolute_dir>(path: P) -> io::Result { - let path = path.as_ref(); - - let candidate = if path.is_absolute() { - path.to_path_buf() - } else { - // Directorio base CARGO_MANIFEST_DIR si está disponible; o current_dir() en su defecto. - env::var_os("CARGO_MANIFEST_DIR") - .map(PathBuf::from) - .or_else(|| env::current_dir().ok()) - .unwrap_or_else(|| PathBuf::from(".")) - .join(path) - }; +pub fn absolute_dir(root_path: P, relative_path: Q) -> io::Result +where + P: AsRef, + Q: AsRef, +{ + // Une ambas rutas: + // - Si `relative_path` es absoluta, el `join` la devuelve tal cual, descartando `root_path`. + // - Si el resultado es aún relativo, lo será respecto al directorio actual. + let candidate = root_path.as_ref().join(relative_path.as_ref()); // Resuelve `.`/`..`, enlaces simbólicos y obtiene la ruta absoluta en un único paso. let absolute_dir = candidate.canonicalize()?; @@ -56,16 +47,6 @@ pub fn resolve_absolute_dir>(path: P) -> io::Result { } } -/// Devuelve la ruta absoluta a un directorio existente. -#[deprecated(since = "0.3.0", note = "Use [`resolve_absolute_dir`] instead")] -pub fn absolute_dir(root_path: P, relative_path: Q) -> io::Result -where - P: AsRef, - Q: AsRef, -{ - resolve_absolute_dir(root_path.as_ref().join(relative_path.as_ref())) -} - // MACROS ÚTILES *********************************************************************************** #[doc(hidden)] diff --git a/tests/util.rs b/tests/util.rs index 70699a7..6e0896f 100644 --- a/tests/util.rs +++ b/tests/util.rs @@ -1,6 +1,6 @@ use pagetop::prelude::*; -use std::{env, fs, io}; +use std::{fs, io}; use tempfile::TempDir; #[cfg(unix)] @@ -13,36 +13,15 @@ mod unix { // /tmp//sub let td = TempDir::new()?; - let sub = td.path().join("sub"); + let root = td.path(); + let sub = root.join("sub"); fs::create_dir(&sub)?; - let abs = util::resolve_absolute_dir(&sub)?; + let abs = util::absolute_dir(root, "sub")?; assert_eq!(abs, std::fs::canonicalize(&sub)?); Ok(()) } - #[pagetop::test] - async fn ok_relative_dir_with_manifest() -> io::Result<()> { - let _app = service::test::init_service(Application::new().test()).await; - - let td = TempDir::new()?; - let sub = td.path().join("sub"); - fs::create_dir(&sub)?; - - // Fija CARGO_MANIFEST_DIR para que "sub" se resuelva contra td.path() - let prev_manifest_dir = env::var_os("CARGO_MANIFEST_DIR"); - env::set_var("CARGO_MANIFEST_DIR", td.path()); - let res = util::resolve_absolute_dir("sub"); - // Restaura entorno. - match prev_manifest_dir { - Some(v) => env::set_var("CARGO_MANIFEST_DIR", v), - None => env::remove_var("CARGO_MANIFEST_DIR"), - } - - assert_eq!(res?, std::fs::canonicalize(&sub)?); - Ok(()) - } - #[pagetop::test] async fn error_not_a_directory() -> io::Result<()> { let _app = service::test::init_service(Application::new().test()).await; @@ -51,7 +30,7 @@ mod unix { let file = td.path().join("foo.txt"); fs::write(&file, b"data")?; - let err = util::resolve_absolute_dir(&file).unwrap_err(); + let err = util::absolute_dir(td.path(), "foo.txt").unwrap_err(); assert_eq!(err.kind(), io::ErrorKind::InvalidInput); Ok(()) } @@ -67,36 +46,15 @@ mod windows { // C:\Users\...\Temp\... let td = TempDir::new()?; - let sub = td.path().join("sub"); + let root = td.path(); + let sub = root.join("sub"); fs::create_dir(&sub)?; - let abs = util::resolve_absolute_dir(&sub)?; + let abs = util::absolute_dir(root, sub.as_path())?; assert_eq!(abs, std::fs::canonicalize(&sub)?); Ok(()) } - #[pagetop::test] - async fn ok_relative_dir_with_manifest() -> io::Result<()> { - let _app = service::test::init_service(Application::new().test()).await; - - let td = TempDir::new()?; - let sub = td.path().join("sub"); - fs::create_dir(&sub)?; - - // Fija CARGO_MANIFEST_DIR para que "sub" se resuelva contra td.path() - let prev_manifest_dir = env::var_os("CARGO_MANIFEST_DIR"); - env::set_var("CARGO_MANIFEST_DIR", td.path()); - let res = util::resolve_absolute_dir("sub"); - // Restaura entorno. - match prev_manifest_dir { - Some(v) => env::set_var("CARGO_MANIFEST_DIR", v), - None => env::remove_var("CARGO_MANIFEST_DIR"), - } - - assert_eq!(res?, std::fs::canonicalize(&sub)?); - Ok(()) - } - #[pagetop::test] async fn error_not_a_directory() -> io::Result<()> { let _app = service::test::init_service(Application::new().test()).await; @@ -105,7 +63,7 @@ mod windows { let file = td.path().join("foo.txt"); fs::write(&file, b"data")?; - let err = util::resolve_absolute_dir(&file).unwrap_err(); + let err = util::absolute_dir(td.path(), "foo.txt").unwrap_err(); assert_eq!(err.kind(), io::ErrorKind::InvalidInput); Ok(()) }