diff options
author | Matthias Beyer <mail@beyermatthias.de> | 2020-11-05 19:23:39 +0100 |
---|---|---|
committer | Matthias Beyer <mail@beyermatthias.de> | 2020-11-05 19:42:59 +0100 |
commit | 09ca98cc77abbec3b511d79c0a966a1527e9b880 (patch) | |
tree | ce18b3f80b47ae322ed68ca0224585ba695b5c1e | |
parent | 80f89476c350f2c33abfdc75d5082fb41f4d68a2 (diff) |
Change MergedStore to take Release/StagingStore via Arc<>
Signed-off-by: Matthias Beyer <mail@beyermatthias.de>
-rw-r--r-- | src/filestore/merged.rs | 72 | ||||
-rw-r--r-- | src/filestore/release.rs | 4 | ||||
-rw-r--r-- | src/job/runnable.rs | 4 | ||||
-rw-r--r-- | src/job/set.rs | 2 |
4 files changed, 50 insertions, 32 deletions
diff --git a/src/filestore/merged.rs b/src/filestore/merged.rs index 9eb4305..04ffe0e 100644 --- a/src/filestore/merged.rs +++ b/src/filestore/merged.rs @@ -1,3 +1,9 @@ +use std::sync::Arc; +use std::sync::RwLock; + +use anyhow::anyhow; +use anyhow::Result; + use crate::filestore::Artifact; use crate::filestore::ReleaseStore; use crate::filestore::StagingStore; @@ -10,45 +16,61 @@ use crate::package::PackageVersionConstraint; /// The stores are not actually merged (on disk or in memory), but the querying mechanism works in /// a way where it _always_ preferes the staging store over the release store. /// -pub struct MergedStores<'a> { - release: &'a ReleaseStore, - staging: &'a StagingStore, +pub struct MergedStores { + release: Arc<RwLock<ReleaseStore>>, + staging: Arc<RwLock<StagingStore>>, } -impl<'a> MergedStores<'a> { - pub (in crate::filestore) fn new(release: &'a ReleaseStore, staging: &'a StagingStore) -> Self { +impl MergedStores { + pub fn new(release: Arc<RwLock<ReleaseStore>>, staging: Arc<RwLock<StagingStore>>) -> Self { MergedStores { release, staging } } - pub fn get_artifact_by_name(&self, name: &PackageName) -> Vec<&Artifact> { - let v = self.staging.0 - .values() - .filter(|a| a.name() == name) - .collect::<Vec<_>>(); + pub fn get_artifact_by_name(&self, name: &PackageName) -> Result<Vec<&Artifact>> { + let v = self.staging + .read() + .map_err(|_| anyhow!("Lock poisoned")) + .map(|s| { + s.0.values() + .filter(|a| a.name() == name) + .collect::<Vec<_>>() + })?; if v.is_empty() { - self.release.0 - .values() - .filter(|a| a.name() == name) - .collect() + self.release + .read() + .map_err(|_| anyhow!("Lock poisoned")) + .map(|r| { + r.0.values() + .filter(|a| a.name() == name) + .collect() + }) } else { - v + Ok(v) } } - pub fn get_artifact_by_name_and_version(&self, name: &PackageName, version: &PackageVersionConstraint) -> Vec<&Artifact> { - let v = self.staging.0 - .values() - .filter(|a| a.name() == name && version.matches(a.version())) - .collect::<Vec<_>>(); + pub fn get_artifact_by_name_and_version(&self, name: &PackageName, version: &PackageVersionConstraint) -> Result<Vec<&Artifact>> { + let v = self.staging + .read() + .map_err(|_| anyhow!("Lock poisoned")) + .map(|s| { + s.0.values() + .filter(|a| a.name() == name && version.matches(a.version())) + .collect::<Vec<_>>() + })?; if v.is_empty() { - self.release.0 - .values() - .filter(|a| a.name() == name && version.matches(a.version())) - .collect() + self.release + .read() + .map_err(|_| anyhow!("Lock poisoned")) + .map(|r| { + r.0.values() + .filter(|a| a.name() == name && version.matches(a.version())) + .collect() + }) } else { - v + Ok(v) } } diff --git a/src/filestore/release.rs b/src/filestore/release.rs index 407ceac..dcdb442 100644 --- a/src/filestore/release.rs +++ b/src/filestore/release.rs @@ -14,9 +14,5 @@ impl ReleaseStore { pub fn load(root: &Path, progress: ProgressBar) -> Result<Self> { FileStoreImpl::load(root, progress).map(ReleaseStore) } - - pub fn merged<'a>(&'a self, staging: &'a StagingStore) -> MergedStores<'a> { - MergedStores::new(self, staging) - } } diff --git a/src/job/runnable.rs b/src/job/runnable.rs index 0a2bcb2..1fc529a 100644 --- a/src/job/runnable.rs +++ b/src/job/runnable.rs @@ -35,7 +35,7 @@ pub struct RunnableJob { } impl RunnableJob { - pub fn build_from_job<'a>(job: Job, merged_stores: &'a MergedStores<'a>) -> Result<Self> { + pub fn build_from_job(job: Job, merged_stores: &MergedStores) -> Result<Self> { let script = ScriptBuilder::new(&job.script_shebang) .build(&job.package, &job.script_phases)?; @@ -45,7 +45,7 @@ impl RunnableJob { .into_iter() .map(|runtime_dep| { let (name, version) = runtime_dep.parse_as_name_and_version()?; - let mut a = merged_stores.get_artifact_by_name_and_version(&name, &version); + let mut a = merged_stores.get_artifact_by_name_and_version(&name, &version)?; if a.is_empty() { Err(anyhow!("Cannot find dependency: {:?} {:?}", name, version)) diff --git a/src/job/set.rs b/src/job/set.rs index a89c352..82f2b6c 100644 --- a/src/job/set.rs +++ b/src/job/set.rs @@ -23,7 +23,7 @@ impl JobSet { self.set.is_empty() } - pub fn into_runables<'a>(self, merged_stores: &'a MergedStores<'a>) -> impl Iterator<Item = Result<RunnableJob>> + 'a { + pub fn into_runables<'a>(self, merged_stores: &'a MergedStores) -> impl Iterator<Item = Result<RunnableJob>> + 'a { self.set.into_iter().map(move |j| RunnableJob::build_from_job(j, merged_stores)) } |