secrets_provider_tests/
suite.rs

1use crate::{
2    Capabilities, ProviderUnderTest, TestEnv, assert_deleted, assert_get_eq, medium_payload,
3    small_payload,
4};
5use anyhow::{Context, Result};
6
7/// Runs the shared conformance suite against a provider.
8pub struct ConformanceSuite<'a, P: ProviderUnderTest> {
9    provider_name: String,
10    provider: &'a P,
11    caps: Capabilities,
12    env: TestEnv,
13}
14
15impl<'a, P: ProviderUnderTest> ConformanceSuite<'a, P> {
16    pub fn new(provider_name: impl Into<String>, provider: &'a P, caps: Capabilities) -> Self {
17        let provider_name = provider_name.into();
18        Self {
19            env: TestEnv::from_env(&provider_name),
20            provider_name,
21            provider,
22            caps,
23        }
24    }
25
26    pub async fn run(&self) -> Result<()> {
27        let key = self.env.prefix.key("secret");
28        let initial = small_payload();
29        let updated = medium_payload();
30
31        self.provider
32            .put(&key, &initial)
33            .await
34            .with_context(|| format!("put failed for {}:{key}", self.provider_name))?;
35
36        assert_get_eq(self.provider, &self.provider_name, &key, &initial).await?;
37
38        self.provider
39            .put(&key, &updated)
40            .await
41            .with_context(|| format!("overwrite failed for {}:{key}", self.provider_name))?;
42        assert_get_eq(self.provider, &self.provider_name, &key, &updated).await?;
43
44        if self.caps.list {
45            let list = self
46                .provider
47                .list(&self.env.prefix.base())
48                .await
49                .with_context(|| format!("list failed for {}:{key}", self.provider_name))?;
50            if !list.iter().any(|item| item.ends_with(&key)) {
51                anyhow::bail!(
52                    "list did not return expected key {}:{key}",
53                    self.provider_name
54                );
55            }
56        }
57
58        self.provider
59            .delete(&key)
60            .await
61            .with_context(|| format!("delete failed for {}:{key}", self.provider_name))?;
62
63        if self.env.cleanup {
64            assert_deleted(self.provider, &self.provider_name, &key).await?;
65        }
66
67        Ok(())
68    }
69}