Skip to content

Commit

Permalink
feat(config): add vault provider
Browse files Browse the repository at this point in the history
Signed-off-by: Frank Yang <[email protected]>
  • Loading branch information
FrankYang0529 committed Oct 1, 2022
1 parent 13f7916 commit becd76c
Show file tree
Hide file tree
Showing 4 changed files with 185 additions and 4 deletions.
136 changes: 132 additions & 4 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 2 additions & 0 deletions crates/config/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,8 @@ spin-app = { path = "../app" }
spin-core = { path = "../core" }
thiserror = "1"
tokio = { version = "1", features = ["rt-multi-thread"] }
vaultrs = "0.6.2"
serde = "1.0.145"

[dependencies.wit-bindgen-wasmtime]
git = "https://github.com/bytecodealliance/wit-bindgen"
Expand Down
1 change: 1 addition & 0 deletions crates/config/src/provider.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use crate::Key;

/// Environment variable based provider.
pub mod env;
pub mod vault;

/// A config provider.
#[async_trait]
Expand Down
50 changes: 50 additions & 0 deletions crates/config/src/provider/vault.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
use anyhow::{anyhow, Result};
use async_trait::async_trait;
use serde::{Deserialize, Serialize};
use vaultrs::{
client::{VaultClient, VaultClientSettingsBuilder},
kv2,
};

use crate::{Key, Provider};

/// A config Provider that uses HashiCorp Vault.
#[derive(Debug)]
pub struct VaultProvider {
url: String,
token: String,
}

impl VaultProvider {
pub fn new(url: impl AsRef<String>, token: impl AsRef<String>) -> Result<Self> {
Ok(Self {
url: url.as_ref().to_string(),
token: token.as_ref().to_string(),
})
}
}

#[derive(Debug, Deserialize, Serialize)]
struct Secret {
value: String,
}

#[async_trait]
impl Provider for VaultProvider {
async fn get(&self, key: &Key) -> Result<Option<String>> {
let client = VaultClient::new(
VaultClientSettingsBuilder::default()
.address(&self.url)
.token(&self.token)
.build()?,
)?;
let keys = key.0.split("/").collect::<Vec<_>>();
if keys.len() == 1 {
return Err(anyhow!("vault key must contain the mount path"));
}
let mount = keys[0];
let path = keys[1..].join("/");
let secret: Secret = kv2::read(&client, mount, &path).await?;
Ok(Some(secret.value))
}
}

0 comments on commit becd76c

Please sign in to comment.