Skip to content

Commit

Permalink
Unit tests for KMS signing functionality
Browse files Browse the repository at this point in the history
Small part of reading and initializing key and certficate data is covered with tests.

Signed-off-by: Eugene Koira <eugkoira@amazon.com>
  • Loading branch information
eugkoira committed Apr 18, 2024
1 parent ec911e3 commit 6855daf
Show file tree
Hide file tree
Showing 2 changed files with 171 additions and 1 deletion.
3 changes: 2 additions & 1 deletion .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,8 @@ jobs:
- uses: actions/checkout@v3
- run: rustup install ${{ matrix.rust }}
- run: cargo +${{ matrix.rust }} build --verbose
- run: cargo +${{ matrix.rust }} test --verbose
- run: cargo +${{ matrix.rust }} test --verbose \
-- --skip tests::kms # Requires AWS creds
clippy:
runs-on: ubuntu-latest
steps:
Expand Down
169 changes: 169 additions & 0 deletions src/utils/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -807,3 +807,172 @@ impl PcrSignatureChecker {
Ok(())
}
}

#[cfg(test)]
mod tests {
use crate::utils::{SignKey, SignKeyData, SignKeyDataInfo, SignKeyInfo};
use std::{env, io::Write};
use tempfile::{NamedTempFile, TempPath};

const TEST_CERT_CONTENT: &[u8] = "test cert content".as_bytes();
const TEST_PKEY_CONTENT: &[u8] = "test key content".as_bytes();

fn generate_certificate_file() -> Result<TempPath, std::io::Error> {
let cert_file = NamedTempFile::new()?;
cert_file.as_file().write(TEST_CERT_CONTENT)?;
Ok(cert_file.into_temp_path())
}

fn generate_pkey_file() -> Result<TempPath, std::io::Error> {
let key_file = NamedTempFile::new()?;
key_file.as_file().write(TEST_PKEY_CONTENT)?;
Ok(key_file.into_temp_path())
}

#[test]
fn test_local_sign_key_data_from_invalid_local_key_info() -> Result<(), std::io::Error> {
let cert_file_path = generate_certificate_file()?;

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: cert_file_path.to_str().unwrap().to_string(),
key_info: SignKeyInfo::LocalPrivateKeyInfo {
path: "/invalid/path".to_string(),
},
});

assert!(key_data.is_err());
Ok(())
}

#[test]
fn test_local_sign_key_data_from_invalid_cert_key_info() -> Result<(), std::io::Error> {
let key_file_path = generate_pkey_file()?;

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: "/invalid/path".to_string(),
key_info: SignKeyInfo::LocalPrivateKeyInfo {
path: key_file_path.to_str().unwrap().to_string(),
},
});

assert!(key_data.is_err());
Ok(())
}

#[test]
fn test_local_sign_key_data_from_valid_key_info() -> Result<(), std::io::Error> {
let cert_file_path = generate_certificate_file()?;
let key_file_path = generate_pkey_file()?;

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: cert_file_path.to_str().unwrap().to_string(),
key_info: SignKeyInfo::LocalPrivateKeyInfo {
path: key_file_path.to_str().unwrap().to_string(),
},
})
.unwrap();

assert_eq!(key_data.cert, TEST_CERT_CONTENT);
assert!(matches!(key_data.key, SignKey::LocalPrivateKey(key) if key == TEST_PKEY_CONTENT));

Ok(())
}

mod kms {
use std::sync::Mutex;

use super::*;

// Mutex to lock and prevent running tests that modify AWS_REGION env variable
// within multiple threads
static ENV_MUTEX: std::sync::Mutex<i32> = Mutex::new(0);

#[test]
fn test_kms_sign_key_data_from_invalid_cert_key_info() -> Result<(), std::io::Error> {
let key_id = env::var("AWS_KMS_TEST_KEY_ID").expect("Please set AWS_KMS_TEST_KEY_ID");
let key_region = env::var("AWS_KMS_TEST_KEY_REGION").ok();

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: "/invalid/path".to_string(),
key_info: SignKeyInfo::KmsKeyInfo {
id: key_id,
region: key_region,
},
});

assert!(key_data.is_err());
Ok(())
}

#[test]
fn test_kms_sign_key_data_from_valid_key_info_explicit_region() -> Result<(), std::io::Error>
{
let cert_file_path = generate_certificate_file()?;
let key_id = env::var("AWS_KMS_TEST_KEY_ID").expect("Please set AWS_KMS_TEST_KEY_ID");
let key_region =
env::var("AWS_KMS_TEST_KEY_REGION").expect("Please set AWS_KMS_TEST_KEY_REGION");
let _m = ENV_MUTEX.lock().unwrap();
env::remove_var("AWS_REGION");

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: cert_file_path.to_str().unwrap().to_string(),
key_info: SignKeyInfo::KmsKeyInfo {
id: key_id,
region: Some(key_region),
},
})
.unwrap();

assert_eq!(key_data.cert, TEST_CERT_CONTENT);
assert!(matches!(key_data.key, SignKey::KmsKey(_)));

Ok(())
}

#[test]
fn test_kms_sign_key_data_from_valid_key_info_region_from_env() -> Result<(), std::io::Error>
{
let cert_file_path = generate_certificate_file()?;
let key_id = env::var("AWS_KMS_TEST_KEY_ID").expect("Please set AWS_KMS_TEST_KEY_ID");
let key_region =
env::var("AWS_KMS_TEST_KEY_REGION").expect("Please set AWS_KMS_TEST_KEY_REGION");

let _m = ENV_MUTEX.lock().unwrap();
env::set_var("AWS_REGION", key_region);

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: cert_file_path.to_str().unwrap().to_string(),
key_info: SignKeyInfo::KmsKeyInfo {
id: key_id,
region: None,
},
})
.unwrap();

assert_eq!(key_data.cert, TEST_CERT_CONTENT);
assert!(matches!(key_data.key, SignKey::KmsKey(_)));

Ok(())
}

#[test]
fn test_kms_sign_key_data_from_valid_key_info_no_region() -> Result<(), std::io::Error> {
let cert_file_path = generate_certificate_file()?;
let key_id = env::var("AWS_KMS_TEST_KEY_ID").expect("Please set AWS_KMS_TEST_KEY_ID");

let _m = ENV_MUTEX.lock().unwrap();
env::remove_var("AWS_REGION");

let key_data = SignKeyData::new(&SignKeyDataInfo {
cert_path: cert_file_path.to_str().unwrap().to_string(),
key_info: SignKeyInfo::KmsKeyInfo {
id: key_id,
region: None,
},
});

assert!(key_data.is_err());
Ok(())
}
}
}

0 comments on commit 6855daf

Please sign in to comment.