- implement shape in Rust
- implement more readers - fix downloading of bioformats jar - (mostly) compatible with python version
This commit is contained in:
@@ -1,131 +1,177 @@
|
||||
#[cfg(not(feature = "python"))]
|
||||
use j4rs::{JvmBuilder, MavenArtifact, MavenArtifactRepo, MavenSettings, errors::J4RsError};
|
||||
#[cfg(not(feature = "python"))]
|
||||
use retry::{delay, delay::Exponential, retry};
|
||||
use std::error::Error;
|
||||
#[cfg(not(feature = "python"))]
|
||||
use std::fmt::Display;
|
||||
#[cfg(not(feature = "python"))]
|
||||
use std::fmt::Formatter;
|
||||
#[cfg(not(feature = "python"))]
|
||||
use std::path::PathBuf;
|
||||
#[cfg(not(feature = "python"))]
|
||||
use std::{env, fs};
|
||||
#[cfg(feature = "bioformats_java")]
|
||||
const BIOFORMATS_VERSION: &str = "8.5.0";
|
||||
|
||||
#[cfg(feature = "python")]
|
||||
use j4rs::Jvm;
|
||||
#[cfg(feature = "bioformats_java")]
|
||||
mod bioformats {
|
||||
use std::error::Error;
|
||||
use std::fmt::{Display, Formatter};
|
||||
|
||||
#[cfg(feature = "movie")]
|
||||
use ffmpeg_sidecar::download::auto_download;
|
||||
#[derive(Clone, Debug)]
|
||||
pub(crate) enum BuildError {
|
||||
J4rsVersionNotFound,
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "python"))]
|
||||
#[derive(Clone, Debug)]
|
||||
enum BuildError {
|
||||
BioFormatsNotDownloaded,
|
||||
}
|
||||
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"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "python"))]
|
||||
impl Display for BuildError {
|
||||
fn fmt(&self, fmt: &mut Formatter) -> Result<(), std::fmt::Error> {
|
||||
write!(fmt, "Bioformats package not downloaded")
|
||||
impl Error for BuildError {}
|
||||
|
||||
fn get_j4rs_version() -> Result<String, Box<dyn Error>> {
|
||||
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<dyn Error>> {
|
||||
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(not(feature = "python"))]
|
||||
impl Error for BuildError {}
|
||||
#[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};
|
||||
|
||||
fn main() -> Result<(), Box<dyn Error>> {
|
||||
#[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<dyn Error>> {
|
||||
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<std::path::PathBuf, J4RsError> {
|
||||
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<dyn std::error::Error>> {
|
||||
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<dyn std::error::Error>> {
|
||||
println!("cargo::rerun-if-changed=build.rs");
|
||||
|
||||
if std::env::var("DOCS_RS").is_err() {
|
||||
#[cfg(feature = "movie")]
|
||||
auto_download()?;
|
||||
ffmpeg_sidecar::download::auto_download()?;
|
||||
|
||||
#[cfg(not(feature = "python"))]
|
||||
{
|
||||
retry(
|
||||
Exponential::from_millis(1000).map(delay::jitter).take(4),
|
||||
deploy_java_artifacts,
|
||||
)?;
|
||||
let path = default_jassets_path()?;
|
||||
if !path.join("bioformats_package-8.3.0.jar").exists() {
|
||||
Err(BuildError::BioFormatsNotDownloaded)?;
|
||||
}
|
||||
}
|
||||
#[cfg(feature = "bioformats_java")]
|
||||
bioformats::build()?;
|
||||
|
||||
#[cfg(feature = "python")]
|
||||
{
|
||||
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)?;
|
||||
}
|
||||
#[cfg(all(not(feature = "python"), feature = "bioformats_java"))]
|
||||
no_python_bioformats::build()?;
|
||||
|
||||
Jvm::copy_j4rs_libs_under(py_src_path.to_str().unwrap())?;
|
||||
|
||||
// rename else maturin will ignore them
|
||||
for file in std::fs::read_dir(&py_deps_path)? {
|
||||
let f = file?.path().to_str().unwrap().to_string();
|
||||
if !f.ends_with("_") {
|
||||
std::fs::rename(&f, std::format!("{f}_"))?;
|
||||
}
|
||||
}
|
||||
|
||||
// remove so we don't include too much accidentally
|
||||
for file in std::fs::read_dir(&py_jassets_path)? {
|
||||
let f = file?.path();
|
||||
if !f.file_name().unwrap().to_str().unwrap().starts_with("j4rs") {
|
||||
std::fs::remove_file(&f)?;
|
||||
}
|
||||
}
|
||||
}
|
||||
#[cfg(all(feature = "python", feature = "bioformats_java"))]
|
||||
python_bioformats::build()?;
|
||||
}
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "python"))]
|
||||
fn default_jassets_path() -> Result<PathBuf, J4RsError> {
|
||||
let is_build_script = env::var("OUT_DIR").is_ok();
|
||||
|
||||
let mut start_path = if is_build_script {
|
||||
PathBuf::from(env::var("OUT_DIR")?)
|
||||
} else {
|
||||
env::current_exe()?
|
||||
};
|
||||
start_path = 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_owned(),
|
||||
))
|
||||
}
|
||||
|
||||
#[cfg(not(feature = "python"))]
|
||||
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.3.0"))?;
|
||||
|
||||
#[cfg(feature = "gpl-formats")]
|
||||
jvm.deploy_artifact(&MavenArtifact::from("ome:formats-gpl:8.3.0"))?;
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user