#[cfg(feature = "bioformats_java")] const BIOFORMATS_VERSION: &str = "8.5.0"; #[cfg(feature = "bioformats_java")] mod bioformats { use std::error::Error; use std::fmt::{Display, Formatter}; #[derive(Clone, Debug)] pub(crate) enum BuildError { J4rsVersionNotFound, } impl Display for BuildError { fn fmt(&self, fmt: &mut Formatter) -> Result<(), std::fmt::Error> { match self { Self::J4rsVersionNotFound => write!(fmt, "J4rsVersion not found in Cargo.lock"), } } } impl Error for BuildError {} fn get_j4rs_version() -> Result> { let manifest_dir = std::env::var("CARGO_MANIFEST_DIR").expect("CARGO_MANIFEST_DIR not set"); let lock_path = std::path::Path::new(&manifest_dir).join("Cargo.lock"); let lock_toml = std::fs::read_to_string(&lock_path)?; let value: toml::Value = toml::from_str(&lock_toml)?; if let Some(packages) = value.get("package").and_then(|v| v.as_array()) { for package in packages { if let (Some(name), Some(version)) = ( package.get("name").and_then(|v| v.as_str()), package.get("version"), ) && name == "j4rs" { return Ok(version .to_string() .strip_prefix("\"") .and_then(|v| v.strip_suffix("\"")) .ok_or(BuildError::J4rsVersionNotFound)? .to_string()); } } } Err(Box::new(BuildError::J4rsVersionNotFound {})) } pub(crate) fn build() -> Result<(), Box> { let j4rs_version = get_j4rs_version()?; let out_dir = std::env::var("OUT_DIR")?; let dest_path = std::path::Path::new(&out_dir).join("constants.rs"); let contents = format!( r#" /// Generated by build.rs pub(super) const J4RS_VERSION: &str = "{}"; pub(super) const BIOFORMATS_VERSION: &str = "{}"; "#, j4rs_version, crate::BIOFORMATS_VERSION, ); std::fs::write(&dest_path, contents)?; Ok(()) } } #[cfg(all(not(feature = "python"), feature = "bioformats_java"))] mod no_python_bioformats { use j4rs::errors::J4RsError; use j4rs::{JvmBuilder, MavenArtifact, MavenArtifactRepo, MavenSettings}; use retry::delay::Exponential; use retry::{delay, retry}; use std::error::Error; use std::fmt::{Display, Formatter}; #[derive(Clone, Debug)] pub(crate) enum BuildError { BioFormatsNotDownloaded, } impl Display for BuildError { fn fmt(&self, fmt: &mut Formatter) -> Result<(), std::fmt::Error> { write!(fmt, "Bioformats package not downloaded") } } impl Error for BuildError {} pub(crate) fn build() -> Result<(), Box> { retry( Exponential::from_millis(1000).map(delay::jitter).take(4), deploy_java_artifacts, )?; let path = default_jassets_path()?; if !path.join("bioformats_package-8.5.0.jar").exists() { Err(BuildError::BioFormatsNotDownloaded)?; } Ok(()) } fn default_jassets_path() -> Result { let is_build_script = std::env::var("OUT_DIR").is_ok(); let mut start_path = if is_build_script { std::path::PathBuf::from(std::env::var("OUT_DIR")?) } else { std::env::current_exe()? }; start_path = std::fs::canonicalize(start_path)?; while start_path.pop() { for entry in std::fs::read_dir(&start_path)? { let path = entry?.path(); if path.file_name().map(|x| x == "jassets").unwrap_or(false) { return Ok(path); } } } Err(J4RsError::GeneralError( "Can not find jassets directory".to_string(), )) } fn deploy_java_artifacts() -> Result<(), J4RsError> { let jvm = JvmBuilder::new() .skip_setting_native_lib() .with_maven_settings(MavenSettings::new(vec![MavenArtifactRepo::from( "openmicroscopy::https://artifacts.openmicroscopy.org/artifactory/ome.releases", )])) .build()?; jvm.deploy_artifact(&MavenArtifact::from("ome:bioformats_package:8.5.0"))?; #[cfg(feature = "gpl-formats")] jvm.deploy_artifact(&MavenArtifact::from("ome:formats-gpl:8.5.0"))?; Ok(()) } } #[cfg(all(feature = "python", feature = "bioformats_java"))] mod python_bioformats { pub(crate) fn build() -> Result<(), Box> { let py_src_path = std::env::current_dir()?.join("py").join("ndbioimage"); let py_jassets_path = py_src_path.join("jassets"); let py_deps_path = py_src_path.join("deps"); if py_jassets_path.exists() { std::fs::remove_dir_all(&py_jassets_path)?; } if py_deps_path.exists() { std::fs::remove_dir_all(&py_deps_path)?; } j4rs::Jvm::copy_j4rs_libs_under(py_src_path.to_str().unwrap())?; Ok(()) } } fn main() -> Result<(), Box> { println!("cargo::rerun-if-changed=build.rs"); if std::env::var("DOCS_RS").is_err() { #[cfg(feature = "movie")] ffmpeg_sidecar::download::auto_download()?; #[cfg(feature = "bioformats_java")] bioformats::build()?; #[cfg(all(not(feature = "python"), feature = "bioformats_java"))] no_python_bioformats::build()?; #[cfg(all(feature = "python", feature = "bioformats_java"))] python_bioformats::build()?; } Ok(()) }