[pbs-devel] [PATCH proxmox-backup] fix #4719: wait for tape to be available in changer
Dominik Csapak
d.csapak at proxmox.com
Mon May 8 13:03:41 CEST 2023
instead of aborting. If the tape is currently e.g. offline, in an
import/export slot or in the wrong drive, this gives the user the chance to
manually move it/insert it, so that the backup job can continue.
Send an e-mail like we do on a standalone drive, but adapt the messages
to contain the changer instead of the drive.
This can help when not all tapes are currently available in the changer.
Signed-off-by: Dominik Csapak <d.csapak at proxmox.com>
---
src/server/email_notifications.rs | 19 ++++++----
src/tape/drive/mod.rs | 59 +++++++++++++++++++------------
2 files changed, 49 insertions(+), 29 deletions(-)
diff --git a/src/server/email_notifications.rs b/src/server/email_notifications.rs
index 1224191c..27b638bb 100644
--- a/src/server/email_notifications.rs
+++ b/src/server/email_notifications.rs
@@ -540,27 +540,34 @@ pub fn send_tape_backup_status(
/// Send email to a person to request a manual media change
pub fn send_load_media_email(
- drive: &str,
+ changer: bool,
+ device: &str,
label_text: &str,
to: &str,
reason: Option<String>,
) -> Result<(), Error> {
use std::fmt::Write as _;
- let subject = format!("Load Media '{label_text}' request for drive '{drive}'");
+ let device_type = if changer { "changer" } else { "drive" };
+
+ let subject = format!("Load Media '{label_text}' request for {device_type} '{device}'");
let mut text = String::new();
if let Some(reason) = reason {
let _ = write!(
text,
- "The drive has the wrong or no tape inserted. Error:\n{reason}\n\n"
+ "The {device_type} has the wrong or no tape(s) inserted. Error:\n{reason}\n\n"
);
}
- text.push_str("Please insert the requested media into the backup drive.\n\n");
-
- let _ = writeln!(text, "Drive: {drive}");
+ if changer {
+ text.push_str("Please insert the requested media into the changer.\n\n");
+ let _ = writeln!(text, "Changer: {device}");
+ } else {
+ text.push_str("Please insert the requested media into the backup drive.\n\n");
+ let _ = writeln!(text, "Drive: {device}");
+ }
let _ = writeln!(text, "Media: {label_text}");
send_job_status_mail(to, &subject, &text)
diff --git a/src/tape/drive/mod.rs b/src/tape/drive/mod.rs
index c69ebc63..86f01201 100644
--- a/src/tape/drive/mod.rs
+++ b/src/tape/drive/mod.rs
@@ -298,6 +298,7 @@ enum TapeRequestError {
OpenFailed(String),
WrongLabel(String),
ReadFailed(String),
+ LoadingFailed(String),
}
impl std::fmt::Display for TapeRequestError {
@@ -321,6 +322,9 @@ impl std::fmt::Display for TapeRequestError {
TapeRequestError::ReadFailed(reason) => {
write!(f, "tape read failed - {}", reason)
}
+ TapeRequestError::LoadingFailed(reason) => {
+ write!(f, "could not load tape into drive - {}", reason)
+ }
}
}
}
@@ -374,40 +378,31 @@ pub fn request_and_load_media(
let label_text = label.label_text.clone();
- if drive_config.changer.is_some() {
- task_log!(
- worker,
- "loading media '{}' into drive '{}'",
- label_text,
- drive
- );
-
- let mut changer = MtxMediaChanger::with_drive_config(&drive_config)?;
- changer.load_media(&label_text)?;
-
- let mut handle: Box<dyn TapeDriver> =
- Box::new(open_lto_tape_drive(&drive_config)?);
-
- let media_id = check_label(handle.as_mut(), &label.uuid)?;
-
- return Ok((handle, media_id));
- }
-
let mut last_error = TapeRequestError::None;
+ let changer = &drive_config.changer;
+
let update_and_log_request_error =
|old: &mut TapeRequestError, new: TapeRequestError| -> Result<(), Error> {
if new != *old {
task_log!(worker, "{}", new);
+ let (device_type, device) = if let Some(changer) = changer {
+ ("changer", changer.as_str())
+ } else {
+ ("drive", drive)
+ };
+
task_log!(
worker,
- "Please insert media '{}' into drive '{}'",
+ "Please insert media '{}' into {} '{}'",
label_text,
- drive
+ device_type,
+ device
);
if let Some(to) = notify_email {
send_load_media_email(
- drive,
+ changer.is_some(),
+ device,
&label_text,
to,
Some(new.to_string()),
@@ -427,13 +422,31 @@ pub fn request_and_load_media(
worker.check_abort()?;
std::thread::sleep(std::time::Duration::from_millis(100));
}
- } else {
+ } else if drive_config.changer.is_none() {
task_log!(
worker,
"Checking for media '{}' in drive '{}'",
label_text,
drive
);
+ } else {
+ task_log!(
+ worker,
+ "trying to load media '{}' into drive '{}'",
+ label_text,
+ drive
+ );
+ }
+
+ if drive_config.changer.is_some() {
+ let mut changer = MtxMediaChanger::with_drive_config(&drive_config)?;
+ if let Err(err) = changer.load_media(&label_text) {
+ update_and_log_request_error(
+ &mut last_error,
+ TapeRequestError::LoadingFailed(err.to_string()),
+ )?;
+ continue;
+ }
}
let mut handle = match open_lto_tape_drive(&drive_config) {
--
2.30.2
More information about the pbs-devel
mailing list