mirror of
https://github.com/rustfs/rustfs.git
synced 2026-08-11 07:36:53 +00:00
feat(admin): expose KMS backup and restore behind explicit guards (#5579)
* feat(kms): add backup and restore admin API Wires the merged KMS backup contract, Local export and Local restore into the admin API: export a sealed bundle, run a zero-write restore preflight, execute a confirmed restore, roll an interrupted restore back, and report subsystem readiness. - Dedicated kms:Backup / kms:Restore actions, recorded in the admin route matrix. Neither is reachable through any other KMS action. - Restore requires two independent confirmations: an echo of the bundle manifest's backup id, and an explicitly named conflict policy (the default never writes). - The backup KEK comes from the environment and is refused when it reuses a secret of the configured backend, compared both as the literal value and as raw key bytes. - No endpoint accepts a path: bundles are addressed by a validated name under a configured root, and the restore target is always the server's own configured key directory. - Bundles now carry a sanitized configuration artifact built as an allowlist projection, so a future backend credential field cannot leak into a bundle by default. Restore verifies it and never applies it. - Audit entries go through the existing KMS admin wiring and carry identifiers only. * test(kms): pin the backup admin API gates Fixes the test KEK to a real 32-byte value and drives the export refusal from the configured backend rather than from the handle that happens to be available, so a Local handle cannot export on behalf of a backend whose material RustFS does not own.
This commit is contained in:
@@ -730,6 +730,13 @@ pub enum KmsAction {
|
||||
DescribeKeyAction,
|
||||
#[strum(serialize = "kms:Decrypt")]
|
||||
DecryptAction,
|
||||
/// Export a KMS backup bundle. Separate from every key action because a
|
||||
/// bundle carries the material of every key at once.
|
||||
#[strum(serialize = "kms:Backup")]
|
||||
BackupAction,
|
||||
/// Preflight or execute a KMS restore.
|
||||
#[strum(serialize = "kms:Restore")]
|
||||
RestoreAction,
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
@@ -767,6 +774,8 @@ mod tests {
|
||||
("kms:ListKeys", KmsAction::ListKeysAction),
|
||||
("kms:DescribeKey", KmsAction::DescribeKeyAction),
|
||||
("kms:Decrypt", KmsAction::DecryptAction),
|
||||
("kms:Backup", KmsAction::BackupAction),
|
||||
("kms:Restore", KmsAction::RestoreAction),
|
||||
] {
|
||||
let action = Action::try_from(raw).expect("Should parse KMS action");
|
||||
assert_eq!(action, Action::KmsAction(expected));
|
||||
|
||||
Reference in New Issue
Block a user