[pve-devel] [PATCH v7 pve-rs 1/1] add bindings for proxmox-apt
Fabian Ebner
f.ebner at proxmox.com
Wed Jun 23 15:39:01 CEST 2021
which contains includes logic for repository handling.
Signed-off-by: Fabian Ebner <f.ebner at proxmox.com>
---
Changes from v6:
* have repositories() return everything at once
* base on now existing pve-rs
* don't use raw_return
* add bindings for add/change
Cargo.toml | 2 +
Makefile | 6 +-
src/apt/mod.rs | 1 +
src/apt/repositories.rs | 128 ++++++++++++++++++++++++++++++++++++++++
src/lib.rs | 4 +-
5 files changed, 136 insertions(+), 5 deletions(-)
create mode 100644 src/apt/mod.rs
create mode 100644 src/apt/repositories.rs
diff --git a/Cargo.toml b/Cargo.toml
index 9c274ff..d39c1ad 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -19,4 +19,6 @@ crate-type = [ "cdylib" ]
anyhow = "1.0"
proxmox = { version = "0.11.5", default-features = false }
perlmod = { version = "0.5.1", features = [ "exporter" ] }
+proxmox-apt = "0.2.0"
proxmox-openid = "0.5.0"
+serde = "1.0"
diff --git a/Makefile b/Makefile
index e340623..9701c8e 100644
--- a/Makefile
+++ b/Makefile
@@ -14,10 +14,12 @@ DEBS=$(MAIN_DEB) $(DBGSYM_DEB)
DESTDIR=
-PM_DIRS :=
+PM_DIRS := \
+ PVE/RS/APT
PM_FILES := \
- PVE/RS/OpenId.pm
+ PVE/RS/OpenId.pm \
+ PVE/RS/APT/Repositories.pm
ifeq ($(BUILD_MODE), release)
CARGO_BUILD_ARGS += --release
diff --git a/src/apt/mod.rs b/src/apt/mod.rs
new file mode 100644
index 0000000..574c1a7
--- /dev/null
+++ b/src/apt/mod.rs
@@ -0,0 +1 @@
+mod repositories;
diff --git a/src/apt/repositories.rs b/src/apt/repositories.rs
new file mode 100644
index 0000000..3a421f0
--- /dev/null
+++ b/src/apt/repositories.rs
@@ -0,0 +1,128 @@
+#[perlmod::package(name = "PVE::RS::APT::Repositories", lib = "pve_rs")]
+mod export {
+ use std::convert::TryInto;
+
+ use anyhow::{bail, Error};
+ use serde::{Deserialize, Serialize};
+
+ use proxmox_apt::repositories::{
+ APTRepositoryFile, APTRepositoryFileError, APTRepositoryInfo, APTStandardRepository,
+ };
+
+ #[derive(Deserialize, Serialize)]
+ #[serde(rename_all = "kebab-case")]
+ /// Result for the repositories() function
+ pub struct RepositoriesResult {
+ /// Successfully parsed files.
+ pub files: Vec<APTRepositoryFile>,
+
+ /// Errors for files that could not be parsed or read.
+ pub errors: Vec<APTRepositoryFileError>,
+
+ /// Common digest for successfully parsed files.
+ pub digest: String,
+
+ /// Additional information/warnings about repositories.
+ pub infos: Vec<APTRepositoryInfo>,
+
+ /// Standard repositories and their configuration status.
+ pub standard_repos: Vec<APTStandardRepository>,
+ }
+
+ #[derive(Deserialize, Serialize)]
+ #[serde(rename_all = "kebab-case")]
+ /// For changing an existing repository.
+ pub struct ChangeProperties {
+ /// Whether the repository should be enabled or not.
+ pub enabled: Option<bool>,
+ }
+
+ /// Get information about configured and standard repositories.
+ #[export]
+ pub fn repositories() -> Result<RepositoriesResult, Error> {
+ let (files, errors, digest) = proxmox_apt::repositories::repositories()?;
+ let digest = proxmox::tools::digest_to_hex(&digest);
+
+ let infos = proxmox_apt::repositories::check_repositories(&files)?;
+ let standard_repos = proxmox_apt::repositories::standard_repositories("pve", &files);
+
+ Ok(RepositoriesResult {
+ files,
+ errors,
+ digest,
+ infos,
+ standard_repos,
+ })
+ }
+
+ /// Add the repository identified by the `handle`.
+ ///
+ /// The `digest` parameter asserts that the configuration has not been modified.
+ #[export]
+ pub fn add_repository(handle: &str, digest: Option<&str>) -> Result<(), Error> {
+ let (mut files, _errors, current_digest) = proxmox_apt::repositories::repositories()?;
+
+ if let Some(digest) = digest {
+ let expected_digest = proxmox::tools::hex_to_digest(digest)?;
+ if expected_digest != current_digest {
+ bail!("detected modified configuration - file changed by other user? Try again.");
+ }
+ }
+
+ let (repo, path) =
+ proxmox_apt::repositories::get_standard_repository(handle.try_into()?, "pve")?;
+
+ if let Some(file) = files.iter_mut().find(|file| file.path == path) {
+ file.repositories.push(repo);
+
+ file.write()?;
+ } else {
+ let mut file = match APTRepositoryFile::new(&path)? {
+ Some(file) => file,
+ None => bail!("invalid path - {}", path),
+ };
+
+ file.repositories.push(repo);
+
+ file.write()?;
+ }
+
+ Ok(())
+ }
+
+ /// Change the properties of the specified repository.
+ ///
+ /// The `digest` parameter asserts that the configuration has not been modified.
+ #[export]
+ pub fn change_repository(
+ path: &str,
+ index: usize,
+ options: ChangeProperties,
+ digest: Option<&str>,
+ ) -> Result<(), Error> {
+ let (mut files, _errors, current_digest) = proxmox_apt::repositories::repositories()?;
+
+ if let Some(digest) = digest {
+ let expected_digest = proxmox::tools::hex_to_digest(digest)?;
+ if expected_digest != current_digest {
+ bail!("detected modified configuration - file changed by other user? Try again.");
+ }
+ }
+
+ if let Some(file) = files.iter_mut().find(|file| file.path == path) {
+ if let Some(repo) = file.repositories.get_mut(index) {
+ if let Some(enabled) = options.enabled {
+ repo.set_enabled(enabled);
+ }
+
+ file.write()?;
+ } else {
+ bail!("invalid index - {}", index);
+ }
+ } else {
+ bail!("invalid path - {}", path);
+ }
+
+ Ok(())
+ }
+}
diff --git a/src/lib.rs b/src/lib.rs
index ec61052..cad331d 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -1,4 +1,2 @@
-
-// TODO: add submodule here
-//pub mod apt;
+pub mod apt;
pub mod openid;
--
2.30.2
More information about the pve-devel
mailing list