1pub mod cfs;
2pub mod ims;
3
4use std::{collections::HashMap, str::FromStr};
5
6use serde::{Deserialize, Serialize};
7use serde_json::Value;
8use strum_macros::{AsRefStr, Display, EnumIter, EnumString, IntoStaticStr};
9
10use crate::error::Error;
11
12#[derive(Serialize, Deserialize, Debug)]
13pub enum K8sAuth {
14 Native {
15 certificate_authority_data: String,
16 client_certificate_data: String,
17 client_key_data: String,
18 },
19 Vault {
20 base_url: String,
21 secret_path: String,
22 role_id: String,
23 },
24}
25
26#[derive(Serialize, Deserialize, Debug)]
27pub struct K8sDetails {
28 pub api_url: String,
29 pub authentication: K8sAuth,
30}
31
32#[derive(
34 Debug, EnumIter, EnumString, IntoStaticStr, AsRefStr, Display, Serialize, Deserialize, Clone,
35)]
36pub enum ArtifactType {
37 Memory,
38 Processor,
39 NodeAccel,
40 NodeHsnNic,
41 Drive,
42 CabinetPDU,
43 CabinetPDUPowerConnector,
44 CMMRectifier,
45 NodeAccelRiser,
46 NodeEnclosurePowerSupplie,
47 NodeBMC,
48 RouterBMC,
49}
50
51#[derive(Debug, Serialize, Deserialize, Clone)]
52pub struct NodeSummary {
53 pub xname: String,
54 pub r#type: String,
55 pub processors: Vec<ArtifactSummary>,
56 pub memory: Vec<ArtifactSummary>,
57 pub node_accels: Vec<ArtifactSummary>,
58 pub node_hsn_nics: Vec<ArtifactSummary>,
59}
60
61impl From<HWInvByLocNode> for NodeSummary {
207 fn from(value: HWInvByLocNode) -> Self {
208 NodeSummary {
209 xname: value.id,
210 r#type: value.r#type.unwrap_or_default(),
211 processors: value
212 .processors
213 .unwrap_or_default()
214 .into_iter()
215 .map(ArtifactSummary::from)
216 .collect(),
217 memory: value
219 .memory
220 .unwrap_or_default()
221 .into_iter()
222 .map(ArtifactSummary::from)
223 .collect(),
224 node_accels: value
226 .node_accels
227 .unwrap_or_default()
228 .into_iter()
229 .map(ArtifactSummary::from)
230 .collect(),
231 node_hsn_nics: value
233 .node_hsn_nics
234 .unwrap_or_default()
235 .into_iter()
236 .map(ArtifactSummary::from)
237 .collect(),
238 }
240 }
241}
242
243impl Into<HWInvByLocNode> for NodeSummary {
244 fn into(self) -> HWInvByLocNode {
245 let redfish_system_fru_info = RedfishSystemFRUInfo {
246 asset_tag: None,
247 bios_version: None,
248 model: None,
249 manufacturer: None,
250 part_number: None,
251 serial_number: None,
252 sku: None,
253 system_type: None,
254 uuid: None,
255 };
256
257 let hw_inv_by_fr_node = HWInvByFRUNode {
258 fru_id: None,
259 r#type: None,
260 fru_sub_type: None,
261 hw_inventory_by_fru_type: self.r#type.clone(),
262 node_fru_info: redfish_system_fru_info,
263 };
264
265 HWInvByLocNode {
266 id: self.xname,
267 r#type: Some(self.r#type.clone()),
268 ordinal: None,
269 status: None,
270 hw_inventory_by_location_type: self.r#type,
271 populated_fru: Some(hw_inv_by_fr_node),
272 node_location_info: None,
273 processors: Some(
274 self.processors
275 .into_iter()
276 .map(|processor| processor.into())
277 .collect(),
278 ),
279 node_accels: Some(
280 self.node_accels
281 .into_iter()
282 .map(|node_accel| node_accel.into())
283 .collect(),
284 ),
285 drives: None,
286 memory: Some(
287 self.memory
288 .into_iter()
289 .map(|memory| memory.into())
290 .collect(),
291 ),
292 node_accel_risers: None,
293 node_hsn_nics: Some(
294 self.node_hsn_nics
295 .into_iter()
296 .map(|node_hsn_nic| node_hsn_nic.into())
297 .collect(),
298 ),
299 }
300 }
301}
302
303impl NodeSummary {
304 pub fn from_csm_value(hw_artifact_value: Value) -> Self {
305 let processors = hw_artifact_value["Processors"]
306 .as_array()
307 .unwrap_or(&Vec::new())
308 .iter()
309 .map(|processor_value| ArtifactSummary::from_processor_value(processor_value.clone()))
310 .collect();
311
312 let memory = hw_artifact_value["Memory"]
313 .as_array()
314 .unwrap_or(&Vec::new())
315 .iter()
316 .map(|memory_value| ArtifactSummary::from_memory_value(memory_value.clone()))
317 .collect();
318
319 let node_accels = hw_artifact_value["NodeAccels"]
320 .as_array()
321 .unwrap_or(&Vec::new())
322 .iter()
323 .map(|nodeaccel_value| ArtifactSummary::from_nodeaccel_value(nodeaccel_value.clone()))
324 .collect();
325
326 let node_hsn_nics = hw_artifact_value["NodeHsnNics"]
327 .as_array()
328 .unwrap_or(&Vec::new())
329 .iter()
330 .map(|nodehsnnic_value| {
331 ArtifactSummary::from_nodehsnnics_value(nodehsnnic_value.clone())
332 })
333 .collect();
334
335 Self {
336 xname: hw_artifact_value["ID"].as_str().unwrap().to_string(),
337 r#type: hw_artifact_value["Type"].as_str().unwrap().to_string(),
338 processors,
339 memory,
340 node_accels,
341 node_hsn_nics,
342 }
343 }
344}
345
346#[derive(Debug, Serialize, Deserialize, Clone)]
347pub struct ArtifactSummary {
348 pub xname: String,
349 pub r#type: ArtifactType,
350 pub info: Option<String>,
351}
352
353impl From<HWInvByLocProcessor> for ArtifactSummary {
354 fn from(value: HWInvByLocProcessor) -> Self {
355 ArtifactSummary {
356 xname: value.id,
357 r#type: ArtifactType::from_str(value.r#type.unwrap().as_str()).unwrap(),
358 info: value.populated_fru.and_then(|hw_inv_by_fru_processor| {
359 hw_inv_by_fru_processor.processor_fru_info.model
360 }),
361 }
362 }
363}
364
365impl Into<HWInvByLocProcessor> for ArtifactSummary {
366 fn into(self) -> HWInvByLocProcessor {
367 let redfish_process_fru_info = RedfishProcessorFRUInfo {
368 instruction_set: None,
369 manufacturer: None,
370 max_speed_mhz: None,
371 model: self.info,
372 processor_architecture: None,
373 processor_id: None,
374 processor_type: None,
375 total_cores: None,
376 total_threads: None,
377 };
378
379 let hw_inv_by_fru_processor = HWInvByFRUProcessor {
380 fru_id: None,
381 r#type: Some(self.r#type.to_string()),
382 fru_sub_type: None,
383 hw_inventory_by_fru_type: self.r#type.to_string(),
384 processor_fru_info: redfish_process_fru_info,
385 };
386
387 let processor_location_info = RedfishProcessorLocationInfo {
388 id: None,
389 name: None,
390 description: None,
391 socket: None,
392 };
393
394 HWInvByLocProcessor {
395 id: self.xname,
396 r#type: Some(self.r#type.to_string()),
397 ordinal: None,
398 status: None,
399 hw_inventory_by_location_type: self.r#type.to_string(),
400 populated_fru: Some(hw_inv_by_fru_processor),
401 processor_location_info,
402 }
403 }
404}
405
406impl From<HWInvByLocMemory> for ArtifactSummary {
407 fn from(value: HWInvByLocMemory) -> Self {
408 ArtifactSummary {
409 xname: value.id,
410 r#type: ArtifactType::from_str(value.r#type.unwrap().as_str()).unwrap(),
411 info: value.populated_fru.and_then(|hw_inv_by_fru_memory| {
412 hw_inv_by_fru_memory
413 .memory_fru_info
414 .capacity_mib
415 .map(|capacity_mib| capacity_mib.to_string())
416 }),
417 }
418 }
419}
420
421impl Into<HWInvByLocMemory> for ArtifactSummary {
422 fn into(self) -> HWInvByLocMemory {
423 let redfish_memory_fru_info = RedfishMemoryFRUInfo {
424 base_module_type: None,
425 bus_width_bits: None,
426 capacity_mib: self.info.map(|info| usize::from_str(&info).unwrap_or(0)), data_width_bits: None,
429 error_correction: None,
430 manufacturer: None,
431 memory_type: None,
432 memory_device_type: None,
433 operating_speed_mhz: None,
434 part_number: None,
435 rank_count: None,
436 serial_number: None,
437 };
438
439 let hw_inv_by_fru_memory = HWInvByFRUMemory {
440 fru_id: None,
441 r#type: Some(self.r#type.to_string()),
442 fru_sub_type: None,
443 hw_inventory_by_fru_type: self.r#type.to_string(),
444 memory_fru_info: redfish_memory_fru_info,
445 };
446
447 let memory_location = MemoryLocation {
448 socket: None,
449 memory_controller: None,
450 channel: None,
451 slot: None,
452 };
453
454 let redfish_memory_location_info = RedfishMemoryLocationInfo {
455 id: None,
456 name: None,
457 description: None,
458 memory_location: Some(memory_location),
459 };
460
461 HWInvByLocMemory {
462 id: self.xname,
463 r#type: Some(self.r#type.to_string()),
464 ordinal: None,
465 status: None,
466 hw_inventory_by_location_type: self.r#type.to_string(),
467 populated_fru: Some(hw_inv_by_fru_memory),
468 memory_location_info: redfish_memory_location_info,
469 }
470 }
471}
472
473impl From<HWInvByLocNodeAccel> for ArtifactSummary {
474 fn from(value: HWInvByLocNodeAccel) -> Self {
475 ArtifactSummary {
476 xname: value.id,
477 r#type: ArtifactType::from_str(value.r#type.unwrap().as_str()).unwrap(),
478 info: value.populated_fru.and_then(|hw_inv_by_fru_node_accel| {
479 hw_inv_by_fru_node_accel.node_accel_fru_info.model
480 }),
481 }
482 }
483}
484
485impl Into<HWInvByLocNodeAccel> for ArtifactSummary {
486 fn into(self) -> HWInvByLocNodeAccel {
487 let redfish_processor_fru_info = RedfishProcessorFRUInfo {
490 instruction_set: None,
491 manufacturer: None,
492 max_speed_mhz: None,
493 model: self.info,
494 processor_architecture: None,
495 processor_id: None,
496 processor_type: None,
497 total_cores: None,
498 total_threads: None,
499 };
500
501 let hw_inv_by_fru_node_accel = HWInvByFRUNodeAccel {
502 fru_id: None,
503 r#type: Some(self.r#type.to_string()),
504 fru_sub_type: None,
505 hw_inventory_by_fru_type: self.r#type.to_string(),
506 node_accel_fru_info: redfish_processor_fru_info,
507 };
508
509 HWInvByLocNodeAccel {
510 id: self.xname,
511 r#type: Some(self.r#type.to_string()),
512 ordinal: None,
513 status: None,
514 hw_inventory_by_location_type: self.r#type.to_string(),
515 populated_fru: Some(hw_inv_by_fru_node_accel),
516 node_accel_location_info: None,
517 }
518 }
519}
520
521impl From<HWInvByLocHSNNIC> for ArtifactSummary {
522 fn from(value: HWInvByLocHSNNIC) -> Self {
523 ArtifactSummary {
524 xname: value.id,
525 r#type: ArtifactType::from_str(value.r#type.unwrap().as_str()).unwrap(),
526 info: value
527 .populated_fru
528 .and_then(|hw_inv_by_fru_hsn_nic| hw_inv_by_fru_hsn_nic.hsn_nic_fru_info.model),
529 }
530 }
531}
532
533impl Into<HWInvByLocHSNNIC> for ArtifactSummary {
534 fn into(self) -> HWInvByLocHSNNIC {
535 let hsn_nic_fru_info = HSNNICFRUInfo {
538 manufacturer: None,
539 model: self.info,
540 part_number: None,
541 sku: None,
542 serial_number: None,
543 };
544
545 let hw_inv_by_fru_hsn_nic = HWInvByFRUHSNNIC {
546 fru_id: None,
547 r#type: Some(self.r#type.to_string()),
548 fru_sub_type: None,
549 hw_inventory_by_fru_type: self.r#type.to_string(),
550 hsn_nic_fru_info,
551 };
552
553 let hsn_nic_location_info = HSNNICLocationInfo {
554 id: None,
555 name: None,
556 description: None,
557 };
558
559 HWInvByLocHSNNIC {
560 id: self.xname,
561 r#type: Some(self.r#type.to_string()),
562 ordinal: None,
563 status: None,
564 hw_inventory_by_location_type: self.r#type.to_string(),
565 populated_fru: Some(hw_inv_by_fru_hsn_nic),
566 hsn_nic_location_info,
567 }
568 }
569}
570
571impl ArtifactSummary {
572 fn from_processor_value(processor_value: Value) -> Self {
573 Self {
574 xname: processor_value["ID"].as_str().unwrap().to_string(),
575 r#type: ArtifactType::from_str(processor_value["Type"].as_str().unwrap()).unwrap(),
576 info: processor_value
577 .pointer("/PopulatedFRU/ProcessorFRUInfo/Model")
578 .map(|model| model.as_str().unwrap().to_string()),
579 }
580 }
581
582 fn from_memory_value(memory_value: Value) -> Self {
583 Self {
584 xname: memory_value["ID"].as_str().unwrap().to_string(),
585 r#type: ArtifactType::from_str(memory_value["Type"].as_str().unwrap()).unwrap(),
586 info: memory_value
587 .pointer("/PopulatedFRU/MemoryFRUInfo/CapacityMiB")
588 .map(|capacity_mib| capacity_mib.as_number().unwrap().to_string() + " MiB"),
589 }
590 }
591
592 fn from_nodehsnnics_value(nodehsnnic_value: Value) -> Self {
593 Self {
594 xname: nodehsnnic_value["ID"].as_str().unwrap().to_string(),
595 r#type: ArtifactType::from_str(nodehsnnic_value["Type"].as_str().unwrap()).unwrap(),
596 info: nodehsnnic_value
597 .pointer("/NodeHsnNicLocationInfo/Description")
598 .map(|description| description.as_str().unwrap().to_string()),
599 }
600 }
601
602 fn from_nodeaccel_value(nodeaccel_value: Value) -> Self {
603 Self {
604 xname: nodeaccel_value["ID"].as_str().unwrap().to_string(),
605 r#type: ArtifactType::from_str(nodeaccel_value["Type"].as_str().unwrap()).unwrap(),
606 info: nodeaccel_value
607 .pointer("/PopulatedFRU/NodeAccelFRUInfo/Model")
608 .map(|model| model.as_str().unwrap().to_string()),
609 }
610 }
611}
612
613#[derive(Debug, Serialize, Deserialize, Clone)]
615pub struct Group {
616 pub label: String,
617 #[serde(skip_serializing_if = "Option::is_none")]
618 pub description: Option<String>,
619 #[serde(skip_serializing_if = "Option::is_none")]
620 pub tags: Option<Vec<String>>,
621 #[serde(skip_serializing_if = "Option::is_none")]
622 pub members: Option<Member>,
623 #[serde(skip_serializing_if = "Option::is_none")]
624 #[serde(rename = "exclusiveGroup")]
625 pub exclusive_group: Option<String>,
626}
627
628#[derive(Debug, Serialize, Deserialize, Default, Clone)]
629pub struct Member {
630 #[serde(skip_serializing_if = "Option::is_none")]
631 pub ids: Option<Vec<String>>,
632}
633#[derive(Debug, Serialize, Deserialize, Default, Clone)]
634pub struct XnameId {
635 #[serde(skip_serializing_if = "Option::is_none")]
636 pub id: Option<String>,
637}
638
639impl Group {
640 pub fn new(
642 label: &str,
643 member_vec_opt: Option<Vec<String>>,
644 tag_vec_opt: Option<Vec<String>>,
645 exclusive_opt: Option<String>,
646 ) -> Self {
647 let members_opt = if let Some(member_vec) = member_vec_opt {
648 Some(Member {
649 ids: Some(member_vec),
650 })
651 } else {
652 None
653 };
654
655 let group = Self {
656 label: label.to_string(),
657 description: None,
658 tags: tag_vec_opt,
659 members: members_opt,
660 exclusive_group: exclusive_opt,
661 };
662
663 group
664 }
665
666 pub fn get_members(&self) -> Vec<String> {
668 self.members
669 .clone()
670 .map(|member| member.ids.unwrap_or_default())
671 .unwrap_or_default()
672 }
673}
674
675#[derive(Debug, Serialize, Deserialize, Clone)]
676pub struct NodeMetadataArray {
677 #[serde(skip_serializing_if = "Option::is_none")]
678 #[serde(rename = "Components")]
679 pub components: Option<Vec<Component>>,
680}
681
682#[derive(Debug, Serialize, Deserialize, Clone)]
683pub struct Component {
684 #[serde(skip_serializing_if = "Option::is_none")]
685 #[serde(rename = "ID")]
686 pub id: Option<String>,
687 #[serde(skip_serializing_if = "Option::is_none")]
688 #[serde(rename = "Type")]
689 pub r#type: Option<String>,
690 #[serde(skip_serializing_if = "Option::is_none")]
691 #[serde(rename = "State")]
692 pub state: Option<String>,
693 #[serde(skip_serializing_if = "Option::is_none")]
694 #[serde(rename = "Flag")]
695 pub flag: Option<String>,
696 #[serde(skip_serializing_if = "Option::is_none")]
697 #[serde(rename = "Enabled")]
698 pub enabled: Option<bool>,
699 #[serde(skip_serializing_if = "Option::is_none")]
700 #[serde(rename = "SoftwareStatus")]
701 pub software_status: Option<String>,
702 #[serde(skip_serializing_if = "Option::is_none")]
703 #[serde(rename = "Role")]
704 pub role: Option<String>,
705 #[serde(skip_serializing_if = "Option::is_none")]
706 #[serde(rename = "SubRole")]
707 pub sub_role: Option<String>,
708 #[serde(skip_serializing_if = "Option::is_none")]
709 #[serde(rename = "NID")]
710 pub nid: Option<usize>,
711 #[serde(skip_serializing_if = "Option::is_none")]
712 #[serde(rename = "Subtype")]
713 pub subtype: Option<String>,
714 #[serde(skip_serializing_if = "Option::is_none")]
715 #[serde(rename = "NetType")]
716 pub net_type: Option<String>,
717 #[serde(skip_serializing_if = "Option::is_none")]
718 #[serde(rename = "Arch")]
719 pub arch: Option<String>,
720 #[serde(skip_serializing_if = "Option::is_none")]
721 #[serde(rename = "Class")]
722 pub class: Option<String>,
723 #[serde(skip_serializing_if = "Option::is_none")]
724 #[serde(rename = "ReservationDisabled")]
725 pub reservation_disabled: Option<bool>,
726 #[serde(skip_serializing_if = "Option::is_none")]
727 #[serde(rename = "Locked")]
728 pub locked: Option<bool>,
729}
730
731#[derive(Debug, Serialize, Deserialize, Clone)]
732pub struct ComponentArrayPostQuery {
733 #[serde(skip_serializing_if = "Option::is_none")]
734 #[serde(rename = "ComponentIDs")]
735 pub component_ids: Option<Vec<String>>,
736 #[serde(skip_serializing_if = "Option::is_none")]
737 pub partition: Option<String>,
738 #[serde(skip_serializing_if = "Option::is_none")]
739 pub group: Option<String>,
740 #[serde(skip_serializing_if = "Option::is_none")]
741 #[serde(rename = "stateonly")]
742 pub state_only: Option<bool>,
743 #[serde(skip_serializing_if = "Option::is_none")]
744 #[serde(rename = "flagonly")]
745 pub falg_only: Option<bool>,
746 #[serde(skip_serializing_if = "Option::is_none")]
747 #[serde(rename = "roleonly")]
748 pub role_only: Option<bool>,
749 #[serde(skip_serializing_if = "Option::is_none")]
750 #[serde(rename = "nidonly")]
751 pub nid_only: Option<bool>,
752 #[serde(skip_serializing_if = "Option::is_none")]
753 pub r#type: Option<String>,
754 #[serde(skip_serializing_if = "Option::is_none")]
755 pub state: Option<String>,
756 #[serde(skip_serializing_if = "Option::is_none")]
757 pub flag: Option<String>,
758 #[serde(skip_serializing_if = "Option::is_none")]
759 pub enabled: Option<String>,
760 #[serde(skip_serializing_if = "Option::is_none")]
761 #[serde(rename = "softwarestatus")]
762 pub software_status: Option<String>,
763 #[serde(skip_serializing_if = "Option::is_none")]
764 pub role: Option<String>,
765 #[serde(skip_serializing_if = "Option::is_none")]
766 pub subrole: Option<String>,
767 #[serde(skip_serializing_if = "Option::is_none")]
768 pub subtype: Option<String>,
769 #[serde(skip_serializing_if = "Option::is_none")]
770 arch: Option<String>,
771 #[serde(skip_serializing_if = "Option::is_none")]
772 pub class: Option<String>,
773 #[serde(skip_serializing_if = "Option::is_none")]
774 pub nid: Option<String>,
775 #[serde(skip_serializing_if = "Option::is_none")]
776 pub nid_start: Option<String>,
777 #[serde(skip_serializing_if = "Option::is_none")]
778 pub nid_end: Option<String>,
779}
780
781#[derive(Debug, Serialize, Deserialize, Clone)]
782pub struct ComponentArrayPostByNidQuery {
783 #[serde(rename = "NIDRanges")]
784 pub nid_ranges: Vec<String>,
785 #[serde(skip_serializing_if = "Option::is_none")]
786 pub partition: Option<String>,
787 #[serde(skip_serializing_if = "Option::is_none")]
788 #[serde(rename = "stateonly")]
789 pub state_only: Option<bool>,
790 #[serde(skip_serializing_if = "Option::is_none")]
791 #[serde(rename = "flagonly")]
792 pub falg_only: Option<bool>,
793 #[serde(skip_serializing_if = "Option::is_none")]
794 #[serde(rename = "roleonly")]
795 pub role_only: Option<bool>,
796 #[serde(skip_serializing_if = "Option::is_none")]
797 #[serde(rename = "nidonly")]
798 pub nid_only: Option<bool>,
799}
800
801#[derive(Debug, Serialize, Deserialize, Clone)]
802pub struct ComponentArrayPostArray {
803 #[serde(rename = "Components")]
804 pub components: Vec<ComponentCreate>,
805 #[serde(skip_serializing_if = "Option::is_none")]
806 #[serde(rename = "Force")]
807 pub force: Option<bool>,
808}
809
810#[derive(Debug, Serialize, Deserialize, Clone)]
811pub struct ComponentCreate {
812 #[serde(rename = "ID")]
813 pub id: String,
814 #[serde(rename = "State")]
815 pub state: String,
816 #[serde(skip_serializing_if = "Option::is_none")]
817 #[serde(rename = "Flag")]
818 pub flag: Option<String>,
819 #[serde(skip_serializing_if = "Option::is_none")]
820 #[serde(rename = "Enabled")]
821 pub enabled: Option<bool>,
822 #[serde(skip_serializing_if = "Option::is_none")]
823 #[serde(rename = "SoftwareStatus")]
824 pub software_status: Option<String>,
825 #[serde(skip_serializing_if = "Option::is_none")]
826 #[serde(rename = "Role")]
827 pub role: Option<String>,
828 #[serde(skip_serializing_if = "Option::is_none")]
829 #[serde(rename = "SubRole")]
830 pub sub_role: Option<String>,
831 #[serde(skip_serializing_if = "Option::is_none")]
832 #[serde(rename = "NID")]
833 pub nid: Option<usize>,
834 #[serde(skip_serializing_if = "Option::is_none")]
835 #[serde(rename = "Subtype")]
836 pub subtype: Option<String>,
837 #[serde(skip_serializing_if = "Option::is_none")]
838 #[serde(rename = "NetType")]
839 pub net_type: Option<String>,
840 #[serde(skip_serializing_if = "Option::is_none")]
841 #[serde(rename = "Arch")]
842 pub arch: Option<String>,
843 #[serde(skip_serializing_if = "Option::is_none")]
844 #[serde(rename = "Class")]
845 pub class: Option<String>,
846}
847
848#[derive(Debug, Serialize, Deserialize, Clone)]
849pub struct ComponentPut {
850 pub component: ComponentCreate,
851 #[serde(skip_serializing_if = "Option::is_none")]
852 #[serde(rename = "Force")]
853 pub force: Option<bool>,
854}
855
856#[derive(Debug, Serialize, Deserialize, Default, Clone)]
857pub struct BootParameters {
858 #[serde(default)]
859 pub hosts: Vec<String>,
860 #[serde(skip_serializing_if = "Option::is_none")]
861 pub macs: Option<Vec<String>>,
862 #[serde(skip_serializing_if = "Option::is_none")]
863 pub nids: Option<Vec<u32>>,
864 #[serde(default)]
865 pub params: String, #[serde(default)]
869 pub kernel: String,
870 #[serde(default)]
871 pub initrd: String,
872 #[serde(rename = "cloud-init")]
873 #[serde(skip_serializing_if = "Option::is_none")]
874 pub cloud_init: Option<Value>,
875}
876
877impl BootParameters {
878 pub fn get_image_id_from_s3_path(s3_path: &str) -> Option<&str> {
883 s3_path.split("/").skip(3).next()
884 }
885
886 pub fn get_boot_image(&self) -> String {
889 let params: HashMap<&str, &str> = self
890 .params
891 .split_whitespace()
892 .map(|kernel_param| {
893 kernel_param
894 .split_once('=')
895 .map(|(key, value)| (key.trim(), value.trim()))
896 .unwrap_or((kernel_param, ""))
897 })
898 .collect();
899
900 let root_kernel_param_opt = params.get("root");
903 let metal_server_kernel_param_opt = params.get("metal.server");
906
907 let boot_image_id_opt: Option<&str> = if let Some(root_kernel_param) = root_kernel_param_opt
908 {
909 Self::get_image_id_from_s3_path(root_kernel_param)
910 } else if let Some(metal_server_kernel_param) = metal_server_kernel_param_opt {
911 Self::get_image_id_from_s3_path(metal_server_kernel_param)
912 } else {
913 None
914 };
915
916 boot_image_id_opt.unwrap_or("").to_string()
917
918 }
932
933 pub fn update_boot_image(&mut self, new_image_id: &str) -> Result<bool, Error> {
940 let mut changed = false;
941 let mut params: HashMap<&str, &str> = self
945 .params
946 .split_whitespace()
947 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
948 .collect();
949
950 let root_kernel_param_rslt = params.get("root");
953
954 let mut root_kernel_param: Vec<&str> = match root_kernel_param_rslt {
955 Some(root_kernel_param) => root_kernel_param.split("/").collect::<Vec<&str>>(),
956 None => {
957 return Err(Error::Message(
958 "ERROR - The 'root' kernel param is missing from user input".to_string(),
959 ));
960 }
961 };
962
963 for current_image_id in &mut root_kernel_param {
965 if uuid::Uuid::try_parse(current_image_id).is_ok() {
968 if *current_image_id != new_image_id {
969 changed = true;
970 }
971 *current_image_id = new_image_id;
973 }
974 }
975
976 let new_root_kernel_param = root_kernel_param.join("/");
978
979 params
981 .entry("root")
982 .and_modify(|root_param| *root_param = &new_root_kernel_param);
983
984 self.update_kernel_param("root", &new_root_kernel_param);
985
986 let mut params: HashMap<&str, &str> = self
990 .params
991 .split_whitespace()
992 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
993 .map(|(key, value)| (key.trim(), value.trim()))
994 .collect();
995
996 let mut metal_server_kernel_param: Vec<&str>;
998 if let Some(metal_server_data) = params.get("metal.server") {
999 metal_server_kernel_param = metal_server_data.split("/").collect();
1000
1001 for substring in &mut metal_server_kernel_param {
1002 if uuid::Uuid::try_parse(substring).is_ok() {
1003 *substring = new_image_id;
1004 changed = true;
1005 }
1006 }
1007
1008 let new_metal_server_kernel_param = metal_server_kernel_param.join("/");
1009
1010 params
1011 .entry("metal.server")
1012 .and_modify(|metal_server_param| {
1013 *metal_server_param = &new_metal_server_kernel_param
1014 });
1015
1016 self.update_kernel_param("metal.server", &new_metal_server_kernel_param);
1017
1018 params = self
1020 .params
1021 .split_whitespace()
1022 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1023 .collect();
1024 } else {
1025 };
1026
1027 let mut nmd_kernel_param: Vec<&str>;
1029 if let Some(nmd_data) = params.get("nmd_data") {
1030 nmd_kernel_param = nmd_data.split("/").collect();
1031
1032 for substring in &mut nmd_kernel_param {
1033 if uuid::Uuid::try_parse(substring).is_ok() {
1034 *substring = new_image_id;
1035 changed = true;
1036 }
1037 }
1038
1039 let new_nmd_kernel_param = nmd_kernel_param.join("/");
1040
1041 params
1042 .entry("nmd_data")
1043 .and_modify(|nmd_param| *nmd_param = &new_nmd_kernel_param);
1044
1045 self.update_kernel_param("nmd_data", &new_nmd_kernel_param);
1046 } else {
1047 };
1048
1049 self.kernel = format!("s3://boot-images/{}/kernel", new_image_id);
1050
1051 self.initrd = format!("s3://boot-images/{}/initrd", new_image_id);
1052
1053 Ok(changed)
1054 }
1055
1056 pub fn update_kernel_params(&mut self, new_params: &str) -> bool {
1061 let mut change = false;
1062
1063 let new_params: Vec<(&str, &str)> = new_params
1064 .split_whitespace()
1065 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1066 .map(|(key, value)| (key.trim(), value.trim()))
1067 .collect();
1068
1069 let mut params: HashMap<&str, &str> = self
1070 .params
1071 .split_whitespace()
1072 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1073 .collect();
1074
1075 for (new_key, new_value) in &new_params {
1076 for (key, value) in params.iter_mut() {
1077 if *key == *new_key {
1078 log::debug!("key '{}' found", key);
1079 if value != new_value {
1080 log::info!("changing key {} from {} to {}", key, value, new_value);
1081
1082 *value = new_value;
1083 change = true
1084 } else {
1085 log::debug!("key '{}' value does not change ({})", key, value);
1086 }
1087 }
1088 }
1089 }
1090
1091 if change == false {
1092 log::debug!("No value change in kernel params. Checking is either new params have been added or removed");
1093 if new_params.len() != params.len() {
1094 log::info!("num kernel parameters have changed");
1095 change = true;
1096 }
1097 }
1098
1099 self.params = params
1100 .iter()
1101 .map(|(key, value)| {
1102 if !value.is_empty() {
1103 format!("{key}={value}")
1104 } else {
1105 key.to_string()
1106 }
1107 })
1108 .collect::<Vec<String>>()
1109 .join(" ");
1110
1111 change
1112 }
1113
1114 pub fn update_kernel_param(&mut self, new_key: &str, new_value: &str) -> bool {
1119 let mut changed = false;
1120 let mut params: HashMap<&str, &str> = self
1122 .params
1123 .split_whitespace()
1124 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1125 .map(|(key, value)| (key.trim(), value.trim()))
1126 .collect();
1127
1128 for (current_key, current_value) in params.iter_mut() {
1131 if *current_key == new_key {
1132 log::debug!("key '{}' found", new_key);
1133 if *current_value != new_value {
1134 log::info!(
1135 "changing key {} from {} to {}",
1136 new_key,
1137 current_value,
1138 new_value
1139 );
1140
1141 *current_value = new_value;
1142 changed = true
1143 } else {
1144 log::debug!(
1145 "key '{}' value does not change ({})",
1146 new_key,
1147 current_value
1148 );
1149 }
1150 }
1151 }
1156
1157 self.params = params
1159 .iter()
1160 .map(|(key, value)| {
1161 if !value.is_empty() {
1162 format!("{key}={value}")
1163 } else {
1164 key.to_string()
1165 }
1166 })
1167 .collect::<Vec<String>>()
1168 .join(" ");
1169
1170 changed
1171 }
1172
1173 pub fn add_kernel_params(&mut self, new_kernel_params: &str) -> bool {
1178 let mut changed = false;
1179 let mut params: HashMap<&str, &str> = self
1180 .params
1181 .split_whitespace()
1182 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1183 .map(|(key, value)| (key.trim(), value.trim()))
1184 .collect();
1185
1186 let new_kernel_params_tuple: HashMap<&str, &str> = new_kernel_params
1187 .split_whitespace()
1188 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1189 .collect();
1190
1191 for (key, new_value) in new_kernel_params_tuple {
1192 if params.contains_key(key) {
1195 log::info!("key '{}' already exists, the new kernel parameter won't be added since it already exists", key);
1196 } else {
1197 log::info!(
1198 "key '{}' not found, adding new kernel param with value '{}'",
1199 key,
1200 new_value
1201 );
1202 params.insert(key, new_value);
1203 changed = true
1204 }
1205 }
1206
1207 self.params = params
1208 .iter()
1209 .map(|(key, value)| {
1210 if !value.is_empty() {
1211 format!("{key}={value}")
1212 } else {
1213 key.to_string()
1214 }
1215 })
1216 .collect::<Vec<String>>()
1217 .join(" ");
1218
1219 changed
1220 }
1221
1222 pub fn delete_kernel_params(&mut self, kernel_params_to_delete: &str) -> bool {
1227 let mut changed = false;
1228 let mut params: HashMap<&str, &str> = self
1229 .params
1230 .split_whitespace()
1231 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1232 .map(|(key, value)| (key.trim(), value.trim()))
1233 .collect();
1234
1235 let kernel_params_to_delete_tuple: HashMap<&str, &str> = kernel_params_to_delete
1236 .split_whitespace()
1237 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1238 .collect();
1239
1240 for (key, _value) in kernel_params_to_delete_tuple {
1241 changed = changed | params.remove(key).is_some();
1242 }
1243
1244 self.params = params
1245 .iter()
1246 .map(|(key, value)| {
1247 if !value.is_empty() {
1248 format!("{key}={value}")
1249 } else {
1250 key.to_string()
1251 }
1252 })
1253 .collect::<Vec<String>>()
1254 .join(" ");
1255
1256 changed
1257 }
1258
1259 pub fn apply_kernel_params(&mut self, new_params: &str) -> bool {
1264 let mut change = false;
1265
1266 let new_params: Vec<(&str, &str)> = new_params
1267 .split_whitespace()
1268 .map(|kernel_param| kernel_param.split_once('=').unwrap_or((kernel_param, "")))
1269 .map(|(key, value)| (key.trim(), value.trim()))
1270 .collect();
1271
1272 let mut params: HashMap<&str, &str> = HashMap::new();
1273
1274 for (new_key, new_value) in &new_params {
1275 for (key, value) in params.iter_mut() {
1276 if *key == *new_key {
1277 log::debug!("key '{}' found", key);
1278 if value != new_value {
1279 log::info!("changing key {} from {} to {}", key, value, new_value);
1280
1281 *value = new_value;
1282 change = true
1283 } else {
1284 log::debug!("key '{}' value does not change ({})", key, value);
1285 }
1286 }
1287 }
1288 }
1289
1290 if change == false {
1291 log::debug!("No value change in kernel params. Checking is either new params have been added or removed");
1292 if new_params.len() != params.len() {
1293 log::info!("num kernel parameters have changed");
1294 change = true;
1295 }
1296 }
1297
1298 self.params = new_params
1299 .iter()
1300 .map(|(key, value)| {
1301 if !value.is_empty() {
1302 format!("{key}={value}")
1303 } else {
1304 key.to_string()
1305 }
1306 })
1307 .collect::<Vec<String>>()
1308 .join(" ");
1309
1310 change
1311 }
1312}
1313
1314#[derive(Debug, Serialize, Deserialize)]
1315pub enum ComponentType {
1316 CDU,
1317 CabinetCDU,
1318 CabinetPDU,
1319 CabinetPDUOutlet,
1320 CabinetPDUPowerConnector,
1321 CabinetPDUController,
1322 r#Cabinet,
1323 Chassis,
1324 ChassisBMC,
1325 CMMRectifier,
1326 CMMFpga,
1327 CEC,
1328 ComputeModule,
1329 RouterModule,
1330 NodeBMC,
1331 NodeEnclosure,
1332 NodeEnclosurePowerSupply,
1333 HSNBoard,
1334 Node,
1335 Processor,
1336 Drive,
1337 StorageGroup,
1338 NodeNIC,
1339 Memory,
1340 NodeAccel,
1341 NodeAccelRiser,
1342 NodeFpga,
1343 HSNAsic,
1344 RouterFpga,
1345 RouterBMC,
1346 HSNLink,
1347 HSNConnector,
1348 INVALID,
1349}
1350
1351#[derive(Debug, Serialize, Deserialize, Clone)]
1352pub struct ProcessorId {
1353 #[serde(rename = "EffectiveFamily")]
1354 #[serde(skip_serializing_if = "Option::is_none")]
1355 pub effective_family: Option<String>,
1356 #[serde(rename = "EffectiveModel")]
1357 #[serde(skip_serializing_if = "Option::is_none")]
1358 pub efffective_model: Option<String>,
1359 #[serde(rename = "IdentificationRegisters")]
1360 #[serde(skip_serializing_if = "Option::is_none")]
1361 pub identification_registers: Option<String>,
1362 #[serde(rename = "MicrocodeInfo")]
1363 #[serde(skip_serializing_if = "Option::is_none")]
1364 pub microcode_info: Option<String>,
1365 #[serde(rename = "Step")]
1366 #[serde(skip_serializing_if = "Option::is_none")]
1367 pub step: Option<String>,
1368 #[serde(rename = "VendorId")]
1369 #[serde(skip_serializing_if = "Option::is_none")]
1370 pub vendor_id: Option<String>,
1371}
1372
1373#[derive(Debug, Serialize, Deserialize, Clone)]
1374pub struct HWInvByFRUProcessor {
1375 #[serde(rename = "FRUID")]
1376 #[serde(skip_serializing_if = "Option::is_none")]
1377 pub fru_id: Option<String>,
1378 #[serde(rename = "Type")]
1379 #[serde(skip_serializing_if = "Option::is_none")]
1380 pub r#type: Option<String>,
1381 #[serde(rename = "FRUSubType")]
1382 #[serde(skip_serializing_if = "Option::is_none")]
1383 pub fru_sub_type: Option<String>,
1384 #[serde(rename = "HWInventoryByFRUType")]
1385 pub hw_inventory_by_fru_type: String,
1386 #[serde(rename = "ProcessorFRUInfo")]
1387 pub processor_fru_info: RedfishProcessorFRUInfo,
1388}
1389
1390#[derive(Debug, Serialize, Deserialize, Clone)]
1391pub struct HWInvByFRUMemory {
1392 #[serde(rename = "FRUID")]
1393 #[serde(skip_serializing_if = "Option::is_none")]
1394 pub fru_id: Option<String>,
1395 #[serde(rename = "Type")]
1396 #[serde(skip_serializing_if = "Option::is_none")]
1397 pub r#type: Option<String>,
1398 #[serde(rename = "FRUSubType")]
1399 #[serde(skip_serializing_if = "Option::is_none")]
1400 pub fru_sub_type: Option<String>,
1401 #[serde(rename = "HWInventoryByFRUType")]
1402 pub hw_inventory_by_fru_type: String,
1403 #[serde(rename = "MemoryFRUInfo")]
1404 pub memory_fru_info: RedfishMemoryFRUInfo,
1405}
1406
1407#[derive(Debug, Serialize, Deserialize, Clone)]
1408pub struct HWInvByFRUHSNNIC {
1409 #[serde(rename = "FRUID")]
1410 #[serde(skip_serializing_if = "Option::is_none")]
1411 pub fru_id: Option<String>,
1412 #[serde(rename = "Type")]
1413 #[serde(skip_serializing_if = "Option::is_none")]
1414 pub r#type: Option<String>,
1415 #[serde(rename = "FRUSubType")]
1416 #[serde(skip_serializing_if = "Option::is_none")]
1417 pub fru_sub_type: Option<String>,
1418 #[serde(rename = "HWInventoryByFRUType")]
1419 pub hw_inventory_by_fru_type: String,
1420 #[serde(rename = "HSNNICFRUInfo")]
1421 pub hsn_nic_fru_info: HSNNICFRUInfo,
1422}
1423
1424#[derive(Debug, Serialize, Deserialize, Clone)]
1425pub struct HWInvByFRUNodeAccel {
1426 #[serde(rename = "FRUID")]
1427 #[serde(skip_serializing_if = "Option::is_none")]
1428 pub fru_id: Option<String>,
1429 #[serde(rename = "Type")]
1430 #[serde(skip_serializing_if = "Option::is_none")]
1431 pub r#type: Option<String>,
1432 #[serde(rename = "FRUSubType")]
1433 #[serde(skip_serializing_if = "Option::is_none")]
1434 pub fru_sub_type: Option<String>,
1435 #[serde(rename = "HWInventoryByFRUType")]
1436 pub hw_inventory_by_fru_type: String,
1437 #[serde(rename = "NodeAccelFRUInfo")]
1438 pub node_accel_fru_info: RedfishProcessorFRUInfo, }
1441
1442#[derive(Debug, Serialize, Deserialize, Clone)]
1443pub struct RedfishProcessorFRUInfo {
1444 #[serde(rename = "InstructionSet")]
1445 #[serde(skip_serializing_if = "Option::is_none")]
1446 pub instruction_set: Option<String>,
1447 #[serde(rename = "Manufacturer")]
1448 #[serde(skip_serializing_if = "Option::is_none")]
1449 pub manufacturer: Option<String>,
1450 #[serde(rename = "MaxSpeedMHz")]
1451 #[serde(skip_serializing_if = "Option::is_none")]
1452 pub max_speed_mhz: Option<usize>,
1453 #[serde(rename = "Model")]
1454 #[serde(skip_serializing_if = "Option::is_none")]
1455 pub model: Option<String>,
1456 #[serde(rename = "ProcessorArchitecture")]
1457 #[serde(skip_serializing_if = "Option::is_none")]
1458 pub processor_architecture: Option<String>,
1459 #[serde(rename = "ProcessorId")]
1460 #[serde(skip_serializing_if = "Option::is_none")]
1461 pub processor_id: Option<ProcessorId>,
1462 #[serde(rename = "ProcessorType")]
1463 #[serde(skip_serializing_if = "Option::is_none")]
1464 pub processor_type: Option<String>,
1465 #[serde(rename = "TotalCores")]
1466 #[serde(skip_serializing_if = "Option::is_none")]
1467 pub total_cores: Option<usize>,
1468 #[serde(rename = "TotalThreads")]
1469 #[serde(skip_serializing_if = "Option::is_none")]
1470 pub total_threads: Option<usize>,
1471}
1472
1473#[derive(Debug, Serialize, Deserialize, Clone)]
1474pub struct RedfishMemoryFRUInfo {
1475 #[serde(rename = "BaseModuleType")]
1476 #[serde(skip_serializing_if = "Option::is_none")]
1477 pub base_module_type: Option<String>,
1478 #[serde(rename = "BusWidthBits")]
1479 #[serde(skip_serializing_if = "Option::is_none")]
1480 pub bus_width_bits: Option<usize>,
1481 #[serde(rename = "CapacityMiB")]
1482 #[serde(skip_serializing_if = "Option::is_none")]
1483 pub capacity_mib: Option<usize>,
1484 #[serde(rename = "DataWidthBits")]
1485 #[serde(skip_serializing_if = "Option::is_none")]
1486 pub data_width_bits: Option<usize>,
1487 #[serde(rename = "ErrorCorrection")]
1488 #[serde(skip_serializing_if = "Option::is_none")]
1489 pub error_correction: Option<String>,
1490 #[serde(rename = "Manufacturer")]
1491 #[serde(skip_serializing_if = "Option::is_none")]
1492 pub manufacturer: Option<String>,
1493 #[serde(rename = "MemoryType")]
1494 #[serde(skip_serializing_if = "Option::is_none")]
1495 pub memory_type: Option<String>,
1496 #[serde(rename = "MemoryDeviceType")]
1497 #[serde(skip_serializing_if = "Option::is_none")]
1498 pub memory_device_type: Option<String>,
1499 #[serde(rename = "OperatingSpeedMhz")]
1500 #[serde(skip_serializing_if = "Option::is_none")]
1501 pub operating_speed_mhz: Option<usize>,
1502 #[serde(rename = "PartNumber")]
1503 #[serde(skip_serializing_if = "Option::is_none")]
1504 pub part_number: Option<String>,
1505 #[serde(rename = "RankCount")]
1506 #[serde(skip_serializing_if = "Option::is_none")]
1507 pub rank_count: Option<usize>,
1508 #[serde(rename = "SerialNumber")]
1509 #[serde(skip_serializing_if = "Option::is_none")]
1510 pub serial_number: Option<String>,
1511}
1512
1513#[derive(Debug, Serialize, Deserialize, Clone)]
1514pub struct HWInventoryByFRU {
1515 #[serde(rename = "FRUID")]
1516 #[serde(skip_serializing_if = "Option::is_none")]
1517 pub fru_id: Option<String>,
1518 #[serde(rename = "Type")]
1519 #[serde(skip_serializing_if = "Option::is_none")]
1520 pub r#type: Option<String>,
1521 #[serde(rename = "FRUSubType")]
1522 #[serde(skip_serializing_if = "Option::is_none")]
1523 pub fru_sub_type: Option<String>,
1524 #[serde(rename = "HWInventoryByFRUType")]
1525 pub hw_inventory_by_fru_type: String,
1526}
1527
1528#[derive(Debug, Serialize, Deserialize, Clone)]
1529pub struct RedfishChassisLocationInfo {
1530 #[serde(rename = "Id")]
1531 #[serde(skip_serializing_if = "Option::is_none")]
1532 pub id: Option<String>,
1533 #[serde(rename = "Name")]
1534 #[serde(skip_serializing_if = "Option::is_none")]
1535 pub name: Option<String>,
1536 #[serde(rename = "Description")]
1537 #[serde(skip_serializing_if = "Option::is_none")]
1538 pub description: Option<String>,
1539 #[serde(rename = "Hostname")]
1540 #[serde(skip_serializing_if = "Option::is_none")]
1541 pub hostname: Option<String>,
1542}
1543
1544#[derive(Debug, Serialize, Deserialize, Clone)]
1545pub struct HWInvByLocChassis {
1546 #[serde(rename = "ID")]
1547 pub id: String,
1548 #[serde(rename = "Type")]
1549 #[serde(skip_serializing_if = "Option::is_none")]
1550 pub r#type: Option<String>,
1551 #[serde(rename = "Ordinal")]
1552 #[serde(skip_serializing_if = "Option::is_none")]
1553 pub ordinal: Option<u32>,
1554 #[serde(rename = "Status")]
1555 #[serde(skip_serializing_if = "Option::is_none")]
1556 pub status: Option<String>,
1557 #[serde(rename = "HWInventoryByLocationType")]
1558 pub hw_inventory_by_location_type: String,
1559 #[serde(rename = "PopulatedFRU")]
1560 #[serde(skip_serializing_if = "Option::is_none")]
1561 pub populated_fru: Option<HWInventoryByFRU>,
1562 #[serde(rename = "ChassisLocatinInfo")]
1563 #[serde(skip_serializing_if = "Option::is_none")]
1564 pub chassis_location_info: Option<RedfishChassisLocationInfo>,
1565 #[serde(rename = "ComputeModules")]
1566 #[serde(skip_serializing_if = "Option::is_none")]
1567 pub compute_modules: Option<HWInvByLocComputeModule>,
1568 #[serde(rename = "RouterModules")]
1569 #[serde(skip_serializing_if = "Option::is_none")]
1570 pub router_modules: Option<HWInvByLocRouterModule>,
1571}
1572
1573#[derive(Debug, Serialize, Deserialize, Clone)]
1574pub struct HWInvByLocNodeEnclosure {
1575 #[serde(rename = "ID")]
1576 pub id: String,
1577 #[serde(rename = "Type")]
1578 #[serde(skip_serializing_if = "Option::is_none")]
1579 pub r#type: Option<String>,
1580 #[serde(rename = "Ordinal")]
1581 #[serde(skip_serializing_if = "Option::is_none")]
1582 pub ordinal: Option<u32>,
1583 #[serde(rename = "Status")]
1584 #[serde(skip_serializing_if = "Option::is_none")]
1585 pub status: Option<String>,
1586 #[serde(rename = "HWInventoryByLocationType")]
1587 pub hw_inventory_by_location_type: String,
1588 #[serde(rename = "PopulatedFRU")]
1589 #[serde(skip_serializing_if = "Option::is_none")]
1590 pub populated_fru: Option<HWInventoryByFRU>,
1591 #[serde(rename = "NodeEnclosureLocationInfo")]
1592 #[serde(skip_serializing_if = "Option::is_none")]
1593 pub node_enclosure_location_info: Option<RedfishChassisLocationInfo>,
1594}
1595
1596#[derive(Debug, Serialize, Deserialize, Clone)]
1597pub struct HWInvByLocComputeModule {
1598 #[serde(rename = "ID")]
1599 pub id: String,
1600 #[serde(rename = "Type")]
1601 #[serde(skip_serializing_if = "Option::is_none")]
1602 pub r#type: Option<String>,
1603 #[serde(rename = "Ordinal")]
1604 #[serde(skip_serializing_if = "Option::is_none")]
1605 pub ordinal: Option<u32>,
1606 #[serde(rename = "Status")]
1607 #[serde(skip_serializing_if = "Option::is_none")]
1608 pub status: Option<String>,
1609 #[serde(rename = "HWInventoryByLocationType")]
1610 pub hw_inventory_by_location_type: String,
1611 #[serde(rename = "PopulatedFRU")]
1612 #[serde(skip_serializing_if = "Option::is_none")]
1613 pub populated_fru: Option<HWInventoryByFRU>,
1614 #[serde(rename = "ComputeModuleLocationInfo")]
1615 #[serde(skip_serializing_if = "Option::is_none")]
1616 pub compute_module_location_info: Option<RedfishChassisLocationInfo>,
1617 #[serde(rename = "NodeEnclosures")]
1618 #[serde(skip_serializing_if = "Option::is_none")]
1619 pub node_enclosures: Option<HWInvByLocNodeEnclosure>,
1620}
1621
1622#[derive(Debug, Serialize, Deserialize, Clone)]
1623pub struct HWInvByLocHSNBoard {
1624 #[serde(rename = "ID")]
1625 pub id: String,
1626 #[serde(rename = "Type")]
1627 #[serde(skip_serializing_if = "Option::is_none")]
1628 pub r#type: Option<String>,
1629 #[serde(rename = "Ordinal")]
1630 #[serde(skip_serializing_if = "Option::is_none")]
1631 pub ordinal: Option<u32>,
1632 #[serde(rename = "Status")]
1633 #[serde(skip_serializing_if = "Option::is_none")]
1634 pub status: Option<String>,
1635 #[serde(rename = "HWInventoryByLocationType")]
1636 pub hw_inventory_by_location_type: String,
1637 #[serde(rename = "PopulatedFRU")]
1638 #[serde(skip_serializing_if = "Option::is_none")]
1639 pub populated_fru: Option<HWInventoryByFRU>,
1640 #[serde(rename = "HSNBoardLocationInfo")]
1641 #[serde(skip_serializing_if = "Option::is_none")]
1642 pub hsn_board_location_info: Option<RedfishChassisLocationInfo>,
1643}
1644
1645#[derive(Debug, Serialize, Deserialize, Clone)]
1646pub struct HWInvByLocRouterModule {
1647 #[serde(rename = "ID")]
1648 pub id: String,
1649 #[serde(rename = "Type")]
1650 #[serde(skip_serializing_if = "Option::is_none")]
1651 pub r#type: Option<String>,
1652 #[serde(rename = "Ordinal")]
1653 #[serde(skip_serializing_if = "Option::is_none")]
1654 pub ordinal: Option<u32>,
1655 #[serde(rename = "Status")]
1656 #[serde(skip_serializing_if = "Option::is_none")]
1657 pub status: Option<String>,
1658 #[serde(rename = "HWInventoryByLocationType")]
1659 pub hw_inventory_by_location_type: String,
1660 #[serde(rename = "PopulatedFRU")]
1661 #[serde(skip_serializing_if = "Option::is_none")]
1662 pub populated_fru: Option<HWInventoryByFRU>,
1663 #[serde(rename = "RouterModuleLocationInfo")]
1664 #[serde(skip_serializing_if = "Option::is_none")]
1665 pub router_module_location_info: Option<RedfishChassisLocationInfo>,
1666 pub hsn_boards: Option<HWInvByLocHSNBoard>,
1667}
1668
1669#[derive(Debug, Serialize, Deserialize, Clone)]
1670pub struct HWInvByLocCabinet {
1671 #[serde(rename = "ID")]
1672 pub id: String,
1673 #[serde(rename = "Type")]
1674 #[serde(skip_serializing_if = "Option::is_none")]
1675 pub r#type: Option<String>,
1676 #[serde(rename = "Ordinal")]
1677 #[serde(skip_serializing_if = "Option::is_none")]
1678 pub ordinal: Option<u32>,
1679 #[serde(rename = "Status")]
1680 #[serde(skip_serializing_if = "Option::is_none")]
1681 pub status: Option<String>,
1682 #[serde(rename = "HWInventoryByLocationType")]
1683 pub hw_inventory_by_location_type: String,
1684 #[serde(rename = "PopulatedFRU")]
1685 #[serde(skip_serializing_if = "Option::is_none")]
1686 pub populated_fru: Option<HWInventoryByFRU>,
1687 #[serde(rename = "CabinetLocationInfo")]
1688 #[serde(skip_serializing_if = "Option::is_none")]
1689 pub cabinet_location_info: Option<RedfishChassisLocationInfo>,
1690 #[serde(rename = "Chassis")]
1691 #[serde(skip_serializing_if = "Option::is_none")]
1692 pub chassis: Option<HWInvByLocChassis>,
1693}
1694
1695#[derive(Debug, Serialize, Deserialize, Clone)]
1696pub struct HWInvByLocMgmtSwitch {
1697 #[serde(rename = "ID")]
1698 pub id: String,
1699 #[serde(rename = "Type")]
1700 #[serde(skip_serializing_if = "Option::is_none")]
1701 pub r#type: Option<String>,
1702 #[serde(rename = "Ordinal")]
1703 #[serde(skip_serializing_if = "Option::is_none")]
1704 pub ordinal: Option<u32>,
1705 #[serde(rename = "Status")]
1706 #[serde(skip_serializing_if = "Option::is_none")]
1707 pub status: Option<String>,
1708 #[serde(rename = "HWInventoryByLocationType")]
1709 pub hw_inventory_by_location_type: String,
1710 #[serde(rename = "PopulatedFRU")]
1711 #[serde(skip_serializing_if = "Option::is_none")]
1712 pub populated_fru: Option<HWInventoryByFRU>,
1713 #[serde(rename = "MgmtSwitchLocationInfo")]
1714 #[serde(skip_serializing_if = "Option::is_none")]
1715 pub mgmt_switch_location_info: Option<RedfishChassisLocationInfo>,
1716}
1717
1718#[derive(Debug, Serialize, Deserialize, Clone)]
1719pub struct HWInvByLocMgmtHLSwitch {
1720 #[serde(rename = "ID")]
1721 pub id: String,
1722 #[serde(rename = "Type")]
1723 #[serde(skip_serializing_if = "Option::is_none")]
1724 pub r#type: Option<String>,
1725 #[serde(rename = "Ordinal")]
1726 #[serde(skip_serializing_if = "Option::is_none")]
1727 pub ordinal: Option<u32>,
1728 #[serde(rename = "Status")]
1729 #[serde(skip_serializing_if = "Option::is_none")]
1730 pub status: Option<String>,
1731 #[serde(rename = "HWInventoryByLocationType")]
1732 pub hw_inventory_by_location_type: String,
1733 #[serde(rename = "PopulatedFRU")]
1734 #[serde(skip_serializing_if = "Option::is_none")]
1735 pub populated_fru: Option<HWInventoryByFRU>,
1736 #[serde(rename = "MgmtHLSwitchLocationInfo")]
1737 #[serde(skip_serializing_if = "Option::is_none")]
1738 pub mgmt_hl_switch_location_info: Option<RedfishChassisLocationInfo>,
1739}
1740
1741#[derive(Debug, Serialize, Deserialize, Clone)]
1742pub struct HWInvByLocCDUMgmtSwitch {
1743 #[serde(rename = "ID")]
1744 pub id: String,
1745 #[serde(rename = "Type")]
1746 #[serde(skip_serializing_if = "Option::is_none")]
1747 pub r#type: Option<String>,
1748 #[serde(rename = "Ordinal")]
1749 #[serde(skip_serializing_if = "Option::is_none")]
1750 pub ordinal: Option<u32>,
1751 #[serde(rename = "Status")]
1752 #[serde(skip_serializing_if = "Option::is_none")]
1753 pub status: Option<String>,
1754 #[serde(rename = "HWInventoryByLocationType")]
1755 pub hw_inventory_by_location_type: String,
1756 #[serde(rename = "PopulatedFRU")]
1757 #[serde(skip_serializing_if = "Option::is_none")]
1758 pub populated_fru: Option<HWInventoryByFRU>,
1759 #[serde(rename = "CDUMgmtSwitchLocationInfo")]
1760 #[serde(skip_serializing_if = "Option::is_none")]
1761 pub cdu_mgmt_switch_location_info: Option<RedfishChassisLocationInfo>,
1762}
1763
1764#[derive(Debug, Serialize, Deserialize, Clone)]
1765pub struct ProcessorSummary {
1766 #[serde(rename = "Count")]
1767 #[serde(skip_serializing_if = "Option::is_none")]
1768 pub count: Option<u32>,
1769 #[serde(rename = "Model")]
1770 #[serde(skip_serializing_if = "Option::is_none")]
1771 pub model: Option<String>,
1772}
1773
1774#[derive(Debug, Serialize, Deserialize, Clone)]
1775pub struct MemorySummary {
1776 #[serde(rename = "TotalSystemMemoryGiB")]
1777 #[serde(skip_serializing_if = "Option::is_none")]
1778 pub total_system_memory_gib: Option<u32>,
1779}
1780
1781#[derive(Debug, Serialize, Deserialize, Clone)]
1782pub struct RedfishSystemLocationInfo {
1783 #[serde(rename = "Id")]
1784 #[serde(skip_serializing_if = "Option::is_none")]
1785 pub id: Option<String>,
1786 #[serde(rename = "Name")]
1787 #[serde(skip_serializing_if = "Option::is_none")]
1788 pub name: Option<String>,
1789 #[serde(rename = "Description")]
1790 #[serde(skip_serializing_if = "Option::is_none")]
1791 pub description: Option<String>,
1792 #[serde(rename = "Hostname")]
1793 #[serde(skip_serializing_if = "Option::is_none")]
1794 pub hostname: Option<String>,
1795 #[serde(rename = "ProcessorSummary")]
1796 #[serde(skip_serializing_if = "Option::is_none")]
1797 pub processor_summary: Option<ProcessorSummary>,
1798 #[serde(rename = "MemorySummary")]
1799 #[serde(skip_serializing_if = "Option::is_none")]
1800 pub memory_summary: Option<MemorySummary>,
1801}
1802
1803#[derive(Debug, Serialize, Deserialize, Clone)]
1804pub struct RedfishProcessorLocationInfo {
1805 #[serde(rename = "Id")]
1806 #[serde(skip_serializing_if = "Option::is_none")]
1807 pub id: Option<String>,
1808 #[serde(rename = "Name")]
1809 #[serde(skip_serializing_if = "Option::is_none")]
1810 pub name: Option<String>,
1811 #[serde(rename = "Description")]
1812 #[serde(skip_serializing_if = "Option::is_none")]
1813 pub description: Option<String>,
1814 #[serde(rename = "Socket")]
1815 #[serde(skip_serializing_if = "Option::is_none")]
1816 pub socket: Option<String>,
1817}
1818
1819#[derive(Debug, Serialize, Deserialize, Clone)]
1820pub struct HWInvByLocProcessor {
1821 #[serde(rename = "ID")]
1822 pub id: String,
1823 #[serde(rename = "Type")]
1824 #[serde(skip_serializing_if = "Option::is_none")]
1825 pub r#type: Option<String>,
1826 #[serde(rename = "Ordinal")]
1827 #[serde(skip_serializing_if = "Option::is_none")]
1828 pub ordinal: Option<u32>,
1829 #[serde(rename = "Status")]
1830 #[serde(skip_serializing_if = "Option::is_none")]
1831 pub status: Option<String>,
1832 #[serde(rename = "HWInventoryByLocationType")]
1833 pub hw_inventory_by_location_type: String,
1834 #[serde(rename = "PopulatedFRU")]
1835 #[serde(skip_serializing_if = "Option::is_none")]
1836 pub populated_fru: Option<HWInvByFRUProcessor>,
1837 #[serde(rename = "ProcessorLocationInfo")]
1838 pub processor_location_info: RedfishProcessorLocationInfo,
1839}
1840
1841#[derive(Debug, Serialize, Deserialize, Clone)]
1842pub struct HWInvByLocNodeAccel {
1843 #[serde(rename = "ID")]
1844 pub id: String,
1845 #[serde(rename = "Type")]
1846 #[serde(skip_serializing_if = "Option::is_none")]
1847 pub r#type: Option<String>,
1848 #[serde(rename = "Ordinal")]
1849 #[serde(skip_serializing_if = "Option::is_none")]
1850 pub ordinal: Option<u32>,
1851 #[serde(rename = "Status")]
1852 #[serde(skip_serializing_if = "Option::is_none")]
1853 pub status: Option<String>,
1854 #[serde(rename = "HWInventoryByLocationType")]
1855 pub hw_inventory_by_location_type: String,
1856 #[serde(rename = "PopulatedFRU")]
1857 #[serde(skip_serializing_if = "Option::is_none")]
1858 pub populated_fru: Option<HWInvByFRUNodeAccel>,
1859 #[serde(rename = "NodeAccelLocationInfo")]
1860 #[serde(skip_serializing_if = "Option::is_none")]
1861 pub node_accel_location_info: Option<RedfishProcessorLocationInfo>,
1862}
1863
1864#[derive(Debug, Serialize, Deserialize, Clone)]
1865pub struct RedfishDriveLocationInfo {
1866 #[serde(rename = "Id")]
1867 #[serde(skip_serializing_if = "Option::is_none")]
1868 pub id: Option<String>,
1869 #[serde(rename = "Name")]
1870 #[serde(skip_serializing_if = "Option::is_none")]
1871 pub name: Option<String>,
1872 #[serde(rename = "Description")]
1873 #[serde(skip_serializing_if = "Option::is_none")]
1874 pub description: Option<String>,
1875}
1876
1877#[derive(Debug, Serialize, Deserialize, Clone)]
1878pub struct HWInvByLocDrive {
1879 #[serde(rename = "ID")]
1880 pub id: String,
1881 #[serde(rename = "Type")]
1882 #[serde(skip_serializing_if = "Option::is_none")]
1883 pub r#type: Option<String>,
1884 #[serde(rename = "Ordinal")]
1885 #[serde(skip_serializing_if = "Option::is_none")]
1886 pub ordinal: Option<u32>,
1887 #[serde(rename = "Status")]
1888 #[serde(skip_serializing_if = "Option::is_none")]
1889 pub status: Option<String>,
1890 #[serde(rename = "HWInventoryByLocationType")]
1891 pub hw_inventory_by_location_type: String,
1892 #[serde(rename = "PopulatedFRU")]
1893 #[serde(skip_serializing_if = "Option::is_none")]
1894 pub populated_fru: Option<HWInventoryByFRU>,
1895 #[serde(rename = "DriveLocationInfo")]
1896 #[serde(skip_serializing_if = "Option::is_none")]
1897 pub drive_location_info: Option<RedfishDriveLocationInfo>,
1898}
1899
1900#[derive(Debug, Serialize, Deserialize, Clone)]
1901pub struct MemoryLocation {
1902 #[serde(rename = "Socket")]
1903 #[serde(skip_serializing_if = "Option::is_none")]
1904 pub socket: Option<u32>,
1905 #[serde(rename = "MemoryController")]
1906 #[serde(skip_serializing_if = "Option::is_none")]
1907 pub memory_controller: Option<u32>,
1908 #[serde(rename = "Channel")]
1909 #[serde(skip_serializing_if = "Option::is_none")]
1910 pub channel: Option<u32>,
1911 #[serde(rename = "Slot")]
1912 #[serde(skip_serializing_if = "Option::is_none")]
1913 pub slot: Option<u32>,
1914}
1915
1916#[derive(Debug, Serialize, Deserialize, Clone)]
1917pub struct RedfishMemoryLocationInfo {
1918 #[serde(rename = "Id")]
1919 #[serde(skip_serializing_if = "Option::is_none")]
1920 pub id: Option<String>,
1921 #[serde(rename = "Name")]
1922 #[serde(skip_serializing_if = "Option::is_none")]
1923 pub name: Option<String>,
1924 #[serde(rename = "Description")]
1925 #[serde(skip_serializing_if = "Option::is_none")]
1926 pub description: Option<String>,
1927 #[serde(rename = "MemoryLocation")]
1928 #[serde(skip_serializing_if = "Option::is_none")]
1929 pub memory_location: Option<MemoryLocation>,
1930}
1931
1932#[derive(Debug, Serialize, Deserialize, Clone)]
1933pub struct HWInvByLocMemory {
1934 #[serde(rename = "ID")]
1935 pub id: String,
1936 #[serde(rename = "Type")]
1937 #[serde(skip_serializing_if = "Option::is_none")]
1938 pub r#type: Option<String>,
1939 #[serde(rename = "Ordinal")]
1940 #[serde(skip_serializing_if = "Option::is_none")]
1941 pub ordinal: Option<u32>,
1942 #[serde(rename = "Status")]
1943 #[serde(skip_serializing_if = "Option::is_none")]
1944 pub status: Option<String>,
1945 #[serde(rename = "HWInventoryByLocationType")]
1946 pub hw_inventory_by_location_type: String,
1947 #[serde(rename = "PopulatedFRU")]
1948 #[serde(skip_serializing_if = "Option::is_none")]
1949 pub populated_fru: Option<HWInvByFRUMemory>,
1950 #[serde(rename = "MemoryLocationInfo")]
1951 pub memory_location_info: RedfishMemoryLocationInfo,
1952}
1953
1954#[derive(Debug, Serialize, Deserialize, Clone)]
1955pub struct RedfishNodeAccelRiserLocationInfo {
1956 #[serde(rename = "Name")]
1957 #[serde(skip_serializing_if = "Option::is_none")]
1958 pub name: Option<String>,
1959 #[serde(rename = "Description")]
1960 #[serde(skip_serializing_if = "Option::is_none")]
1961 pub description: Option<String>,
1962}
1963
1964#[derive(Debug, Serialize, Deserialize, Clone)]
1965pub struct HWInvByLocNodeAccelRiser {
1966 #[serde(rename = "ID")]
1967 pub id: String,
1968 #[serde(rename = "Type")]
1969 #[serde(skip_serializing_if = "Option::is_none")]
1970 pub r#type: Option<String>,
1971 #[serde(rename = "Ordinal")]
1972 #[serde(skip_serializing_if = "Option::is_none")]
1973 pub ordinal: Option<u32>,
1974 #[serde(rename = "Status")]
1975 #[serde(skip_serializing_if = "Option::is_none")]
1976 pub status: Option<String>,
1977 #[serde(rename = "HWInventoryByLocationType")]
1978 pub hw_inventory_by_location_type: String,
1979 #[serde(rename = "PopulatedFRU")]
1980 #[serde(skip_serializing_if = "Option::is_none")]
1981 pub populated_fru: Option<HWInventoryByFRU>,
1982 #[serde(rename = "NodeAccelRiserLocationInfo")]
1983 #[serde(skip_serializing_if = "Option::is_none")]
1984 pub node_accel_riser_location_info: Option<RedfishNodeAccelRiserLocationInfo>,
1985}
1986
1987#[derive(Debug, Serialize, Deserialize, Clone)]
1988pub struct HSNNICLocationInfo {
1989 #[serde(rename = "Id")]
1990 #[serde(skip_serializing_if = "Option::is_none")]
1991 pub id: Option<String>,
1992 #[serde(rename = "Name")]
1993 #[serde(skip_serializing_if = "Option::is_none")]
1994 pub name: Option<String>,
1995 #[serde(rename = "Description")]
1996 #[serde(skip_serializing_if = "Option::is_none")]
1997 pub description: Option<String>,
1998}
1999
2000#[derive(Debug, Serialize, Deserialize, Clone)]
2001pub struct HWInvByLocHSNNIC {
2002 #[serde(rename = "ID")]
2003 pub id: String,
2004 #[serde(rename = "Type")]
2005 #[serde(skip_serializing_if = "Option::is_none")]
2006 pub r#type: Option<String>,
2007 #[serde(rename = "Ordinal")]
2008 #[serde(skip_serializing_if = "Option::is_none")]
2009 pub ordinal: Option<u32>,
2010 #[serde(rename = "Status")]
2011 #[serde(skip_serializing_if = "Option::is_none")]
2012 pub status: Option<String>,
2013 #[serde(rename = "HWInventoryByLocationType")]
2014 pub hw_inventory_by_location_type: String,
2015 #[serde(rename = "PopulatedFRU")]
2016 #[serde(skip_serializing_if = "Option::is_none")]
2017 pub populated_fru: Option<HWInvByFRUHSNNIC>,
2018 #[serde(rename = "HSNNICLocationInfo")]
2021 pub hsn_nic_location_info: HSNNICLocationInfo,
2022}
2023
2024#[derive(Debug, Serialize, Deserialize, Clone)]
2025pub struct RedfishSystemFRUInfo {
2026 #[serde(rename = "AssetTag")]
2027 #[serde(skip_serializing_if = "Option::is_none")]
2028 pub asset_tag: Option<String>,
2029 #[serde(rename = "BiosVersion")]
2030 #[serde(skip_serializing_if = "Option::is_none")]
2031 pub bios_version: Option<String>,
2032 #[serde(rename = "Model")]
2033 #[serde(skip_serializing_if = "Option::is_none")]
2034 pub model: Option<String>,
2035 #[serde(rename = "Manufacturer")]
2036 #[serde(skip_serializing_if = "Option::is_none")]
2037 pub manufacturer: Option<String>,
2038 #[serde(rename = "PartNumber")]
2039 #[serde(skip_serializing_if = "Option::is_none")]
2040 pub part_number: Option<String>,
2041 #[serde(rename = "SerialNumber")]
2042 #[serde(skip_serializing_if = "Option::is_none")]
2043 pub serial_number: Option<String>,
2044 #[serde(rename = "SKU")]
2045 #[serde(skip_serializing_if = "Option::is_none")]
2046 pub sku: Option<String>,
2047 #[serde(rename = "SystemType")]
2048 #[serde(skip_serializing_if = "Option::is_none")]
2049 pub system_type: Option<String>,
2050 #[serde(rename = "UUID")]
2051 #[serde(skip_serializing_if = "Option::is_none")]
2052 pub uuid: Option<String>,
2053}
2054
2055#[derive(Debug, Serialize, Deserialize, Clone)]
2056pub struct HWInvByFRUNode {
2057 #[serde(rename = "FRUID")]
2058 #[serde(skip_serializing_if = "Option::is_none")]
2059 pub fru_id: Option<String>,
2060 #[serde(rename = "Type")]
2061 #[serde(skip_serializing_if = "Option::is_none")]
2062 pub r#type: Option<String>,
2063 #[serde(rename = "FRUSubType")]
2064 #[serde(skip_serializing_if = "Option::is_none")]
2065 pub fru_sub_type: Option<String>,
2066 #[serde(rename = "HWInventoryByFRUType")]
2067 pub hw_inventory_by_fru_type: String,
2068 #[serde(rename = "NodeFRUInfo")]
2069 pub node_fru_info: RedfishSystemFRUInfo,
2070}
2071
2072#[derive(Debug, Serialize, Deserialize, Clone)]
2073pub struct HSNNICFRUInfo {
2074 #[serde(rename = "Manufacturer")]
2075 #[serde(skip_serializing_if = "Option::is_none")]
2076 pub manufacturer: Option<String>,
2077 #[serde(rename = "Model")]
2078 #[serde(skip_serializing_if = "Option::is_none")]
2079 pub model: Option<String>,
2080 #[serde(rename = "PartNumber")]
2081 #[serde(skip_serializing_if = "Option::is_none")]
2082 pub part_number: Option<String>,
2083 #[serde(rename = "SKU")]
2084 #[serde(skip_serializing_if = "Option::is_none")]
2085 pub sku: Option<String>,
2086 #[serde(rename = "SerialNumber")]
2087 #[serde(skip_serializing_if = "Option::is_none")]
2088 pub serial_number: Option<String>,
2089}
2090
2091#[derive(Debug, Serialize, Deserialize, Clone)]
2092pub struct HWInvByLocNode {
2093 #[serde(rename = "ID")]
2094 pub id: String,
2095 #[serde(rename = "Type")]
2096 #[serde(skip_serializing_if = "Option::is_none")]
2097 pub r#type: Option<String>,
2098 #[serde(rename = "Ordinal")]
2099 #[serde(skip_serializing_if = "Option::is_none")]
2100 pub ordinal: Option<u32>,
2101 #[serde(rename = "Status")]
2102 #[serde(skip_serializing_if = "Option::is_none")]
2103 pub status: Option<String>,
2104 #[serde(rename = "HWInventoryByLocationType")]
2105 pub hw_inventory_by_location_type: String,
2106 #[serde(rename = "PopulatedFRU")]
2107 #[serde(skip_serializing_if = "Option::is_none")]
2108 pub populated_fru: Option<HWInvByFRUNode>,
2109 #[serde(rename = "NodeLocationInfo")]
2110 #[serde(skip_serializing_if = "Option::is_none")]
2111 pub node_location_info: Option<RedfishSystemLocationInfo>,
2112 #[serde(rename = "Processors")]
2113 #[serde(skip_serializing_if = "Option::is_none")]
2114 pub processors: Option<Vec<HWInvByLocProcessor>>,
2115 #[serde(rename = "NodeAccels")]
2116 #[serde(skip_serializing_if = "Option::is_none")]
2117 pub node_accels: Option<Vec<HWInvByLocNodeAccel>>,
2118 #[serde(rename = "Dives")]
2119 #[serde(skip_serializing_if = "Option::is_none")]
2120 pub drives: Option<Vec<HWInvByLocDrive>>,
2121 #[serde(rename = "Memory")]
2122 #[serde(skip_serializing_if = "Option::is_none")]
2123 pub memory: Option<Vec<HWInvByLocMemory>>,
2124 #[serde(rename = "NodeAccelRisers")]
2125 #[serde(skip_serializing_if = "Option::is_none")]
2126 pub node_accel_risers: Option<Vec<HWInvByLocNodeAccelRiser>>,
2127 #[serde(rename = "NodeHsnNICs")]
2128 #[serde(skip_serializing_if = "Option::is_none")]
2129 pub node_hsn_nics: Option<Vec<HWInvByLocHSNNIC>>,
2130}
2131
2132#[derive(Debug, Serialize, Deserialize, Clone)]
2133pub struct RedfishPDULocationInfo {
2134 #[serde(rename = "Id")]
2135 #[serde(skip_serializing_if = "Option::is_none")]
2136 pub id: Option<String>,
2137 #[serde(rename = "Name")]
2138 #[serde(skip_serializing_if = "Option::is_none")]
2139 pub name: Option<String>,
2140 #[serde(rename = "Description")]
2141 #[serde(skip_serializing_if = "Option::is_none")]
2142 pub description: Option<String>,
2143 #[serde(rename = "UUID")]
2144 #[serde(skip_serializing_if = "Option::is_none")]
2145 pub uuid: Option<String>,
2146}
2147
2148#[derive(Debug, Serialize, Deserialize, Clone)]
2149pub struct RedfishOutletLocationInfo {
2150 #[serde(rename = "Id")]
2151 #[serde(skip_serializing_if = "Option::is_none")]
2152 pub id: Option<String>,
2153 #[serde(rename = "Name")]
2154 #[serde(skip_serializing_if = "Option::is_none")]
2155 pub name: Option<String>,
2156 #[serde(rename = "Description")]
2157 #[serde(skip_serializing_if = "Option::is_none")]
2158 pub description: Option<String>,
2159}
2160
2161#[derive(Debug, Serialize, Deserialize, Clone)]
2162pub struct HWInvByLocOutlet {
2163 #[serde(rename = "ID")]
2164 pub id: String,
2165 #[serde(rename = "Type")]
2166 #[serde(skip_serializing_if = "Option::is_none")]
2167 pub r#type: Option<String>,
2168 #[serde(rename = "Ordinal")]
2169 #[serde(skip_serializing_if = "Option::is_none")]
2170 pub ordinal: Option<u32>,
2171 #[serde(rename = "Status")]
2172 #[serde(skip_serializing_if = "Option::is_none")]
2173 pub status: Option<String>,
2174 #[serde(rename = "HWInventoryByLocationType")]
2175 pub hw_inventory_by_location_type: String,
2176 #[serde(rename = "PopulatedFRU")]
2177 #[serde(skip_serializing_if = "Option::is_none")]
2178 pub populated_fru: Option<HWInventoryByFRU>,
2179 #[serde(rename = "OutletLocationInfo")]
2180 #[serde(skip_serializing_if = "Option::is_none")]
2181 pub outlet_location_info: Option<RedfishOutletLocationInfo>,
2182}
2183
2184#[derive(Debug, Serialize, Deserialize, Clone)]
2185pub struct HWInvByLocPDU {
2186 #[serde(rename = "ID")]
2187 pub id: String,
2188 #[serde(rename = "Type")]
2189 #[serde(skip_serializing_if = "Option::is_none")]
2190 pub r#type: Option<String>,
2191 #[serde(rename = "Ordinal")]
2192 #[serde(skip_serializing_if = "Option::is_none")]
2193 pub ordinal: Option<u32>,
2194 #[serde(rename = "Status")]
2195 #[serde(skip_serializing_if = "Option::is_none")]
2196 pub status: Option<String>,
2197 #[serde(rename = "HWInventoryByLocationType")]
2198 pub hw_inventory_by_location_type: String,
2199 #[serde(rename = "PopulatedFRU")]
2200 #[serde(skip_serializing_if = "Option::is_none")]
2201 pub populated_fru: Option<HWInventoryByFRU>,
2202 #[serde(rename = "PDULocationInfo")]
2203 #[serde(skip_serializing_if = "Option::is_none")]
2204 pub pdu_location_info: Option<RedfishPDULocationInfo>,
2205 #[serde(rename = "CabinetPDUPowerConnectors")]
2206 #[serde(skip_serializing_if = "Option::is_none")]
2207 pub cabinet_pdu_power_connectors: Option<Vec<HWInvByLocOutlet>>,
2208}
2209
2210#[derive(Debug, Serialize, Deserialize, Clone)]
2211pub struct RedfishCMMRectifierLocationInfo {
2212 #[serde(rename = "Name")]
2213 #[serde(skip_serializing_if = "Option::is_none")]
2214 pub name: Option<String>,
2215 #[serde(rename = "FirmwareVersion")]
2216 #[serde(skip_serializing_if = "Option::is_none")]
2217 pub firmware_version: Option<String>,
2218}
2219
2220#[derive(Debug, Serialize, Deserialize, Clone)]
2221pub struct HWInvByLocCMMRectifier {
2222 #[serde(rename = "ID")]
2223 pub id: String,
2224 #[serde(rename = "Type")]
2225 #[serde(skip_serializing_if = "Option::is_none")]
2226 pub r#type: Option<String>,
2227 #[serde(rename = "Ordinal")]
2228 #[serde(skip_serializing_if = "Option::is_none")]
2229 pub ordinal: Option<u32>,
2230 #[serde(rename = "Status")]
2231 #[serde(skip_serializing_if = "Option::is_none")]
2232 pub status: Option<String>,
2233 #[serde(rename = "HWInventoryByLocationType")]
2234 pub hw_inventory_by_location_type: String,
2235 #[serde(rename = "PopulatedFRU")]
2236 #[serde(skip_serializing_if = "Option::is_none")]
2237 pub populated_fru: Option<HWInventoryByFRU>,
2238 #[serde(rename = "CMMRectifierLocationInfo")]
2239 #[serde(skip_serializing_if = "Option::is_none")]
2240 pub cmm_rectifier_location_info: Option<RedfishCMMRectifierLocationInfo>,
2241}
2242
2243#[derive(Debug, Serialize, Deserialize, Clone)]
2244pub struct RedfishNodeEnclosurePowerSupplyLocationInfo {
2245 #[serde(rename = "Name")]
2246 #[serde(skip_serializing_if = "Option::is_none")]
2247 pub name: Option<String>,
2248 #[serde(rename = "FirmwareVersion")]
2249 #[serde(skip_serializing_if = "Option::is_none")]
2250 pub firmware_version: Option<String>,
2251}
2252
2253#[derive(Debug, Serialize, Deserialize, Clone)]
2254pub struct HWInvByLocNodePowerSupply {
2255 #[serde(rename = "ID")]
2256 pub id: String,
2257 #[serde(rename = "Type")]
2258 #[serde(skip_serializing_if = "Option::is_none")]
2259 pub r#type: Option<String>,
2260 #[serde(rename = "Ordinal")]
2261 #[serde(skip_serializing_if = "Option::is_none")]
2262 pub ordinal: Option<u32>,
2263 #[serde(rename = "Status")]
2264 #[serde(skip_serializing_if = "Option::is_none")]
2265 pub status: Option<String>,
2266 #[serde(rename = "HWInventoryByLocationType")]
2267 pub hw_inventory_by_location_type: String,
2268 #[serde(rename = "PopulatedFRU")]
2269 #[serde(skip_serializing_if = "Option::is_none")]
2270 pub populated_fru: Option<HWInventoryByFRU>,
2271 #[serde(rename = "NodeEnclosurePowerSupplyLocationInfo")]
2272 #[serde(skip_serializing_if = "Option::is_none")]
2273 pub node_enclosure_power_supply_location_info:
2274 Option<RedfishNodeEnclosurePowerSupplyLocationInfo>,
2275}
2276
2277#[derive(Debug, Serialize, Deserialize, Clone)]
2278pub struct RedfishManagerLocationInfo {
2279 #[serde(rename = "Id")]
2280 #[serde(skip_serializing_if = "Option::is_none")]
2281 pub id: Option<String>,
2282 #[serde(rename = "Name")]
2283 #[serde(skip_serializing_if = "Option::is_none")]
2284 pub name: Option<String>,
2285 #[serde(rename = "Description")]
2286 #[serde(skip_serializing_if = "Option::is_none")]
2287 pub description: Option<String>,
2288 #[serde(rename = "DateTime")]
2289 #[serde(skip_serializing_if = "Option::is_none")]
2290 pub date_time: Option<String>,
2291 #[serde(rename = "DateTimeLocalOffset")]
2292 #[serde(skip_serializing_if = "Option::is_none")]
2293 pub date_time_local_offset: Option<String>,
2294 #[serde(rename = "FirmwareVersion")]
2295 #[serde(skip_serializing_if = "Option::is_none")]
2296 pub firmware_version: Option<String>,
2297}
2298
2299#[derive(Debug, Serialize, Deserialize, Clone)]
2300pub struct HWInvByLocNodeBMC {
2301 #[serde(rename = "ID")]
2302 pub id: String,
2303 #[serde(rename = "Type")]
2304 #[serde(skip_serializing_if = "Option::is_none")]
2305 pub r#type: Option<String>,
2306 #[serde(rename = "Ordinal")]
2307 #[serde(skip_serializing_if = "Option::is_none")]
2308 pub ordinal: Option<u32>,
2309 #[serde(rename = "Status")]
2310 #[serde(skip_serializing_if = "Option::is_none")]
2311 pub status: Option<String>,
2312 #[serde(rename = "HWInventoryByLocationType")]
2313 pub hw_inventory_by_location_type: String,
2314 #[serde(rename = "PopulatedFRU")]
2315 #[serde(skip_serializing_if = "Option::is_none")]
2316 pub populated_fru: Option<HWInventoryByFRU>,
2317 #[serde(rename = "NodeBMCLocationInfo")]
2318 #[serde(skip_serializing_if = "Option::is_none")]
2319 pub node_bmc_location_info: Option<RedfishManagerLocationInfo>,
2320}
2321
2322#[derive(Debug, Serialize, Deserialize, Clone)]
2323pub struct HWInvByLocRouterBMC {
2324 #[serde(rename = "ID")]
2325 pub id: String,
2326 #[serde(rename = "Type")]
2327 #[serde(skip_serializing_if = "Option::is_none")]
2328 pub r#type: Option<String>,
2329 #[serde(rename = "Ordinal")]
2330 #[serde(skip_serializing_if = "Option::is_none")]
2331 pub ordinal: Option<u32>,
2332 #[serde(rename = "Status")]
2333 #[serde(skip_serializing_if = "Option::is_none")]
2334 pub status: Option<String>,
2335 #[serde(rename = "HWInventoryByLocationType")]
2336 pub hw_inventory_by_location_type: String,
2337 #[serde(rename = "PopulatedFRU")]
2338 #[serde(skip_serializing_if = "Option::is_none")]
2339 pub populated_fru: Option<HWInventoryByFRU>,
2340 #[serde(rename = "RouterBMCLocationInfo")]
2341 #[serde(skip_serializing_if = "Option::is_none")]
2342 pub router_bmc_location_info: Option<RedfishManagerLocationInfo>,
2343}
2344
2345#[derive(Debug, Serialize, Deserialize, Clone)]
2352pub struct HWInventory {
2353 #[serde(rename = "XName")]
2354 #[serde(skip_serializing_if = "Option::is_none")]
2355 pub xname: Option<String>,
2356 #[serde(rename = "Format")]
2357 #[serde(skip_serializing_if = "Option::is_none")]
2358 pub format: Option<String>,
2359 #[serde(rename = "Cabinets")]
2360 #[serde(skip_serializing_if = "Option::is_none")]
2361 pub cabinets: Option<Vec<HWInvByLocCabinet>>,
2362 #[serde(rename = "Chassis")]
2363 #[serde(skip_serializing_if = "Option::is_none")]
2364 pub chassis: Option<Vec<HWInvByLocChassis>>,
2365 #[serde(rename = "ComputeModules")]
2366 #[serde(skip_serializing_if = "Option::is_none")]
2367 pub compute_modules: Option<Vec<HWInvByLocComputeModule>>,
2368 #[serde(rename = "RouterModules")]
2369 #[serde(skip_serializing_if = "Option::is_none")]
2370 pub router_modules: Option<Vec<HWInvByLocRouterModule>>,
2371 #[serde(rename = "NodeEnclosures")]
2372 #[serde(skip_serializing_if = "Option::is_none")]
2373 pub node_enclosures: Option<Vec<HWInvByLocNodeEnclosure>>,
2374 #[serde(rename = "HSNBoards")]
2375 #[serde(skip_serializing_if = "Option::is_none")]
2376 pub hsn_boards: Option<Vec<HWInvByLocHSNBoard>>,
2377 #[serde(rename = "MgmtSwitches")]
2378 #[serde(skip_serializing_if = "Option::is_none")]
2379 pub mgmt_switches: Option<Vec<HWInvByLocMgmtSwitch>>,
2380 #[serde(rename = "MgmtHLSwitches")]
2381 #[serde(skip_serializing_if = "Option::is_none")]
2382 pub mgmt_hl_switches: Option<Vec<HWInvByLocMgmtHLSwitch>>,
2383 #[serde(rename = "CDUMgmtSwitches")]
2384 #[serde(skip_serializing_if = "Option::is_none")]
2385 pub cdu_mgmt_switches: Option<Vec<HWInvByLocCDUMgmtSwitch>>,
2386 #[serde(rename = "Nodes")]
2387 #[serde(skip_serializing_if = "Option::is_none")]
2388 pub nodes: Option<Vec<HWInvByLocNode>>,
2389 #[serde(rename = "Processors")]
2390 #[serde(skip_serializing_if = "Option::is_none")]
2391 pub processors: Option<Vec<HWInvByLocProcessor>>,
2392 #[serde(rename = "NodeAccels")]
2393 #[serde(skip_serializing_if = "Option::is_none")]
2394 pub node_accels: Option<Vec<HWInvByLocNodeAccel>>,
2395 #[serde(rename = "Drives")]
2396 #[serde(skip_serializing_if = "Option::is_none")]
2397 pub drives: Option<Vec<HWInvByLocDrive>>,
2398 #[serde(rename = "Memory")]
2399 #[serde(skip_serializing_if = "Option::is_none")]
2400 pub memory: Option<Vec<HWInvByLocMemory>>,
2401 #[serde(rename = "CabinetPDUs")]
2402 #[serde(skip_serializing_if = "Option::is_none")]
2403 pub cabinet_pdus: Option<Vec<HWInvByLocPDU>>,
2404 #[serde(rename = "CabinetPDUPowerConnectors")]
2405 #[serde(skip_serializing_if = "Option::is_none")]
2406 pub cabinet_pdu_power_connectors: Option<Vec<HWInvByLocOutlet>>,
2407 #[serde(rename = "CMMRectifiers")]
2408 #[serde(skip_serializing_if = "Option::is_none")]
2409 pub cmm_rectifiers: Option<Vec<HWInvByLocCMMRectifier>>,
2410 #[serde(rename = "NodeAccelRisers")]
2411 #[serde(skip_serializing_if = "Option::is_none")]
2412 pub node_accel_risers: Option<Vec<HWInvByLocNodeAccelRiser>>,
2413 #[serde(rename = "NodeHsnNICs")]
2414 #[serde(skip_serializing_if = "Option::is_none")]
2415 pub node_hsn_nics: Option<Vec<HWInvByLocHSNNIC>>,
2416 #[serde(rename = "NodeEnclosurePowerSupplies")]
2417 #[serde(skip_serializing_if = "Option::is_none")]
2418 pub node_enclosure_power_supplies: Option<Vec<HWInvByLocNodePowerSupply>>,
2419 #[serde(rename = "NodeBMC")]
2420 #[serde(skip_serializing_if = "Option::is_none")]
2421 pub node_bmc: Option<Vec<HWInvByLocNodeBMC>>,
2422 #[serde(rename = "RouterBMC")]
2423 #[serde(skip_serializing_if = "Option::is_none")]
2424 pub router_bmc: Option<Vec<HWInvByLocRouterBMC>>,
2425}
2426
2427#[derive(Debug, Serialize, Deserialize, Clone)]
2428pub struct Hardware {
2429 #[serde(rename = "Hardware")]
2430 #[serde(skip_serializing_if = "Option::is_none")]
2431 pub hardware: Option<Vec<HWInvByLocNode>>,
2432}
2433
2434#[derive(Debug, Serialize, Deserialize, Clone)]
2435pub struct NodeLocationInfo {
2436 #[serde(rename = "Id")]
2437 pub id: String,
2438 #[serde(rename = "Name")]
2439 #[serde(skip_serializing_if = "Option::is_none")]
2440 pub name: Option<String>,
2441 #[serde(rename = "Description")]
2442 #[serde(skip_serializing_if = "Option::is_none")]
2443 pub description: Option<String>,
2444 #[serde(rename = "Hostname")]
2445 #[serde(skip_serializing_if = "Option::is_none")]
2446 pub hostname: Option<String>,
2447 #[serde(rename = "ProcessorSummary")]
2448 #[serde(skip_serializing_if = "Option::is_none")]
2449 pub processor_summary: Option<ProcessorSummary>,
2450 #[serde(rename = "MemorySummary")]
2451 #[serde(skip_serializing_if = "Option::is_none")]
2452 pub memory_summary: Option<MemorySummary>,
2453}
2454
2455#[derive(Debug, Serialize, Deserialize, Clone)]
2456#[serde(untagged)] pub enum HWInventoryByLocation {
2458 HWInvByLocNode(HWInvByLocNode),
2468 HWInvByLocProcessor(HWInvByLocProcessor),
2469 HWInvByLocNodeAccel(HWInvByLocNodeAccel),
2470 HWInvByLocMemory(HWInvByLocMemory),
2472 HWInvByLocHSNNIC(HWInvByLocHSNNIC),
2477 }
2481
2482#[derive(Debug, Serialize, Deserialize, Clone)]
2484pub struct HWInventoryByLocationList {
2485 #[serde(rename = "Hardware")]
2486 #[serde(skip_serializing_if = "Option::is_none")]
2487 pub hardware: Option<Vec<HWInventoryByLocation>>,
2488}
2489
2490#[derive(Debug, Serialize, Deserialize, Clone)]
2491pub struct Link {
2492 #[serde(skip_serializing_if = "Option::is_none")]
2493 pub rel: Option<String>,
2494 #[serde(skip_serializing_if = "Option::is_none")]
2495 pub href: Option<String>,
2496}
2497
2498#[derive(Debug, Serialize, Deserialize, Clone)]
2499pub struct Cfs {
2500 #[serde(skip_serializing_if = "Option::is_none")]
2501 pub configuration: Option<String>,
2502}
2503
2504#[derive(Debug, Serialize, Deserialize, Clone)]
2505pub struct BootSet {
2506 #[serde(skip_serializing_if = "Option::is_none")]
2507 pub name: Option<String>,
2508 #[serde(skip_serializing_if = "Option::is_none")]
2509 pub path: Option<String>,
2510 #[serde(skip_serializing_if = "Option::is_none")]
2511 pub cfs: Option<Cfs>,
2512 #[serde(skip_serializing_if = "Option::is_none")]
2513 pub r#type: Option<String>,
2514 #[serde(skip_serializing_if = "Option::is_none")]
2515 pub etag: Option<String>,
2516 #[serde(skip_serializing_if = "Option::is_none")]
2517 pub kernel_parameters: Option<String>,
2518 #[serde(skip_serializing_if = "Option::is_none")]
2519 pub node_list: Option<Vec<String>>,
2520 #[serde(skip_serializing_if = "Option::is_none")]
2521 pub node_roles_groups: Option<Vec<String>>,
2522 #[serde(skip_serializing_if = "Option::is_none")]
2523 pub node_groups: Option<Vec<String>>,
2524 #[serde(skip_serializing_if = "Option::is_none")]
2525 pub arch: Option<String>, #[serde(skip_serializing_if = "Option::is_none")]
2527 pub rootfs_provider: Option<String>,
2528 #[serde(skip_serializing_if = "Option::is_none")]
2529 pub rootfs_provider_passthrough: Option<String>,
2530}
2531
2532#[derive(Debug, Serialize, Deserialize, Clone)]
2533pub struct BosSessionTemplate {
2534 #[serde(skip_serializing_if = "Option::is_none")]
2535 pub name: Option<String>,
2536 #[serde(skip_serializing_if = "Option::is_none")]
2537 pub tenant: Option<String>,
2538 #[serde(skip_serializing_if = "Option::is_none")]
2539 pub description: Option<String>,
2540 #[serde(skip_serializing_if = "Option::is_none")]
2541 pub enable_cfs: Option<bool>,
2542 #[serde(skip_serializing_if = "Option::is_none")]
2543 pub cfs: Option<Cfs>,
2544 #[serde(skip_serializing_if = "Option::is_none")]
2545 pub boot_sets: Option<HashMap<String, BootSet>>,
2546 #[serde(skip_serializing_if = "Option::is_none")]
2547 pub links: Option<Vec<Link>>,
2548}