dora_core/
lib.rs

1use eyre::{Context, bail, eyre};
2use std::{
3    env::consts::{DLL_PREFIX, DLL_SUFFIX},
4    ffi::OsStr,
5    path::Path,
6};
7
8pub use dora_message::{config, uhlc};
9
10#[cfg(feature = "build")]
11pub mod build;
12pub mod descriptor;
13pub mod metadata;
14pub mod topics;
15
16pub fn adjust_shared_library_path(path: &Path) -> Result<std::path::PathBuf, eyre::ErrReport> {
17    let file_name = path
18        .file_name()
19        .ok_or_else(|| eyre!("shared library path has no file name"))?
20        .to_str()
21        .ok_or_else(|| eyre!("shared library file name is not valid UTF8"))?;
22    if file_name.starts_with("lib") {
23        bail!("Shared library file name must not start with `lib`, prefix is added automatically");
24    }
25    if path.extension().is_some() {
26        bail!("Shared library file name must have no extension, it is added automatically");
27    }
28
29    let library_filename = format!("{DLL_PREFIX}{file_name}{DLL_SUFFIX}");
30
31    let path = path.with_file_name(library_filename);
32    Ok(path)
33}
34
35// Search for python binary.
36// Match `python` for windows and macos and `python3` for other platforms.
37pub fn get_python_path() -> Result<std::path::PathBuf, eyre::ErrReport> {
38    let python = if cfg!(windows) || cfg!(target_os = "macos") {
39        which::which("python")
40            .context("failed to find `python` or `python3`. Make sure that python is available.")?
41    } else {
42        which::which("python3")
43            .context("failed to find `python` or `python3`. Make sure that python is available.")?
44    };
45
46    Ok(python)
47}
48
49// Search for pip binary.
50// First search for `pip3` as for ubuntu <20, `pip` can resolves to `python2,7 -m pip`
51// Then search for `pip`, this will resolve for windows to python3 -m pip.
52pub fn get_pip_path() -> Result<std::path::PathBuf, eyre::ErrReport> {
53    let python = match which::which("pip3") {
54        Ok(python) => python,
55        Err(_) => which::which("pip")
56            .context("failed to find `pip3` or `pip`. Make sure that python is available.")?,
57    };
58    Ok(python)
59}
60
61// Search for uv binary.
62pub fn get_uv_path() -> Result<std::path::PathBuf, eyre::ErrReport> {
63    which::which("uv")
64        .context("failed to find `uv`. Make sure to install it using: https://docs.astral.sh/uv/getting-started/installation/")
65}
66
67// Helper function to run a program
68pub async fn run<S>(program: S, args: &[&str], pwd: Option<&Path>) -> eyre::Result<()>
69where
70    S: AsRef<OsStr>,
71{
72    let mut run = tokio::process::Command::new(program);
73    run.args(args);
74
75    if let Some(pwd) = pwd {
76        run.current_dir(pwd);
77    }
78    if !run.status().await?.success() {
79        eyre::bail!("failed to run {args:?}");
80    };
81    Ok(())
82}