Open with key rotation: current key + previous key for dual-key reads. New writes use `current_key_path`. Reads try current first, then previous. Once all old WAL segments are compacted, remove the previous key.
(
path: &Path,
use_direct_io: bool,
current_key_path: &Path,
previous_key_path: &Path,
)
| 32 | /// New writes use `current_key_path`. Reads try current first, then previous. |
| 33 | /// Once all old WAL segments are compacted, remove the previous key. |
| 34 | pub fn open_encrypted_rotating( |
| 35 | path: &Path, |
| 36 | use_direct_io: bool, |
| 37 | current_key_path: &Path, |
| 38 | previous_key_path: &Path, |
| 39 | ) -> crate::Result<Self> { |
| 40 | let current = nodedb_wal::crypto::WalEncryptionKey::from_file(current_key_path) |
| 41 | .map_err(crate::Error::Wal)?; |
| 42 | let previous = nodedb_wal::crypto::WalEncryptionKey::from_file(previous_key_path) |
| 43 | .map_err(crate::Error::Wal)?; |
| 44 | let ring = nodedb_wal::crypto::KeyRing::with_previous(current, previous); |
| 45 | let mut mgr = Self::open(path, use_direct_io)?; |
| 46 | { |
| 47 | let mut wal = mgr.wal.lock().unwrap_or_else(|p| p.into_inner()); |
| 48 | wal.set_encryption_ring(ring.clone()) |
| 49 | .map_err(crate::Error::Wal)?; |
| 50 | } |
| 51 | mgr.encryption_ring = Some(ring); |
| 52 | info!( |
| 53 | current_key = %current_key_path.display(), |
| 54 | previous_key = %previous_key_path.display(), |
| 55 | "WAL encryption enabled with key rotation" |
| 56 | ); |
| 57 | Ok(mgr) |
| 58 | } |
| 59 | |
| 60 | /// Rotate the encryption key at runtime without downtime. |
| 61 | /// |
nothing calls this directly
no test coverage detected