Unverified Commit 987024bf authored by Russell Cohen's avatar Russell Cohen Committed by GitHub
Browse files

Fix publisher check of published versions (#3483)

## Motivation and Context
Switch to the sparse index broke the publishers check if whether or not
a version was already published.

## Description
Fix check, add tests.

## Testing
- Ran test against the real sparse index.


----

_By submitting this pull request, I confirm that you can use, modify,
copy, and redistribute this contribution, under the terms of your
choice._
parent b515533c
Loading
Loading
Loading
Loading
+6 −4
Original line number Diff line number Diff line
@@ -109,10 +109,12 @@ pub fn resolve_publish_location(location: &Path) -> PathBuf {
}

async fn is_published(index: Arc<CratesIndex>, handle: &PackageHandle) -> Result<bool> {
    let crate_name = handle.name.clone();
    let versions =
        tokio::task::spawn_blocking(move || index.published_versions(&crate_name)).await??;
    Ok(!versions.is_empty())
    let name = handle.name.clone();
    let version = handle.version.clone();
    tokio::task::spawn_blocking(move || {
        smithy_rs_tool_common::index::is_published(index.as_ref(), &name, &version)
    })
    .await?
}

/// Waits for the given package to show up on crates.io
+60 −0
Original line number Diff line number Diff line
@@ -7,6 +7,7 @@ use crate::retry::{run_with_retry_sync, ErrorClass};
use anyhow::{anyhow, Context, Error, Result};
use crates_index::Crate;
use reqwest::StatusCode;
use semver::Version;
use std::{collections::HashMap, time::Duration};
use std::{fs, path::Path};

@@ -31,6 +32,11 @@ impl CratesIndex {
        Self(Inner::Fake(FakeIndex::from_file(path)))
    }

    /// Returns a fake crates.io index from a hashmap
    pub fn fake_from_map(versions: HashMap<String, Vec<String>>) -> Self {
        Self(Inner::Fake(FakeIndex { crates: versions }))
    }

    /// Retrieves the published versions for the given crate name.
    pub fn published_versions(&self, crate_name: &str) -> Result<Vec<String>> {
        match &self.0 {
@@ -46,6 +52,12 @@ impl CratesIndex {
    }
}

pub fn is_published(index: &CratesIndex, crate_name: &str, version: &Version) -> Result<bool> {
    let crate_name = crate_name.to_string();
    let versions = index.published_versions(&crate_name)?;
    Ok(versions.contains(&version.to_string()))
}

fn published_versions(index: &crates_index::SparseIndex, crate_name: &str) -> Result<Vec<String>> {
    let url = index
        .crate_url(crate_name)
@@ -106,3 +118,51 @@ impl FakeIndex {
        FakeIndex { crates }
    }
}

#[cfg(test)]
mod test {
    use crate::index::{is_published, CratesIndex};
    use semver::Version;
    use std::collections::HashMap;
    use std::sync::Arc;

    /// Ignored test against the real index
    #[ignore]
    #[test]
    fn test_known_published_versions() {
        let index = Arc::new(CratesIndex::real().unwrap());
        let known_published = Version::new(1, 1, 7);
        let known_never_published = Version::new(999, 999, 999);
        assert_eq!(
            is_published(&index, "aws-smithy-runtime-api", &known_published).unwrap(),
            true
        );

        assert_eq!(
            is_published(&index, "aws-smithy-runtime-api", &known_never_published).unwrap(),
            false
        );
    }

    /// Ignored test against the real index
    #[test]
    fn test_against_fake_index() {
        let mut crates = HashMap::new();
        crates.insert(
            "aws-smithy-runtime-api".to_string(),
            vec!["1.1.7".to_string()],
        );
        let index = Arc::new(CratesIndex::fake_from_map(crates));
        let known_published = Version::new(1, 1, 7);
        let known_never_published = Version::new(999, 999, 999);
        assert_eq!(
            is_published(&index, "aws-smithy-runtime-api", &known_published).unwrap(),
            true
        );

        assert_eq!(
            is_published(&index, "aws-smithy-runtime-api", &known_never_published).unwrap(),
            false
        );
    }
}