From f58bd6add0034fd73c37076860f8334177863872 Mon Sep 17 00:00:00 2001 From: Nick Gerace Date: Wed, 21 Jan 2026 15:51:53 -0500 Subject: [PATCH] Allow innit to take in env variables This changes allows innit to take in env variables. This can be configured by environment variable or command line argument with the new "mode" type. It contains two variants: "env" and "ssm". If the mode is not provided, it defaults to "ssm", which ensures innit runs as it does on main today. If "env" is provided, then innit will take in environment variables to configure all services rather than using ssm. The environment variable use case may not be that interesting on its own, but innit being able to be used across several verticals and cloud providers in the future helps standardize the SI initialization procedure. Theorhetically, a secrets manager provided by a helm chart on a k8s cluster can do the same thing. For now, innit's env var use case is valuable. We'll see how long that will remain to be the case. Signed-off-by: Nick Gerace --- Cargo.lock | 4 +- bin/innit/src/args.rs | 11 ++ lib/bedrock-server/src/routes.rs | 4 +- lib/innit-core/BUCK | 6 +- lib/innit-core/Cargo.toml | 1 - lib/innit-core/src/lib.rs | 17 -- lib/innit-server/BUCK | 4 +- lib/innit-server/Cargo.toml | 2 + lib/innit-server/src/app_state.rs | 12 +- lib/innit-server/src/config.rs | 30 +++- lib/innit-server/src/lib.rs | 6 + lib/innit-server/src/parameter_storage.rs | 159 ++++++++++++++++++ lib/innit-server/src/parameter_storage/env.rs | 81 +++++++++ lib/innit-server/src/parameter_storage/ssm.rs | 38 +++++ lib/innit-server/src/routes.rs | 11 +- .../src/routes/create_parameter.rs | 9 +- lib/innit-server/src/routes/get_parameter.rs | 5 +- .../src/routes/list_parameters.rs | 5 +- lib/innit-server/src/server.rs | 25 ++- lib/si-data-ssm/Cargo.toml | 1 + lib/si-data-ssm/src/lib.rs | 1 + 21 files changed, 373 insertions(+), 59 deletions(-) create mode 100644 lib/innit-server/src/parameter_storage.rs create mode 100644 lib/innit-server/src/parameter_storage/env.rs create mode 100644 lib/innit-server/src/parameter_storage/ssm.rs diff --git a/Cargo.lock b/Cargo.lock index b8fbf8549f..e7b2dc90e1 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -4414,7 +4414,6 @@ dependencies = [ name = "innit-core" version = "0.1.0" dependencies = [ - "aws-sdk-ssm", "config-file", "serde", ] @@ -4423,6 +4422,7 @@ dependencies = [ name = "innit-server" version = "0.1.0" dependencies = [ + "async-trait", "axum 0.6.20", "buck2-resources", "dashmap", @@ -4438,6 +4438,7 @@ dependencies = [ "si-settings", "si-std", "si-tls", + "strum", "telemetry", "thiserror 2.0.12", "tokio", @@ -8051,6 +8052,7 @@ dependencies = [ name = "si-data-ssm" version = "0.1.0" dependencies = [ + "async-trait", "aws-sdk-ssm", "remain", "si-aws-config", diff --git a/bin/innit/src/args.rs b/bin/innit/src/args.rs index e0e3a8b32d..17cbd49ac4 100644 --- a/bin/innit/src/args.rs +++ b/bin/innit/src/args.rs @@ -8,6 +8,7 @@ use innit_server::{ Config, ConfigError, ConfigFile, + Mode, StandardConfigFile, }; use si_service::prelude::*; @@ -78,6 +79,15 @@ pub(crate) struct Args { /// The address and port to bind the HTTP server to [example: 0.0.0.0:80] #[arg(long, env)] pub(crate) socket_addr: Option, + + /// Mode for parameter storage backend [options: env, ssm] + #[arg( + long = "mode", + env = "SI_INNIT_MODE", + default_value = "ssm", + hide_env_values = true + )] + pub(crate) mode: Mode, } impl TryFrom for Config { @@ -91,6 +101,7 @@ impl TryFrom for Config { if let Some(socket_addr) = args.socket_addr { config_map.set("socket_addr", socket_addr); } + config_map.set("mode", args.mode.to_string()); })? .try_into() } diff --git a/lib/bedrock-server/src/routes.rs b/lib/bedrock-server/src/routes.rs index 11ed3c1665..b1f37e2d16 100644 --- a/lib/bedrock-server/src/routes.rs +++ b/lib/bedrock-server/src/routes.rs @@ -15,7 +15,7 @@ use serde_json::{ Value, json, }; -use si_data_ssm::ParameterStoreClientError; +use si_data_ssm::SsmParameterStoreClientError; use thiserror::Error; use super::{ @@ -62,7 +62,7 @@ pub fn public_routes(state: AppState) -> Router { #[derive(Debug, Error)] pub enum AppError { #[error("parameter store client error: {0}")] - ParameterStoreClient(#[from] ParameterStoreClientError), + ParameterStoreClient(#[from] SsmParameterStoreClientError), #[error("server error: {0}")] Server(#[from] ServerError), } diff --git a/lib/innit-core/BUCK b/lib/innit-core/BUCK index 90485abe4d..c19f01377c 100644 --- a/lib/innit-core/BUCK +++ b/lib/innit-core/BUCK @@ -4,12 +4,8 @@ rust_library( name = "innit-core", deps = [ "//lib/config-file:config-file", - "//third-party/rust:aws-sdk-ssm", - "//third-party/rust:chrono", - "//third-party/rust:serde", - "//third-party/rust:serde_json", - "//third-party/rust:ulid" + "//third-party/rust:serde" ], srcs = glob([ "src/**/*.rs", diff --git a/lib/innit-core/Cargo.toml b/lib/innit-core/Cargo.toml index e6192a852e..deede238f4 100644 --- a/lib/innit-core/Cargo.toml +++ b/lib/innit-core/Cargo.toml @@ -9,6 +9,5 @@ rust-version.workspace = true publish.workspace = true [dependencies] -aws-sdk-ssm = { workspace = true } config-file = { path = "../../lib/config-file" } serde = { workspace = true } diff --git a/lib/innit-core/src/lib.rs b/lib/innit-core/src/lib.rs index 2648ce63fa..948a9c10ba 100644 --- a/lib/innit-core/src/lib.rs +++ b/lib/innit-core/src/lib.rs @@ -1,7 +1,3 @@ -use aws_sdk_ssm::types::{ - Parameter as AwsParameter, - ParameterType as AwsParameterType, -}; use config_file::parameter_provider::{ Parameter as ParameterProviderParameter, ParameterType as ParameterProviderParameterType, @@ -18,19 +14,6 @@ pub struct Parameter { pub r#type: Option, } -impl From for Parameter { - fn from(p: AwsParameter) -> Self { - Self { - name: p.name().unwrap_or_default().to_string(), - value: p.value().map(|s| s.to_string()), - r#type: p.r#type().map(|t| match t { - AwsParameterType::StringList => ParameterType::StringList, - _ => ParameterType::String, - }), - } - } -} - impl From for ParameterProviderParameter { fn from(p: Parameter) -> Self { Self { diff --git a/lib/innit-server/BUCK b/lib/innit-server/BUCK index ac43d9c177..80bb9e67d8 100644 --- a/lib/innit-server/BUCK +++ b/lib/innit-server/BUCK @@ -10,8 +10,9 @@ rust_library( "//lib/si-settings:si-settings", "//lib/si-std:si-std", "//lib/si-tls:si-tls", - "//lib/telemetry-rs:telemetry", + "//third-party/rust:async-trait", + "//third-party/rust:aws-sdk-ssm", "//third-party/rust:axum", "//third-party/rust:dashmap", "//third-party/rust:derive_builder", @@ -21,6 +22,7 @@ rust_library( "//third-party/rust:remain", "//third-party/rust:serde", "//third-party/rust:serde_json", + "//third-party/rust:strum", "//third-party/rust:thiserror", "//third-party/rust:tokio", "//third-party/rust:tokio-rustls", diff --git a/lib/innit-server/Cargo.toml b/lib/innit-server/Cargo.toml index e4902ba707..45eada201a 100644 --- a/lib/innit-server/Cargo.toml +++ b/lib/innit-server/Cargo.toml @@ -9,6 +9,7 @@ rust-version.workspace = true publish.workspace = true [dependencies] +async-trait = { workspace = true } axum = { workspace = true } buck2-resources = { path = "../../lib/buck2-resources" } dashmap = { workspace = true } @@ -24,6 +25,7 @@ si-data-ssm = { path = "../../lib/si-data-ssm" } si-settings = { path = "../../lib/si-settings" } si-std = { path = "../../lib/si-std" } si-tls = { path = "../../lib/si-tls" } +strum = { workspace = true } telemetry = { path = "../../lib/telemetry-rs" } thiserror = { workspace = true } tokio = { workspace = true } diff --git a/lib/innit-server/src/app_state.rs b/lib/innit-server/src/app_state.rs index e60958fdb4..c3fa8bd4ca 100644 --- a/lib/innit-server/src/app_state.rs +++ b/lib/innit-server/src/app_state.rs @@ -1,8 +1,10 @@ use axum::extract::FromRef; -use si_data_ssm::ParameterStoreClient; use tokio_util::sync::CancellationToken; -use crate::parameter_cache::ParameterCache; +use crate::{ + parameter_cache::ParameterCache, + parameter_storage::ParameterStore, +}; #[remain::sorted] #[derive(Debug, Eq, PartialEq)] @@ -11,7 +13,7 @@ pub enum ShutdownSource {} #[derive(Clone, Debug, FromRef)] pub struct AppState { pub parameter_cache: ParameterCache, - pub parameter_store_client: ParameterStoreClient, + pub parameter_storage: ParameterStore, shutdown_token: CancellationToken, } @@ -19,12 +21,12 @@ impl AppState { #[allow(clippy::too_many_arguments)] pub fn new( parameter_cache: ParameterCache, - parameter_store_client: ParameterStoreClient, + parameter_storage: ParameterStore, shutdown_token: CancellationToken, ) -> Self { Self { parameter_cache, - parameter_store_client, + parameter_storage, shutdown_token, } } diff --git a/lib/innit-server/src/config.rs b/lib/innit-server/src/config.rs index 00954779a6..04a2deaf0c 100644 --- a/lib/innit-server/src/config.rs +++ b/lib/innit-server/src/config.rs @@ -19,6 +19,10 @@ use si_std::{ CanonicalFileError, }; use si_tls::CertificateSource; +use strum::{ + Display, + EnumString, +}; use telemetry::prelude::*; use thiserror::Error; use ulid::Ulid; @@ -49,7 +53,19 @@ impl ConfigError { type Result = std::result::Result; -/// The config for the forklift server. +#[remain::sorted] +#[derive( + Debug, Default, Clone, Copy, Serialize, Deserialize, PartialEq, Eq, EnumString, Display, +)] +#[serde(rename_all = "lowercase")] +#[strum(serialize_all = "lowercase")] +pub enum Mode { + Env, + #[default] + Ssm, +} + +/// The config for the server. #[derive(Debug, Builder)] pub struct Config { #[builder(default = "default_cache_ttl()")] @@ -78,6 +94,9 @@ pub struct Config { #[builder(default)] dev_mode: bool, + + #[builder(default = "Mode::default()")] + mode: Mode, } impl StandardConfig for Config { @@ -124,6 +143,10 @@ impl Config { pub fn client_ca_arns(&self) -> Option<&Vec> { self.client_ca_arns.as_ref() } + + pub fn mode(&self) -> Mode { + self.mode + } } #[derive(Clone, Debug, Deserialize, Serialize)] @@ -147,6 +170,9 @@ pub struct ConfigFile { #[serde(default)] pub dev_mode: bool, + + #[serde(default)] + mode: Mode, } impl Default for ConfigFile { @@ -161,6 +187,7 @@ impl Default for ConfigFile { socket_addr: get_default_socket_addr(), test_endpoint: default_test_endpoint(), dev_mode: false, + mode: Mode::default(), } } } @@ -182,6 +209,7 @@ impl TryFrom for Config { config.instance_id(value.instance_id); config.quiescent_period(Duration::from_secs(value.quiescent_period_secs)); config.dev_mode(value.dev_mode); + config.mode(value.mode); config.build().map_err(Into::into) } } diff --git a/lib/innit-server/src/lib.rs b/lib/innit-server/src/lib.rs index 00184ba1df..7e2f9cdf5b 100644 --- a/lib/innit-server/src/lib.rs +++ b/lib/innit-server/src/lib.rs @@ -3,6 +3,7 @@ mod app_state; mod config; mod middleware; mod parameter_cache; +mod parameter_storage; mod routes; mod server; @@ -11,8 +12,13 @@ pub use self::{ Config, ConfigError, ConfigFile, + Mode, StandardConfigFile, detect_and_configure_development, }, + parameter_storage::{ + ParameterStore, + ParameterStoreKind, + }, server::Server, }; diff --git a/lib/innit-server/src/parameter_storage.rs b/lib/innit-server/src/parameter_storage.rs new file mode 100644 index 0000000000..c1571bc7d5 --- /dev/null +++ b/lib/innit-server/src/parameter_storage.rs @@ -0,0 +1,159 @@ +#![warn( + bad_style, + clippy::missing_panics_doc, + clippy::panic, + clippy::panic_in_result_fn, + clippy::unwrap_in_result, + clippy::unwrap_used, + dead_code, + improper_ctypes, + missing_debug_implementations, + no_mangle_generic_items, + non_shorthand_field_patterns, + overflowing_literals, + path_statements, + patterns_in_fns_without_body, + unconditional_recursion, + unreachable_pub, + unused, + unused_allocation, + unused_comparisons, + unused_parens, + while_true +)] + +use telemetry::prelude::*; +use thiserror::Error; + +use crate::Mode; + +pub(crate) mod env; +pub(crate) mod ssm; + +#[remain::sorted] +#[derive(Debug, Error)] +pub enum ParameterStoreError { + #[error("attempted write in env mode (write operations not supported in this mode)")] + AttemptedWriteInEnvMode, + #[error("parameter path invalid (must start with '/'): {0}")] + InvalidPath(String), + #[error("parameter not found: {0}")] + ParameterNotFound(String), + #[error("parameter path not found: {0}")] + PathNotFound(String), + #[error("ssm parameter store client error: {0}")] + SsmParameterStoreClient(#[from] si_data_ssm::ParameterStoreClientError), +} + +pub(crate) type ParameterStoreResult = Result; + +#[remain::sorted] +#[derive(Debug, Clone)] +pub enum ParameterStore { + Env(env::EnvParameterStorage), + Ssm(si_data_ssm::ParameterStoreClient), +} + +impl ParameterStore { + pub async fn new(mode: Mode, test_endpoint: Option) -> ParameterStoreResult { + match mode { + Mode::Env => Ok(Self::Env(env::EnvParameterStorage::new())), + Mode::Ssm => { + let ssm_client = if let Some(endpoint) = test_endpoint { + si_data_ssm::ParameterStoreClient::new_for_test(endpoint) + } else { + si_data_ssm::ParameterStoreClient::new().await? + }; + Ok(Self::Ssm(ssm_client)) + } + } + } +} + +#[derive(Debug, Clone, PartialEq, Eq)] +pub enum ParameterType { + String, +} + +#[derive(Debug, Clone, PartialEq, Eq)] +pub struct Parameter { + pub name: String, + pub value: String, + pub parameter_type: ParameterType, +} + +impl Parameter { + pub fn new(name: String, value: String, parameter_type: ParameterType) -> Self { + Self { + name, + value, + parameter_type, + } + } +} + +impl From for innit_core::Parameter { + fn from(p: Parameter) -> Self { + Self { + name: p.name, + value: Some(p.value), + r#type: Some(match p.parameter_type { + ParameterType::String => innit_core::ParameterType::String, + }), + } + } +} + +#[async_trait::async_trait] +pub trait ParameterStoreKind: std::fmt::Debug + Send + Sync { + async fn get_parameter(&self, name: String) -> ParameterStoreResult; + async fn parameters_by_path(&self, path: String) -> ParameterStoreResult>; + async fn create_string_parameter( + &self, + name: String, + value: String, + ) -> ParameterStoreResult<()>; +} + +#[async_trait::async_trait] +impl ParameterStoreKind for ParameterStore { + async fn get_parameter(&self, name: String) -> ParameterStoreResult { + match self { + Self::Env(storage) => storage.get_parameter(name).await, + Self::Ssm(client) => { + ::get_parameter( + client, name, + ) + .await + } + } + } + + async fn parameters_by_path(&self, path: String) -> ParameterStoreResult> { + match self { + Self::Env(storage) => storage.parameters_by_path(path).await, + Self::Ssm(client) => { + ::parameters_by_path( + client, path, + ) + .await + } + } + } + + async fn create_string_parameter( + &self, + name: String, + value: String, + ) -> ParameterStoreResult<()> { + match self { + Self::Env(storage) => storage.create_string_parameter(name, value).await, + Self::Ssm(client) => { + ::create_string_parameter( + client, name, value, + ) + .await + } + } + } +} diff --git a/lib/innit-server/src/parameter_storage/env.rs b/lib/innit-server/src/parameter_storage/env.rs new file mode 100644 index 0000000000..2b467e8200 --- /dev/null +++ b/lib/innit-server/src/parameter_storage/env.rs @@ -0,0 +1,81 @@ +use super::{ + Parameter, + ParameterStoreError, + ParameterStoreKind, + ParameterStoreResult, + ParameterType, +}; + +#[derive(Debug, Default, Clone)] +pub struct EnvParameterStorage; + +impl EnvParameterStorage { + pub fn new() -> Self { + Self + } + + /// Converts a parameter path to an environment variable name + /// Example: `/si/todd/howard` -> `SI_TODD_HOWARD` + fn path_to_env_var(path: &str) -> String { + path.trim_start_matches('/') + .replace('/', "_") + .to_uppercase() + } + + /// Checks if an environment variable key matches a path prefix + fn env_var_matches_path(env_key: &str, path: &str) -> bool { + let normalized = Self::path_to_env_var(path); + // Match exact or with underscore separator to avoid false matches + // e.g., SI_PROD matches SI_PROD_DB but not SI_PRODUCTION + env_key == normalized || env_key.starts_with(&format!("{normalized}_")) + } + + /// Converts an environment variable name back to a parameter path + /// Example: `/si/todd/howard` -> `SI_TODD_HOWARD` + fn env_var_to_path(env_var: &str) -> String { + format!("/{}", env_var.replace('_', "/").to_lowercase()) + } +} + +#[async_trait::async_trait] +impl ParameterStoreKind for EnvParameterStorage { + async fn get_parameter(&self, name: String) -> ParameterStoreResult { + let env_var = Self::path_to_env_var(&name); + + #[allow(clippy::disallowed_methods)] + let value = std::env::var(&env_var) + .map_err(|_| ParameterStoreError::ParameterNotFound(name.clone()))?; + + Ok(Parameter::new(name, value, ParameterType::String)) + } + + async fn parameters_by_path(&self, path: String) -> ParameterStoreResult> { + if !path.starts_with("/") { + return Err(ParameterStoreError::InvalidPath(path)); + } + + let mut parameters = Vec::new(); + + #[allow(clippy::disallowed_methods)] + for (key, value) in std::env::vars() { + if Self::env_var_matches_path(&key, &path) { + let param_name = Self::env_var_to_path(&key); + parameters.push(Parameter::new(param_name, value, ParameterType::String)); + } + } + + if parameters.is_empty() { + return Err(ParameterStoreError::PathNotFound(path)); + } + + Ok(parameters) + } + + async fn create_string_parameter( + &self, + _name: String, + _value: String, + ) -> ParameterStoreResult<()> { + Err(ParameterStoreError::AttemptedWriteInEnvMode) + } +} diff --git a/lib/innit-server/src/parameter_storage/ssm.rs b/lib/innit-server/src/parameter_storage/ssm.rs new file mode 100644 index 0000000000..92541f5912 --- /dev/null +++ b/lib/innit-server/src/parameter_storage/ssm.rs @@ -0,0 +1,38 @@ +use super::{ + Parameter, + ParameterStoreKind, + ParameterStoreResult, + ParameterType, +}; + +fn convert_aws_parameter(ssm_parameter: si_data_ssm::SsmParameter) -> Parameter { + Parameter::new( + ssm_parameter.name().unwrap_or_default().to_string(), + ssm_parameter.value().unwrap_or_default().to_string(), + ParameterType::String, + ) +} + +/// Implementation of ParameterStorage for the SSM ParameterStoreClient. +#[async_trait::async_trait] +impl ParameterStoreKind for si_data_ssm::ParameterStoreClient { + async fn get_parameter(&self, name: String) -> ParameterStoreResult { + let aws_param = self.get_parameter(name).await?; + Ok(convert_aws_parameter(aws_param)) + } + + async fn parameters_by_path(&self, path: String) -> ParameterStoreResult> { + let aws_params = self.parameters_by_path(path).await?; + Ok(aws_params.into_iter().map(convert_aws_parameter).collect()) + } + + async fn create_string_parameter( + &self, + name: String, + value: String, + ) -> ParameterStoreResult<()> { + self.create_string_parameter(name, value) + .await + .map_err(Into::into) + } +} diff --git a/lib/innit-server/src/routes.rs b/lib/innit-server/src/routes.rs index 182a8506a9..9c8a03ed34 100644 --- a/lib/innit-server/src/routes.rs +++ b/lib/innit-server/src/routes.rs @@ -16,7 +16,6 @@ use serde_json::{ Value, json, }; -use si_data_ssm::ParameterStoreClientError; use thiserror::Error; mod clear_cache; @@ -28,7 +27,10 @@ use super::{ app_state::AppState, server::ServerError, }; -use crate::api_error::ApiError; +use crate::{ + api_error::ApiError, + parameter_storage::ParameterStoreError, +}; pub fn public_routes(state: AppState) -> Router { Router::new() @@ -55,12 +57,11 @@ async fn system_status_route() -> Json { Json(json!({ "ok": true })) } -#[allow(clippy::large_enum_variant)] #[remain::sorted] #[derive(Debug, Error)] pub enum AppError { - #[error("parameter store client error: {0}")] - ParameterStoreClient(#[from] ParameterStoreClientError), + #[error("parameter storage error: {0}")] + ParameterStore(#[from] ParameterStoreError), #[error("server error: {0}")] Server(#[from] ServerError), } diff --git a/lib/innit-server/src/routes/create_parameter.rs b/lib/innit-server/src/routes/create_parameter.rs index 0764172f20..5157e7a6b0 100644 --- a/lib/innit-server/src/routes/create_parameter.rs +++ b/lib/innit-server/src/routes/create_parameter.rs @@ -13,13 +13,16 @@ use innit_core::{ use telemetry::tracing::info; use super::AppError; -use crate::app_state::AppState; +use crate::{ + app_state::AppState, + parameter_storage::ParameterStoreKind, +}; pub async fn create_parameter_route( Path(name): Path, State(AppState { parameter_cache, - parameter_store_client, + parameter_storage, .. }): State, Json(CreateParameterRequest { value }): Json, @@ -30,7 +33,7 @@ pub async fn create_parameter_route( name.clone() }; - parameter_store_client + parameter_storage .create_string_parameter(name.clone(), value.clone()) .await?; diff --git a/lib/innit-server/src/routes/get_parameter.rs b/lib/innit-server/src/routes/get_parameter.rs index 62b28f14a5..c4c6942a41 100644 --- a/lib/innit-server/src/routes/get_parameter.rs +++ b/lib/innit-server/src/routes/get_parameter.rs @@ -11,6 +11,7 @@ use telemetry::tracing::info; use super::AppError; use crate::{ app_state::AppState, + parameter_storage::ParameterStoreKind, routes::Json, }; @@ -18,7 +19,7 @@ pub async fn get_parameter_route( Path(name): Path, State(AppState { parameter_cache, - parameter_store_client, + parameter_storage, .. }): State, ) -> Result, AppError> { @@ -36,7 +37,7 @@ pub async fn get_parameter_route( })); } - let parameter: Parameter = parameter_store_client + let parameter: Parameter = parameter_storage .get_parameter(name.clone()) .await? .into(); diff --git a/lib/innit-server/src/routes/list_parameters.rs b/lib/innit-server/src/routes/list_parameters.rs index f0cef8df55..9a48da24f6 100644 --- a/lib/innit-server/src/routes/list_parameters.rs +++ b/lib/innit-server/src/routes/list_parameters.rs @@ -11,6 +11,7 @@ use telemetry::tracing::info; use super::AppError; use crate::{ app_state::AppState, + parameter_storage::ParameterStoreKind, routes::Json, }; @@ -18,7 +19,7 @@ pub async fn list_parameters_route( Path(path): Path, State(AppState { parameter_cache, - parameter_store_client, + parameter_storage, .. }): State, ) -> Result, AppError> { @@ -36,7 +37,7 @@ pub async fn list_parameters_route( })); } - let parameters: Vec = parameter_store_client + let parameters: Vec = parameter_storage .parameters_by_path(path.clone()) .await? .iter() diff --git a/lib/innit-server/src/server.rs b/lib/innit-server/src/server.rs index 66f11d6156..50fea82caa 100644 --- a/lib/innit-server/src/server.rs +++ b/lib/innit-server/src/server.rs @@ -24,10 +24,6 @@ use si_data_acmpca::{ PrivateCertManagerClient, PrivateCertManagerClientError, }; -use si_data_ssm::{ - ParameterStoreClient, - ParameterStoreClientError, -}; use si_tls::{ CertificateSource, ClientCertificateVerifier, @@ -59,6 +55,10 @@ use crate::{ app_state::AppState, middleware::client_cert_auth::verify_client_cert_middleware, parameter_cache::ParameterCache, + parameter_storage::{ + ParameterStore, + ParameterStoreError, + }, }; #[remain::sorted] @@ -68,8 +68,8 @@ pub enum ServerError { CertificateClient(#[from] PrivateCertManagerClientError), #[error("hyper server error")] Hyper(#[from] hyper::Error), - #[error("Parameter Store error: {0}")] - ParameterStore(#[from] ParameterStoreClientError), + #[error("parameter store error")] + ParameterStore(#[from] ParameterStoreError), #[error("serde json error: {0}")] SerdeJson(#[from] serde_json::Error), #[error("failed to setup signal handler")] @@ -97,11 +97,8 @@ impl Server<()> { config: Config, token: CancellationToken, ) -> ServerResult> { - let parameter_store_client = if let Some(endpoint) = config.test_endpoint() { - ParameterStoreClient::new_for_test(endpoint) - } else { - ParameterStoreClient::new().await? - }; + let parameter_store = + ParameterStore::new(config.mode(), config.test_endpoint().clone()).await?; // dev mode, no certs necessary // use a cert if one is supplied @@ -126,7 +123,7 @@ impl Server<()> { let service = build_service( client_cert_verifier, parameter_cache, - parameter_store_client, + parameter_store, token.clone(), )?; @@ -171,10 +168,10 @@ where pub fn build_service( client_cert_verifier: Option>, parameter_cache: ParameterCache, - parameter_store_client: ParameterStoreClient, + parameter_storage: ParameterStore, token: CancellationToken, ) -> ServerResult { - let state = AppState::new(parameter_cache, parameter_store_client, token); + let state = AppState::new(parameter_cache, parameter_storage, token); let public_routes = routes::public_routes(state.clone()); let mut protected_routes = routes::protected_routes(state); diff --git a/lib/si-data-ssm/Cargo.toml b/lib/si-data-ssm/Cargo.toml index bf87e41fa6..1e18a68559 100644 --- a/lib/si-data-ssm/Cargo.toml +++ b/lib/si-data-ssm/Cargo.toml @@ -9,6 +9,7 @@ rust-version.workspace = true publish.workspace = true [dependencies] +async-trait = { workspace = true } aws-sdk-ssm = { workspace = true } remain = { workspace = true } si-aws-config = { path = "../../lib/si-aws-config" } diff --git a/lib/si-data-ssm/src/lib.rs b/lib/si-data-ssm/src/lib.rs index bf9e15d11a..091f1af504 100644 --- a/lib/si-data-ssm/src/lib.rs +++ b/lib/si-data-ssm/src/lib.rs @@ -27,6 +27,7 @@ use std::fmt::Debug; +pub use aws_sdk_ssm::types::Parameter as SsmParameter; // re-export so consumers directly rely on "aws-sdk-ssm" use aws_sdk_ssm::{ config::{ Credentials,