use jks::{Certificate, KeyStore, PrivateKeyEntry};
use std::fs::File;
use std::io::Read;
use std::time::SystemTime;
fn read_private_key_pem(path: &str) -> Result<Vec<u8>, Box<dyn std::error::Error>> {
let mut pem_file = File::open(path)?;
let mut pem_data = String::new();
pem_file.read_to_string(&mut pem_data)?;
let pem = pem::parse(&pem_data)?;
Ok(pem.into_contents())
}
fn read_certificate_pem(path: &str) -> Result<Vec<u8>, Box<dyn std::error::Error>> {
let mut pem_file = File::open(path)?;
let mut pem_data = String::new();
pem_file.read_to_string(&mut pem_data)?;
let pem = pem::parse(&pem_data)?;
Ok(pem.into_contents())
}
fn read_keystore(path: &str, password: &[u8]) -> Result<KeyStore, Box<dyn std::error::Error>> {
let mut file = File::open(path)?;
let mut ks = KeyStore::new();
ks.load(&mut file, password)?;
Ok(ks)
}
fn write_keystore(ks: &KeyStore, path: &str, password: &[u8]) -> Result<(), Box<dyn std::error::Error>> {
let mut file = File::create(path)?;
ks.store(&mut file, password)?;
Ok(())
}
fn zeroing(buf: &mut [u8]) {
for b in buf.iter_mut() {
*b = 0;
}
}
fn main() -> Result<(), Box<dyn std::error::Error>> {
let mut password = *b"password";
let mut ks1 = KeyStore::new();
let private_key = read_private_key_pem("examples/data/key.pem")?;
let cert_content = read_certificate_pem("examples/data/cert.pem")?;
let pke = PrivateKeyEntry {
creation_time: SystemTime::now(),
private_key,
certificate_chain: vec![Certificate {
cert_type: "X509".to_string(),
content: cert_content,
}],
};
ks1.set_private_key_entry("alias", pke, &password)?;
println!("Added private key entry with alias 'alias'");
write_keystore(&ks1, "keystore.jks", &password)?;
println!("Wrote keystore to keystore.jks");
let ks2 = read_keystore("keystore.jks", &password)?;
println!("Loaded keystore from keystore.jks");
let retrieved = ks2.get_private_key_entry("alias", &password)?;
println!("Retrieved private key entry:");
println!(" Certificate chain length: {}", retrieved.certificate_chain.len());
println!(
" Certificate type: {}",
retrieved.certificate_chain[0].cert_type
);
println!(" Private key length: {} bytes", retrieved.private_key.len());
zeroing(&mut password);
println!("\nExample completed successfully!");
Ok(())
}