mezzaluna_loaded_features/feature/mod.rs
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102
use std::path::{Path, PathBuf};
#[cfg(feature = "disk")]
use same_file::Handle;
#[cfg(feature = "disk")]
mod disk;
mod memory;
#[derive(Debug, Hash, PartialEq, Eq)]
enum FeatureType {
#[cfg(feature = "disk")]
Disk(disk::Feature),
Memory(memory::Feature),
}
impl FeatureType {
#[must_use]
#[cfg(feature = "disk")]
pub fn with_handle_and_path(handle: Handle, path: PathBuf) -> Self {
let inner = disk::Feature::with_handle_and_path(handle, path);
Self::Disk(inner)
}
#[must_use]
pub fn with_in_memory_path(path: PathBuf) -> Self {
let inner = memory::Feature::with_path(path);
Self::Memory(inner)
}
#[must_use]
pub fn path(&self) -> &Path {
match self {
#[cfg(feature = "disk")]
Self::Disk(inner) => inner.path(),
Self::Memory(inner) => inner.path(),
}
}
}
/// A Ruby source ("feature") that has been loaded into an interpreter.
///
/// Features can either be loaded from disk or from memory.
///
/// Features are identified by the (potentially relative) path used when loading
/// the file for the first time. Features loaded from disk are deduplicated
/// by their real position on the underlying file system (i.e. their device and
/// inode).
#[derive(Debug, Hash, PartialEq, Eq)]
pub struct Feature {
inner: FeatureType,
}
impl Feature {
/// Create a new feature from a file handle and path.
#[must_use]
#[cfg(feature = "disk")]
#[cfg_attr(docsrs, doc(cfg(feature = "disk")))]
pub fn with_handle_and_path(handle: Handle, path: PathBuf) -> Self {
let inner = FeatureType::with_handle_and_path(handle, path);
Self { inner }
}
/// Create a new feature from a virtual in-memory path.
///
/// # Examples
///
/// ```
/// use std::path::Path;
/// use mezzaluna_loaded_features::Feature;
///
/// let feature = Feature::with_in_memory_path("/src/_lib/test.rb".into());
/// assert_eq!(feature.path(), Path::new("/src/_lib/test.rb"));
/// ```
#[must_use]
pub fn with_in_memory_path(path: PathBuf) -> Self {
let inner = FeatureType::with_in_memory_path(path);
Self { inner }
}
/// Get the path associated with this feature.
///
/// The path returned by this method is not guaranteed to be the same as
/// the path returned by [`LoadedFeatures::features`] since features may
/// be deduplicated by their physical location in the underlying loaders.
///
/// # Examples
///
/// ```
/// use std::path::Path;
/// use mezzaluna_loaded_features::Feature;
///
/// let feature = Feature::with_in_memory_path("/src/_lib/test.rb".into());
/// assert_eq!(feature.path(), Path::new("/src/_lib/test.rb"));
/// ```
///
/// [`LoadedFeatures::features`]: crate::LoadedFeatures::features
#[must_use]
pub fn path(&self) -> &Path {
self.inner.path()
}
}