tape: implement MediaPool flag to consider offline media
For standalone tape drives.
This commit is contained in:
		| @ -109,9 +109,11 @@ fn backup_worker( | |||||||
|     let _lock = MediaPool::lock(status_path, &pool_config.name)?; |     let _lock = MediaPool::lock(status_path, &pool_config.name)?; | ||||||
|  |  | ||||||
|     worker.log("update media online status"); |     worker.log("update media online status"); | ||||||
|     update_media_online_status(&pool_config.drive)?; |     let has_changer = update_media_online_status(&pool_config.drive)?; | ||||||
|  |  | ||||||
|     let pool = MediaPool::with_config(status_path, &pool_config)?; |     let use_offline_media = !has_changer; | ||||||
|  |  | ||||||
|  |     let pool = MediaPool::with_config(status_path, &pool_config, use_offline_media)?; | ||||||
|  |  | ||||||
|     let mut pool_writer = PoolWriter::new(pool, &pool_config.drive)?; |     let mut pool_writer = PoolWriter::new(pool, &pool_config.drive)?; | ||||||
|  |  | ||||||
| @ -138,12 +140,16 @@ fn backup_worker( | |||||||
| } | } | ||||||
|  |  | ||||||
| // Try to update the the media online status | // Try to update the the media online status | ||||||
| fn update_media_online_status(drive: &str) -> Result<(), Error> { | fn update_media_online_status(drive: &str) -> Result<bool, Error> { | ||||||
|  |  | ||||||
|     let (config, _digest) = config::drive::config()?; |     let (config, _digest) = config::drive::config()?; | ||||||
|  |  | ||||||
|  |     let mut has_changer = false; | ||||||
|  |  | ||||||
|     if let Ok(Some((changer, changer_name))) = media_changer(&config, drive) { |     if let Ok(Some((changer, changer_name))) = media_changer(&config, drive) { | ||||||
|  |  | ||||||
|  |         has_changer = true; | ||||||
|  |  | ||||||
|         let changer_id_list = changer.list_media_changer_ids()?; |         let changer_id_list = changer.list_media_changer_ids()?; | ||||||
|  |  | ||||||
|         let status_path = Path::new(TAPE_STATUS_DIR); |         let status_path = Path::new(TAPE_STATUS_DIR); | ||||||
| @ -159,7 +165,7 @@ fn update_media_online_status(drive: &str) -> Result<(), Error> { | |||||||
|         )?; |         )?; | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     Ok(()) |     Ok(has_changer) | ||||||
| } | } | ||||||
|  |  | ||||||
| pub fn backup_snapshot( | pub fn backup_snapshot( | ||||||
|  | |||||||
| @ -81,7 +81,8 @@ pub async fn list_media(pool: Option<String>) -> Result<Vec<MediaListEntry>, Err | |||||||
|  |  | ||||||
|         let config: MediaPoolConfig = config.lookup("pool", pool_name)?; |         let config: MediaPoolConfig = config.lookup("pool", pool_name)?; | ||||||
|  |  | ||||||
|         let pool = MediaPool::with_config(status_path, &config)?; |         let use_offline_media = true; // does not matter here | ||||||
|  |         let pool = MediaPool::with_config(status_path, &config, use_offline_media)?; | ||||||
|  |  | ||||||
|         let current_time = proxmox::tools::time::epoch_i64(); |         let current_time = proxmox::tools::time::epoch_i64(); | ||||||
|  |  | ||||||
|  | |||||||
| @ -44,6 +44,7 @@ pub struct MediaPool { | |||||||
|  |  | ||||||
|     media_set_policy: MediaSetPolicy, |     media_set_policy: MediaSetPolicy, | ||||||
|     retention: RetentionPolicy, |     retention: RetentionPolicy, | ||||||
|  |     use_offline_media: bool, | ||||||
|  |  | ||||||
|     inventory: Inventory, |     inventory: Inventory, | ||||||
|     state_db: MediaStateDatabase, |     state_db: MediaStateDatabase, | ||||||
| @ -59,6 +60,7 @@ impl MediaPool { | |||||||
|         state_path: &Path, |         state_path: &Path, | ||||||
|         media_set_policy: MediaSetPolicy, |         media_set_policy: MediaSetPolicy, | ||||||
|         retention: RetentionPolicy, |         retention: RetentionPolicy, | ||||||
|  |         use_offline_media: bool, | ||||||
|      ) -> Result<Self, Error> { |      ) -> Result<Self, Error> { | ||||||
|  |  | ||||||
|         let inventory = Inventory::load(state_path)?; |         let inventory = Inventory::load(state_path)?; | ||||||
| @ -74,6 +76,7 @@ impl MediaPool { | |||||||
|             name: String::from(name), |             name: String::from(name), | ||||||
|             media_set_policy, |             media_set_policy, | ||||||
|             retention, |             retention, | ||||||
|  |             use_offline_media, | ||||||
|             inventory, |             inventory, | ||||||
|             state_db, |             state_db, | ||||||
|             current_media_set, |             current_media_set, | ||||||
| @ -84,13 +87,14 @@ impl MediaPool { | |||||||
|     pub fn with_config( |     pub fn with_config( | ||||||
|         state_path: &Path, |         state_path: &Path, | ||||||
|         config: &MediaPoolConfig, |         config: &MediaPoolConfig, | ||||||
|  |         use_offline_media: bool, | ||||||
|     ) -> Result<Self, Error> { |     ) -> Result<Self, Error> { | ||||||
|  |  | ||||||
|         let allocation = config.allocation.clone().unwrap_or(String::from("continue")).parse()?; |         let allocation = config.allocation.clone().unwrap_or(String::from("continue")).parse()?; | ||||||
|  |  | ||||||
|         let retention = config.retention.clone().unwrap_or(String::from("keep")).parse()?; |         let retention = config.retention.clone().unwrap_or(String::from("keep")).parse()?; | ||||||
|  |  | ||||||
|         MediaPool::new(&config.name, state_path, allocation, retention) |         MediaPool::new(&config.name, state_path, allocation, retention, use_offline_media) | ||||||
|     } |     } | ||||||
|  |  | ||||||
|     /// Returns the pool name |     /// Returns the pool name | ||||||
| @ -272,7 +276,14 @@ impl MediaPool { | |||||||
|  |  | ||||||
|             // check if media is on site |             // check if media is on site | ||||||
|             match media.location() { |             match media.location() { | ||||||
|                 MediaLocation::Online(_) | MediaLocation::Offline => { /* OK */ }, |                 MediaLocation::Online(_) => { /* OK */ }, | ||||||
|  |                 MediaLocation::Offline => { | ||||||
|  |                     if self.use_offline_media { | ||||||
|  |                         /* OK */ | ||||||
|  |                     } else { | ||||||
|  |                         continue; | ||||||
|  |                     } | ||||||
|  |                 }, | ||||||
|                 MediaLocation::Vault(_) => continue, |                 MediaLocation::Vault(_) => continue, | ||||||
|             } |             } | ||||||
|  |  | ||||||
| @ -380,9 +391,15 @@ impl MediaPool { | |||||||
|             match media.status() { |             match media.status() { | ||||||
|                 MediaStatus::Full => { /* OK */ }, |                 MediaStatus::Full => { /* OK */ }, | ||||||
|                 MediaStatus::Writable if (seq + 1) == media_count =>  { |                 MediaStatus::Writable if (seq + 1) == media_count =>  { | ||||||
|                     last_is_writable = true; |  | ||||||
|                     match media.location() { |                     match media.location() { | ||||||
|                         MediaLocation::Online(_) | MediaLocation::Offline => { /* OK */ }, |                         MediaLocation::Online(_) => { | ||||||
|  |                             last_is_writable = true; | ||||||
|  |                         }, | ||||||
|  |                         MediaLocation::Offline => { | ||||||
|  |                             if self.use_offline_media { | ||||||
|  |                                 last_is_writable = true; | ||||||
|  |                             } | ||||||
|  |                         } | ||||||
|                         MediaLocation::Vault(vault) => { |                         MediaLocation::Vault(vault) => { | ||||||
|                             bail!("writable media offsite in vault '{}'", vault); |                             bail!("writable media offsite in vault '{}'", vault); | ||||||
|                         } |                         } | ||||||
| @ -465,7 +482,7 @@ impl BackupMedia { | |||||||
|     pub fn set_media_set_label(&mut self, set_label: MediaSetLabel) { |     pub fn set_media_set_label(&mut self, set_label: MediaSetLabel) { | ||||||
|         self.id.media_set_label = Some(set_label); |         self.id.media_set_label = Some(set_label); | ||||||
|     } |     } | ||||||
|      |  | ||||||
|     /// Returns the drive label |     /// Returns the drive label | ||||||
|     pub fn label(&self) -> &MediaLabel { |     pub fn label(&self) -> &MediaLabel { | ||||||
|         &self.id.label |         &self.id.label | ||||||
|  | |||||||
		Reference in New Issue
	
	Block a user