summaryrefslogtreecommitdiffstats
path: root/pkgs/by-name/ro/rollup/src
diff options
context:
space:
mode:
authorBenedikt Peetz <benedikt.peetz@b-peetz.de>2026-11-04 17:56:37 +0100
committerBenedikt Peetz <benedikt.peetz@b-peetz.de>2026-11-05 22:47:43 +0100
commit36e836abf8ead21c88154a7e962a8d397d74b78f (patch)
treef8336765778eb22e847e11bfb9d7c92e334810cd /pkgs/by-name/ro/rollup/src
parentflake.nix: Don't perform source mapping via sources and raw_sources (diff)
downloadnixos-config-36e836abf8ead21c88154a7e962a8d397d74b78f.zip
pkgs/rollup: Init
Diffstat (limited to 'pkgs/by-name/ro/rollup/src')
-rw-r--r--pkgs/by-name/ro/rollup/src/main.rs106
1 files changed, 106 insertions, 0 deletions
diff --git a/pkgs/by-name/ro/rollup/src/main.rs b/pkgs/by-name/ro/rollup/src/main.rs
new file mode 100644
index 00000000..8285e702
--- /dev/null
+++ b/pkgs/by-name/ro/rollup/src/main.rs
@@ -0,0 +1,106 @@
+use core::fmt;
+use std::{path::PathBuf, process::Command};
+
+use anyhow::{Context, Result};
+use clap::Parser;
+
+#[derive(Parser)]
+struct Cli {
+ /// The file to pull the patch to rollup from.
+ patch_file: PathBuf,
+}
+
+struct Diff {
+ files: Vec<FileDiff>,
+}
+
+struct FileDiff {
+ from: PathBuf,
+ to: PathBuf,
+ diff: String,
+ index: String,
+}
+
+impl fmt::Display for FileDiff {
+ fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
+ writeln!(
+ f,
+ "diff --git a/{} b/{}",
+ self.from.display(),
+ self.to.display()
+ )?;
+ writeln!(f, "--- a/{}", self.from.display())?;
+ writeln!(f, "+++ b/{}", self.to.display())?;
+ writeln!(f, "index {}", self.index)?;
+ writeln!(f, "{}", self.diff)?;
+
+ Ok(())
+ }
+}
+
+macro_rules! take {
+ ($line:expr, $prefix:literal) => {
+ $line.strip_prefix($prefix).unwrap().trim()
+ };
+}
+
+fn main() -> Result<()> {
+ let args = Cli::parse();
+
+ let data = Command::new("filterdiff")
+ .arg(&args.patch_file)
+ .output()
+ .context("Failed to run `filterdiff` for patch analysis")?;
+
+ let stdout = String::from_utf8(data.stdout).unwrap();
+
+ let mut diff = Diff { files: vec![] };
+ let mut file_diff_from = None;
+ let mut file_diff_to = None;
+ let mut file_diff_diff: Option<String> = None;
+ let mut file_diff_index: Option<String> = None;
+ for (idx, line) in stdout.lines().enumerate() {
+ eprintln!("{}", line);
+
+ if line.starts_with("---") {
+ file_diff_from = Some(PathBuf::from(take!(line, "--- a/")));
+ } else if line.starts_with("+++") {
+ file_diff_to = Some(PathBuf::from(take!(line, "+++ b/")));
+ } else if line.starts_with("index") {
+ file_diff_index = Some(take!(line, "index").to_owned());
+ } else if line.starts_with("diff --git") {
+ if idx != 0 {
+ diff.files.push(FileDiff {
+ from: file_diff_from.take().unwrap(),
+ to: file_diff_to.take().unwrap(),
+ diff: file_diff_diff.take().unwrap(),
+ index: file_diff_index.take().unwrap(),
+ });
+ }
+ } else {
+ match file_diff_diff.as_mut() {
+ Some(str) => {
+ str.push_str(line);
+ str.push('\n');
+ }
+ None => {
+ let mut base = line.to_owned();
+ base.push('\n');
+ file_diff_diff = Some(base);
+ }
+ }
+ }
+ }
+ diff.files.push(FileDiff {
+ from: file_diff_from.unwrap(),
+ to: file_diff_to.unwrap(),
+ diff: file_diff_diff.unwrap(),
+ index: file_diff_index.unwrap(),
+ });
+
+ for file in diff.files {
+ eprintln!("{}", file)
+ }
+
+ Ok(())
+}