Skip to content

Commit

Permalink
Zvv/changelog internalize path (#669)
Browse files Browse the repository at this point in the history
Is there a good way to point a PR at another PR for diff?

I only want to send commit 80b4d5a for
review, but after the other commits are merged.

---------

Co-authored-by: Julien Cretin <[email protected]>
  • Loading branch information
exzachlyvv and ia0 authored Nov 7, 2024
1 parent ba8f253 commit 5364dde
Showing 1 changed file with 55 additions and 38 deletions.
93 changes: 55 additions & 38 deletions crates/cli-tools/src/changelog.rs
Original file line number Diff line number Diff line change
Expand Up @@ -49,17 +49,23 @@ impl Display for Severity {

#[derive(Debug, Default, PartialEq, Eq)]
struct Changelog {
crate_path: String,
releases: Vec<Release>,
skip_counter: u32,
}

impl Changelog {
async fn read_file(path: &str) -> Result<Changelog> {
Self::parse(&String::from_utf8(fs::read(path).await?)?)
fn changelog_path(&self) -> String {
format!("{}/CHANGELOG.md", self.crate_path)
}

async fn write_file(&self, path: &str) -> Result<()> {
fs::write(path, self.to_string().as_bytes()).await
async fn read(path: &str) -> Result<Changelog> {
let changelog_path = format!("{path}/CHANGELOG.md");
Self::parse(path, &String::from_utf8(fs::read(changelog_path).await?)?)
}

async fn write(&self) -> Result<()> {
fs::write(self.changelog_path(), self.to_string().as_bytes()).await
}

fn push_description(&mut self, severity: Severity, content: &str) -> Result<()> {
Expand Down Expand Up @@ -91,7 +97,7 @@ impl Changelog {
}

/// Parses and validates a changelog.
fn parse(input: &str) -> Result<Changelog> {
fn parse(crate_path: impl Into<String>, input: &str) -> Result<Changelog> {
let mut releases: Vec<Release> = Vec::new();
let mut parser = Parser::new(input.lines());
parser.read_exact("# Changelog")?;
Expand Down Expand Up @@ -166,12 +172,13 @@ impl Changelog {
.parse()
.with_context(|| anyhow!("Invalid skip counter {parser}"))?;
parser.done()?;
let result = Changelog { releases, skip_counter };
let result = Changelog { crate_path: crate_path.into(), releases, skip_counter };
assert_eq!(format!("{result}"), input);
Ok(result)
}

async fn validate_cargo_toml(&self, path: &str) -> Result<()> {
async fn validate_cargo_toml(&self) -> Result<()> {
let path = &self.crate_path;
let metadata = metadata(path).await?;
ensure!(
self.releases.first().unwrap().version == metadata.packages[0].version,
Expand All @@ -180,19 +187,19 @@ impl Changelog {
Ok(())
}

async fn sync_cargo_toml(&self, path: &str) -> Result<()> {
async fn sync_cargo_toml(&self) -> Result<()> {
let expected_version = &self.releases.first().unwrap().version;

let mut sed = Command::new("sed");
sed.arg("-i");
sed.arg(format!("s#^version = .*#version = \"{expected_version}\"#"));
sed.arg("Cargo.toml");
cmd::execute(sed.current_dir(path)).await?;
cmd::execute(sed.current_dir(&self.crate_path)).await?;

Ok(())
}

async fn sync_dependencies(&self, _path: &str) -> Result<()> {
async fn sync_dependencies(&self) -> Result<()> {
// TODO

Ok(())
Expand All @@ -201,7 +208,7 @@ impl Changelog {

impl Display for Changelog {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
let Changelog { releases, skip_counter } = self;
let Changelog { releases, skip_counter, .. } = self;
writeln!(f, "# Changelog\n")?;
for release in releases {
write!(f, "{release}")?;
Expand Down Expand Up @@ -316,23 +323,19 @@ pub async fn execute_ci() -> Result<()> {
let paths = cmd::output(Command::new("git").args(["ls-files", "*/CHANGELOG.md"])).await?;
for path in paths.stdout.lines() {
let path = path?;
let changelog = Changelog::read_file(&path).await?;
changelog.validate_cargo_toml(path.strip_suffix("/CHANGELOG.md").unwrap()).await?;
let changelog = Changelog::read(path.strip_suffix("/CHANGELOG.md").unwrap()).await?;
changelog.validate_cargo_toml().await?;
}
Ok(())
}

/// Updates a changelog file and changelog files of dependencies.
pub async fn execute_change(path: &str, severity: Severity, description: &str) -> Result<()> {
let changelog_file_path = format!("{path}/CHANGELOG.md");

let mut changelog = Changelog::read_file(&changelog_file_path).await?;

let mut changelog = Changelog::read(path).await?;
changelog.push_description(severity, description)?;
changelog.write_file(&changelog_file_path).await?;
changelog.sync_cargo_toml(path).await?;
changelog.sync_dependencies(path).await?;

changelog.write().await?;
changelog.sync_cargo_toml().await?;
changelog.sync_dependencies().await?;
Ok(())
}

Expand Down Expand Up @@ -384,8 +387,9 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap(),
Changelog::parse("path", changelog).unwrap(),
Changelog {
crate_path: "path".to_string(),
releases: vec![
Release {
version: Version::parse("0.3.0").unwrap(),
Expand Down Expand Up @@ -492,7 +496,7 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

assert_eq!(format!("{}", Changelog::parse(changelog).unwrap()), changelog);
assert_eq!(format!("{}", Changelog::parse("", changelog).unwrap()), changelog);
}

#[test]
Expand Down Expand Up @@ -526,8 +530,9 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap(),
Changelog::parse("path", changelog).unwrap(),
Changelog {
crate_path: "path".to_string(),
releases: vec![
Release {
version: Version::parse("0.2.0").unwrap(),
Expand Down Expand Up @@ -579,8 +584,9 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap(),
Changelog::parse("path", changelog).unwrap(),
Changelog {
crate_path: "path".to_string(),
releases: vec![
Release {
version: Version::parse("0.2.0").unwrap(),
Expand Down Expand Up @@ -619,7 +625,7 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Description ends with dot line 7"
);
}
Expand All @@ -634,8 +640,9 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap(),
Changelog::parse("path", changelog).unwrap(),
Changelog {
crate_path: "path".to_string(),
releases: vec![Release {
version: Version::parse("0.1.0").unwrap(),
contents: BTreeMap::new(),
Expand All @@ -655,8 +662,9 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap(),
Changelog::parse("path", changelog).unwrap(),
Changelog {
crate_path: "path".to_string(),
releases: vec![Release {
version: Version::parse("0.1.0").unwrap(),
contents: BTreeMap::new(),
Expand All @@ -675,7 +683,7 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Unexpected end of file after line 4"
);
}
Expand All @@ -686,7 +694,7 @@ mod tests {
## 0.1.0";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Line 1 should be \"# Changelog\""
);
}
Expand All @@ -711,7 +719,7 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Release 0.1.1 should be 0.3.0 due to major bump from 0.2.0"
);
}
Expand All @@ -723,7 +731,10 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

assert_eq!(Changelog::parse(changelog).unwrap_err().to_string(), "Expected release line 3");
assert_eq!(
Changelog::parse("", changelog).unwrap_err().to_string(),
"Expected release line 3"
);
}

#[test]
Expand All @@ -739,7 +750,10 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

assert_eq!(Changelog::parse(changelog).unwrap_err().to_string(), "Expected release line 9");
assert_eq!(
Changelog::parse("", changelog).unwrap_err().to_string(),
"Expected release line 9"
);
}

#[test]
Expand All @@ -756,7 +770,7 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Invalid skip counter prefix line 5"
);
}
Expand All @@ -781,7 +795,7 @@ mod tests {
";

assert_eq!(
Changelog::parse(changelog).unwrap_err().to_string(),
Changelog::parse("", changelog).unwrap_err().to_string(),
"Unexpected prerelease line 9"
);
}
Expand All @@ -801,7 +815,8 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

let mut changelog = Changelog::parse(changelog_str).expect("Failed to parse changelog.");
let mut changelog =
Changelog::parse("", changelog_str).expect("Failed to parse changelog.");

changelog.push_description(Severity::Major, "testing no dash").unwrap();
changelog.push_description(Severity::Major, "- testing with dash").unwrap();
Expand Down Expand Up @@ -831,7 +846,8 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

let mut changelog = Changelog::parse(changelog_str).expect("Failed to parse changelog.");
let mut changelog =
Changelog::parse("", changelog_str).expect("Failed to parse changelog.");

let current_release = changelog.get_or_create_release_mut();

Expand All @@ -853,7 +869,8 @@ mod tests {
<!-- Increment to skip CHANGELOG.md test: 0 -->
";

let mut changelog = Changelog::parse(changelog_str).expect("Failed to parse changelog.");
let mut changelog =
Changelog::parse("", changelog_str).expect("Failed to parse changelog.");

let current_release = changelog.get_or_create_release_mut();

Expand Down

0 comments on commit 5364dde

Please sign in to comment.