api2/tape: add notify_user to backup(-jobs) and restore api calls

so that a user can be given that will be notified for
manual intervention (e.g. inserting a tape)

Signed-off-by: Dominik Csapak <d.csapak@proxmox.com>
This commit is contained in:
Dominik Csapak 2021-03-05 14:10:19 +01:00 committed by Dietmar Maurer
parent be8adca115
commit c9793d47f9
5 changed files with 33 additions and 10 deletions

View File

@ -31,6 +31,7 @@ use crate::{
}, },
}, },
server::{ server::{
lookup_user_email,
jobstate::{ jobstate::{
Job, Job,
JobState, JobState,
@ -47,6 +48,7 @@ use crate::{
UPID_SCHEMA, UPID_SCHEMA,
JOB_ID_SCHEMA, JOB_ID_SCHEMA,
MediaPoolConfig, MediaPoolConfig,
Userid,
}, },
server::WorkerTask, server::WorkerTask,
task::TaskState, task::TaskState,
@ -350,7 +352,10 @@ fn backup_worker(
let pool = MediaPool::with_config(status_path, &pool_config, changer_name)?; let pool = MediaPool::with_config(status_path, &pool_config, changer_name)?;
let mut pool_writer = PoolWriter::new(pool, &setup.drive, worker)?; let notify_user = setup.notify_user.as_ref().unwrap_or_else(|| &Userid::root_userid());
let email = lookup_user_email(notify_user);
let mut pool_writer = PoolWriter::new(pool, &setup.drive, worker, email)?;
let mut group_list = BackupInfo::list_backup_groups(&datastore.base_path())?; let mut group_list = BackupInfo::list_backup_groups(&datastore.base_path())?;

View File

@ -33,6 +33,7 @@ use crate::{
DRIVE_NAME_SCHEMA, DRIVE_NAME_SCHEMA,
UPID_SCHEMA, UPID_SCHEMA,
Authid, Authid,
Userid,
}, },
config::{ config::{
self, self,
@ -55,7 +56,10 @@ use crate::{
DynamicIndexReader, DynamicIndexReader,
FixedIndexReader, FixedIndexReader,
}, },
server::WorkerTask, server::{
lookup_user_email,
WorkerTask,
},
tape::{ tape::{
TAPE_STATUS_DIR, TAPE_STATUS_DIR,
TapeRead, TapeRead,
@ -97,6 +101,10 @@ pub const ROUTER: Router = Router::new()
description: "Media set UUID.", description: "Media set UUID.",
type: String, type: String,
}, },
"notify-user": {
type: Userid,
optional: true,
},
}, },
}, },
returns: { returns: {
@ -114,6 +122,7 @@ pub fn restore(
store: String, store: String,
drive: String, drive: String,
media_set: String, media_set: String,
notify_user: Option<Userid>,
rpcenv: &mut dyn RpcEnvironment, rpcenv: &mut dyn RpcEnvironment,
) -> Result<Value, Error> { ) -> Result<Value, Error> {
@ -212,6 +221,7 @@ pub fn restore(
&drive, &drive,
&datastore, &datastore,
&auth_id, &auth_id,
&notify_user,
)?; )?;
} }
@ -241,6 +251,7 @@ pub fn request_and_restore_media(
drive_name: &str, drive_name: &str,
datastore: &DataStore, datastore: &DataStore,
authid: &Authid, authid: &Authid,
notify_user: &Option<Userid>,
) -> Result<(), Error> { ) -> Result<(), Error> {
let media_set_uuid = match media_id.media_set_label { let media_set_uuid = match media_id.media_set_label {
@ -248,7 +259,12 @@ pub fn request_and_restore_media(
Some(ref set) => &set.uuid, Some(ref set) => &set.uuid,
}; };
let (mut drive, info) = request_and_load_media(worker, &drive_config, &drive_name, &media_id.label)?; let email = notify_user
.as_ref()
.and_then(|userid| lookup_user_email(userid))
.or_else(|| lookup_user_email(&authid.clone().into()));
let (mut drive, info) = request_and_load_media(worker, &drive_config, &drive_name, &media_id.label, &email)?;
match info.media_set_label { match info.media_set_label {
None => { None => {

View File

@ -397,7 +397,7 @@ pub fn send_updates_available(
} }
/// Lookup users email address /// Lookup users email address
fn lookup_user_email(userid: &Userid) -> Option<String> { pub fn lookup_user_email(userid: &Userid) -> Option<String> {
use crate::config::user::{self, User}; use crate::config::user::{self, User};

View File

@ -319,6 +319,7 @@ pub fn request_and_load_media(
config: &SectionConfigData, config: &SectionConfigData,
drive: &str, drive: &str,
label: &MediaLabel, label: &MediaLabel,
notify_email: &Option<String>,
) -> Result<( ) -> Result<(
Box<dyn TapeDriver>, Box<dyn TapeDriver>,
MediaId, MediaId,
@ -375,9 +376,6 @@ pub fn request_and_load_media(
return Ok((handle, media_id)); return Ok((handle, media_id));
} }
let to = "root@localhost"; // fixme
let mut last_media_uuid = None; let mut last_media_uuid = None;
let mut last_error = None; let mut last_error = None;
@ -390,7 +388,9 @@ pub fn request_and_load_media(
if tried { if tried {
if let Some(reason) = failure_reason { if let Some(reason) = failure_reason {
task_log!(worker, "Please insert media '{}' into drive '{}'", label_text, drive); task_log!(worker, "Please insert media '{}' into drive '{}'", label_text, drive);
send_load_media_email(drive, &label_text, to, Some(reason))?; if let Some(to) = notify_email {
send_load_media_email(drive, &label_text, to, Some(reason))?;
}
} }
failure_reason = None; failure_reason = None;

View File

@ -64,11 +64,12 @@ pub struct PoolWriter {
drive_name: String, drive_name: String,
status: Option<PoolWriterState>, status: Option<PoolWriterState>,
media_set_catalog: MediaSetCatalog, media_set_catalog: MediaSetCatalog,
notify_email: Option<String>,
} }
impl PoolWriter { impl PoolWriter {
pub fn new(mut pool: MediaPool, drive_name: &str, worker: &WorkerTask) -> Result<Self, Error> { pub fn new(mut pool: MediaPool, drive_name: &str, worker: &WorkerTask, notify_email: Option<String>) -> Result<Self, Error> {
let current_time = proxmox::tools::time::epoch_i64(); let current_time = proxmox::tools::time::epoch_i64();
@ -101,6 +102,7 @@ impl PoolWriter {
drive_name: drive_name.to_string(), drive_name: drive_name.to_string(),
status: None, status: None,
media_set_catalog, media_set_catalog,
notify_email,
}) })
} }
@ -227,7 +229,7 @@ impl PoolWriter {
let (drive_config, _digest) = crate::config::drive::config()?; let (drive_config, _digest) = crate::config::drive::config()?;
let (mut drive, old_media_id) = let (mut drive, old_media_id) =
request_and_load_media(worker, &drive_config, &self.drive_name, media.label())?; request_and_load_media(worker, &drive_config, &self.drive_name, media.label(), &self.notify_email)?;
// test for critical tape alert flags // test for critical tape alert flags
if let Ok(alert_flags) = drive.tape_alert_flags() { if let Ok(alert_flags) = drive.tape_alert_flags() {