From 2c9a6e460273bcafa783b774f9dcff57d93e0ed3 Mon Sep 17 00:00:00 2001 From: "Dr. Matthias Ratajczak" Date: Tue, 31 Jan 2023 16:42:16 +0100 Subject: [PATCH] even more review stuff --- src/backend/actual/pacman.rs | 2 + src/backend/actual/rust.rs | 6 +++ src/backend/backend_trait.rs | 81 +++++++++++++++++++++++++++++++++++- src/backend/macros.rs | 4 ++ src/grouping/group.rs | 11 ++++- src/review.rs | 14 ++++++- 6 files changed, 114 insertions(+), 4 deletions(-) diff --git a/src/backend/actual/pacman.rs b/src/backend/actual/pacman.rs index 7707e22..4bcb465 100644 --- a/src/backend/actual/pacman.rs +++ b/src/backend/actual/pacman.rs @@ -17,8 +17,10 @@ pub(crate) struct Pacman { const BINARY: Text = "paru"; const SECTION: Text = "pacman"; + const SWITCHES_INFO: Switches = &["-Qi"]; const SWITCHES_INSTALL: Switches = &["-S"]; +const SWITCHES_MAKE_DEPENDENCY: Switches = &["-D", "--asdeps"]; const SWITCHES_REMOVE: Switches = &["-Rsn"]; impl Backend for Pacman { diff --git a/src/backend/actual/rust.rs b/src/backend/actual/rust.rs index fe9c517..0bacb23 100644 --- a/src/backend/actual/rust.rs +++ b/src/backend/actual/rust.rs @@ -1,6 +1,7 @@ use std::collections::HashSet; use std::fs::read_to_string; use std::path::PathBuf; +use std::process::ExitStatus; use anyhow::{Context, Result}; use serde_json::Value; @@ -17,6 +18,7 @@ const BINARY: Text = "cargo"; const SECTION: Text = "rust"; const SWITCHES_INSTALL: Switches = &["install"]; const SWITCHES_INFO: Switches = &["search", "--limit", "1"]; +const SWITCHES_MAKE_DEPENDENCY: Switches = &[]; const SWITCHES_REMOVE: Switches = &["uninstall"]; impl Backend for Rust { @@ -34,6 +36,10 @@ impl Backend for Rust { self.get_all_installed_packages() .context("getting all installed packages") } + + fn make_dependency(&self, packages: &[Package]) -> Result { + unreachable!() + } } fn extract_packages(json: Value) -> Result> { diff --git a/src/backend/backend_trait.rs b/src/backend/backend_trait.rs index e8b2bc8..339ad34 100644 --- a/src/backend/backend_trait.rs +++ b/src/backend/backend_trait.rs @@ -1,5 +1,9 @@ +use std::collections::HashMap; use std::fmt::Debug; +use std::fs::{read_to_string, File}; +use std::io::Write; use std::process::Command; +use std::rc::Rc; use std::{collections::HashSet, process::ExitStatus}; use anyhow::{Context, Result}; @@ -12,18 +16,83 @@ pub(in crate::backend) type Text = &'static str; pub(crate) trait Backend: Debug { fn get_binary(&self) -> Text; fn get_section(&self) -> Text; + fn get_switches_info(&self) -> Switches; fn get_switches_install(&self) -> Switches; fn get_switches_remove(&self) -> Switches; - fn get_managed_packages(&self) -> &HashSet; + fn get_switches_make_dependency(&self) -> Switches; + fn load(&mut self, groups: &HashSet); + fn get_managed_packages(&self) -> &HashSet; + /// Get all packages that are installed in the system. fn get_all_installed_packages(&self) -> Result>; /// Get all packages that were installed in the system explicitly. fn get_explicitly_installed_packages(&self) -> Result>; + fn assign_group(&self, to_assign: Vec<(Package, Rc)>) { + let mut group_package_map = HashMap::new(); + + for (p, group) in to_assign { + if !group_package_map.contains_key(&group) { + group_package_map.insert(group.clone(), vec![]); + } + + let inner = group_package_map.get_mut(&group).unwrap(); + inner.push(p); + } + + for vecs in group_package_map.values_mut() { + vecs.sort(); + } + + for (group, packages) in group_package_map { + let group_file_content = read_to_string(&group.path).unwrap(); + let old_length = dbg!(group_file_content.len()); + let mut must_write_section_header = false; + + let mut lines = group_file_content.lines(); + + lines.find(|line| line.contains(&format!("[{}]", self.get_section()))); + lines.next().unwrap(); + + let start_of_section = if let Some(start_of_section) = group_file_content.find() { + start_of_section + } else { + must_write_section_header = true; + old_length + }; + + dbg!(&start_of_section); + + let mut new_file_content = group_file_content + .get(..start_of_section) + .unwrap() + .to_owned(); + + dbg!(&new_file_content); + + todo!(); + + if dbg!(must_write_section_header) { + new_file_content.push_str(&format!("\n[{}]", self.get_section())); + } + for package in packages { + new_file_content.push_str(&format!("\n{package}")); + } + new_file_content.push('\n'); + + if old_length > start_of_section { + new_file_content.push_str(group_file_content.get(old_length..).unwrap()); + } + + let mut file = File::create(&group.path).unwrap(); + write!(file, "{new_file_content}").unwrap(); + } + } + /// Install the specified packages. fn install_packages(&self, packages: &[Package]) -> Result { let mut cmd = Command::new(self.get_binary()); @@ -35,6 +104,16 @@ pub(crate) trait Backend: Debug { .with_context(|| format!("running command {cmd:?}")) } + fn make_dependency(&self, packages: &[Package]) -> Result { + let mut cmd = Command::new(self.get_binary()); + cmd.args(self.get_switches_make_dependency()); + for p in packages { + cmd.arg(format!("{p}")); + } + cmd.status() + .with_context(|| format!("running command [{cmd:?}]")) + } + /// Remove the specified packages. fn remove_packages(&self, packages: &[Package]) -> Result { let mut cmd = Command::new(self.get_binary()); diff --git a/src/backend/macros.rs b/src/backend/macros.rs index ef8ea68..5ca5715 100644 --- a/src/backend/macros.rs +++ b/src/backend/macros.rs @@ -21,6 +21,10 @@ macro_rules! impl_backend_constants { SWITCHES_REMOVE } + fn get_switches_make_dependency(&self) -> Switches { + SWITCHES_MAKE_DEPENDENCY + } + fn get_managed_packages(&self) -> &HashSet { &self.packages } diff --git a/src/grouping/group.rs b/src/grouping/group.rs index c0c8a2a..757793c 100644 --- a/src/grouping/group.rs +++ b/src/grouping/group.rs @@ -1,7 +1,7 @@ use std::fmt::Write; use std::fs::read_to_string; use std::hash::Hash; -use std::path::Path; +use std::path::{Path, PathBuf}; use std::{collections::HashSet, fmt::Display}; use anyhow::{Context, Result}; @@ -14,6 +14,7 @@ use crate::Config; pub struct Group { pub(crate) name: String, pub(crate) sections: HashSet
, + pub(crate) path: PathBuf, } impl Group { @@ -101,7 +102,13 @@ impl Group { println!("WARNING: no sections found in group '{name}'"); } - Ok(Self { name, sections }) + let path = path.into(); + + Ok(Self { + name, + sections, + path, + }) } } diff --git a/src/review.rs b/src/review.rs index 590c69c..cbc2aaf 100644 --- a/src/review.rs +++ b/src/review.rs @@ -197,7 +197,19 @@ impl Strategy { } fn execute(self) -> Result<()> { - todo!() + if !self.delete.is_empty() { + self.backend.remove_packages(&self.delete)?; + } + + if !self.as_dependency.is_empty() { + self.backend.make_dependency(&self.as_dependency)?; + } + + if !self.assign_group.is_empty() { + self.backend.assign_group(self.assign_group); + } + + Ok(()) } fn show(&self) {