api: list datastore: avoid iterating over NS for priv check, use AclTree
Make the assumption that if a user has any privilege that would make an NS and (parts) of its content visible they also should be able to know about the datastore and very basic errors on lookup (path existence and maintenance mode) even if that NS doesn't even exists (yet), as they could, e.g., make or view a backup and find out anyway. This avoids iterating over parts of the whole datastore folder tree on disk, doing a priv check on each, swapping IO to virtual in memory checks on info we got available already anyway, is always a good idea after all Signed-off-by: Thomas Lamprecht <t.lamprecht@proxmox.com>
This commit is contained in:
parent
2c69b69108
commit
8c9c6c0755
|
@ -64,7 +64,7 @@ use crate::api2::backup::optional_ns_param;
|
||||||
use crate::api2::node::rrd::create_value_from_rrd;
|
use crate::api2::node::rrd::create_value_from_rrd;
|
||||||
use crate::backup::{
|
use crate::backup::{
|
||||||
can_access_any_namespace, check_ns_privs_full, verify_all_backups, verify_backup_dir,
|
can_access_any_namespace, check_ns_privs_full, verify_all_backups, verify_backup_dir,
|
||||||
verify_backup_group, verify_filter, ListAccessibleBackupGroups,
|
verify_backup_group, verify_filter, ListAccessibleBackupGroups, NS_PRIVS_OK,
|
||||||
};
|
};
|
||||||
|
|
||||||
use crate::server::jobstate::Job;
|
use crate::server::jobstate::Job;
|
||||||
|
@ -1188,16 +1188,15 @@ pub fn get_datastore_list(
|
||||||
let mut list = Vec::new();
|
let mut list = Vec::new();
|
||||||
|
|
||||||
for (store, (_, data)) in &config.sections {
|
for (store, (_, data)) in &config.sections {
|
||||||
let user_privs = user_info.lookup_privs(&auth_id, &["datastore", store]);
|
let acl_path = &["datastore", store];
|
||||||
|
let user_privs = user_info.lookup_privs(&auth_id, acl_path);
|
||||||
let allowed = (user_privs & (PRIV_DATASTORE_AUDIT | PRIV_DATASTORE_BACKUP)) != 0;
|
let allowed = (user_privs & (PRIV_DATASTORE_AUDIT | PRIV_DATASTORE_BACKUP)) != 0;
|
||||||
|
|
||||||
let mut allow_id = false;
|
let mut allow_id = false;
|
||||||
if !allowed {
|
if !allowed {
|
||||||
if let Ok(datastore) = DataStore::lookup_datastore(store, Some(Operation::Read)) {
|
if let Ok(any_privs) = user_info.any_privs_below(&auth_id, acl_path, NS_PRIVS_OK) {
|
||||||
allow_id = can_access_any_namespace(datastore, &auth_id, &user_info);
|
allow_id = any_privs;
|
||||||
}
|
}
|
||||||
// FIXME: check for any ACL on the datastore below in the error case, otherwise offline
|
|
||||||
// datastore will disappear for users that can only access a specific namespace
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if allowed || allow_id {
|
if allowed || allow_id {
|
||||||
|
|
Loading…
Reference in New Issue