From 22b68016f791958baf7dd982cb92d2306f0e1574 Mon Sep 17 00:00:00 2001 From: Aaron Lauterer Date: Thu, 26 Aug 2021 12:03:32 +0200 Subject: [PATCH] Ceph: add keyring parameter for external clusters By adding the keyring for RBD storage or the secret for CephFS ones, it is possible to add an external Ceph cluster with only one API call. Previously the keyring / secret file needed to be placed in /etc/pve/priv/ceph/$storeID.{keyring,secret} manually. Signed-off-by: Aaron Lauterer --- PVE/API2/Storage/Config.pm | 2 +- PVE/CLI/pvesm.pm | 12 ++++++++++-- PVE/Storage/CephFSPlugin.pm | 22 ++++++++++++++++------ PVE/Storage/RBDPlugin.pm | 26 ++++++++++++++++++++------ 4 files changed, 47 insertions(+), 15 deletions(-) diff --git a/PVE/API2/Storage/Config.pm b/PVE/API2/Storage/Config.pm index ea655c5..bf38df3 100755 --- a/PVE/API2/Storage/Config.pm +++ b/PVE/API2/Storage/Config.pm @@ -112,7 +112,7 @@ __PACKAGE__->register_method ({ return &$api_storage_config($cfg, $param->{storage}); }}); -my $sensitive_params = [qw(password encryption-key master-pubkey)]; +my $sensitive_params = [qw(password encryption-key master-pubkey keyring)]; __PACKAGE__->register_method ({ name => 'create', diff --git a/PVE/CLI/pvesm.pm b/PVE/CLI/pvesm.pm index 668170a..190de91 100755 --- a/PVE/CLI/pvesm.pm +++ b/PVE/CLI/pvesm.pm @@ -64,13 +64,21 @@ sub param_mapping { } }; + my $keyring_map = { + name => 'keyring', + desc => 'file containing the keyring to authenticate in the Ceph cluster', + func => sub { + my ($value) = @_; + return PVE::Tools::file_get_contents($value); + }, + }; my $mapping = { 'cifsscan' => [ $password_map ], 'cifs' => [ $password_map ], 'pbs' => [ $password_map ], - 'create' => [ $password_map, $enc_key_map, $master_key_map ], - 'update' => [ $password_map, $enc_key_map, $master_key_map ], + 'create' => [ $password_map, $enc_key_map, $master_key_map, $keyring_map ], + 'update' => [ $password_map, $enc_key_map, $master_key_map, $keyring_map ], }; return $mapping->{$name}; } diff --git a/PVE/Storage/CephFSPlugin.pm b/PVE/Storage/CephFSPlugin.pm index 2aaa450..3b9a791 100644 --- a/PVE/Storage/CephFSPlugin.pm +++ b/PVE/Storage/CephFSPlugin.pm @@ -146,6 +146,7 @@ sub options { fuse => { optional => 1 }, bwlimit => { optional => 1 }, maxfiles => { optional => 1 }, + keyring => { optional => 1 }, 'prune-backups' => { optional => 1 }, }; } @@ -163,20 +164,29 @@ sub check_config { sub on_add_hook { my ($class, $storeid, $scfg, %param) = @_; - return if defined($scfg->{monhost}); # nothing to do if not pve managed ceph + my $secret = $param{keyring} if defined $param{keyring} // undef; + PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid, $secret); - PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid); + return; +} + +sub on_update_hook { + my ($class, $storeid, $scfg, %param) = @_; + + if (exists($param{keyring})) { + if (defined($param{keyring})) { + PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid, $param{keyring}); + } else { + PVE::CephConfig::ceph_remove_keyfile($scfg->{type}, $storeid); + } + } return; } sub on_delete_hook { my ($class, $storeid, $scfg) = @_; - - return if defined($scfg->{monhost}); # nothing to do if not pve managed ceph - PVE::CephConfig::ceph_remove_keyfile($scfg->{type}, $storeid); - return; } diff --git a/PVE/Storage/RBDPlugin.pm b/PVE/Storage/RBDPlugin.pm index a8d1243..4bd43d5 100644 --- a/PVE/Storage/RBDPlugin.pm +++ b/PVE/Storage/RBDPlugin.pm @@ -305,6 +305,10 @@ sub properties { description => "Always access rbd through krbd kernel module.", type => 'boolean', }, + keyring => { + description => "Client keyring contents (for external clusters).", + type => 'string', + }, }; } @@ -318,6 +322,7 @@ sub options { username => { optional => 1 }, content => { optional => 1 }, krbd => { optional => 1 }, + keyring => { optional => 1 }, bwlimit => { optional => 1 }, }; } @@ -327,20 +332,29 @@ sub options { sub on_add_hook { my ($class, $storeid, $scfg, %param) = @_; - return if defined($scfg->{monhost}); # nothing to do if not pve managed ceph + my $secret = $param{keyring} if defined $param{keyring} // undef; + PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid, $secret); - PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid); + return; +} + +sub on_update_hook { + my ($class, $storeid, $scfg, %param) = @_; + + if (exists($param{keyring})) { + if (defined($param{keyring})) { + PVE::CephConfig::ceph_create_keyfile($scfg->{type}, $storeid, $param{keyring}); + } else { + PVE::CephConfig::ceph_remove_keyfile($scfg->{type}, $storeid); + } + } return; } sub on_delete_hook { my ($class, $storeid, $scfg) = @_; - - return if defined($scfg->{monhost}); # nothing to do if not pve managed ceph - PVE::CephConfig::ceph_remove_keyfile($scfg->{type}, $storeid); - return; }