From 74182bbc60fd55ed8033f9fcab3065d1e93b2904 Mon Sep 17 00:00:00 2001 From: Ian Letourneau Date: Mon, 4 Aug 2025 17:49:40 -0400 Subject: [PATCH 1/3] cleanup harmony with clippy --- opnsense-config/src/config/shell/ssh.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/opnsense-config/src/config/shell/ssh.rs b/opnsense-config/src/config/shell/ssh.rs index 3c66864..60d3702 100644 --- a/opnsense-config/src/config/shell/ssh.rs +++ b/opnsense-config/src/config/shell/ssh.rs @@ -107,7 +107,7 @@ impl OPNsenseShell for SshOPNSenseShell { match result { Ok(bytes) => { if !bytes.is_empty() { - remote_file.write(&bytes).await?; + AsyncWriteExt::write_all(&mut remote_file, &bytes).await?; } } Err(e) => todo!("Error unhandled {e}"), -- 2.39.5 From c64b59a4ec2ec4df1066dc254e1dc74026a25174 Mon Sep 17 00:00:00 2001 From: Ian Letourneau Date: Mon, 4 Aug 2025 21:52:45 -0400 Subject: [PATCH 2/3] apply cargo & clippy fixes --- check.sh | 2 + .../src/main.rs | 14 +-- examples/kube-rs/src/main.rs | 63 +++++++------ examples/lamp/src/main.rs | 2 +- examples/monitoring_with_tenant/src/main.rs | 4 +- examples/tenant/src/main.rs | 4 +- harmony/src/domain/data/id.rs | 13 +-- harmony/src/domain/data/version.rs | 2 +- harmony/src/domain/hardware/mod.rs | 3 +- harmony/src/domain/maestro/mod.rs | 5 +- harmony/src/domain/score.rs | 4 +- harmony/src/domain/topology/k8s.rs | 30 +++--- harmony/src/domain/topology/k8s_anywhere.rs | 12 ++- harmony/src/domain/topology/mod.rs | 2 +- harmony/src/domain/topology/router.rs | 4 +- harmony/src/domain/topology/tenant/k8s.rs | 16 ++-- harmony/src/infra/opnsense/dns.rs | 2 +- harmony/src/infra/opnsense/http.rs | 2 +- harmony/src/infra/opnsense/load_balancer.rs | 91 +++++++++++-------- harmony/src/infra/opnsense/tftp.rs | 2 +- harmony/src/modules/application/feature.rs | 4 +- .../application/features/argo_types.rs | 5 +- .../features/continuous_delivery.rs | 2 +- .../application/features/helm_argocd_score.rs | 2 +- harmony/src/modules/application/mod.rs | 2 +- harmony/src/modules/application/rust.rs | 14 +-- harmony/src/modules/cert_manager/helm.rs | 2 +- harmony/src/modules/dhcp.rs | 10 +- harmony/src/modules/dns.rs | 2 +- harmony/src/modules/helm/chart.rs | 14 +-- harmony/src/modules/helm/command.rs | 41 +++------ harmony/src/modules/k3d/install.rs | 2 +- harmony/src/modules/lamp.rs | 4 +- .../alert_rule/prometheus_alert_rule.rs | 4 +- .../monitoring/grafana/helm/helm_grafana.rs | 5 +- .../kube_prometheus/crd/crd_alertmanagers.rs | 1 - .../kube_prometheus/crd/crd_default_rules.rs | 15 +-- .../crd/crd_prometheus_rules.rs | 2 - .../kube_prometheus/crd/service_monitor.rs | 8 +- .../monitoring/kube_prometheus/helm/config.rs | 6 ++ .../helm/kube_prometheus_helm_chart.rs | 4 +- .../monitoring/kube_prometheus/prometheus.rs | 6 ++ harmony/src/modules/monitoring/ntfy/mod.rs | 1 + harmony/src/modules/monitoring/ntfy/ntfy.rs | 48 ++-------- .../src/modules/monitoring/prometheus/mod.rs | 1 + .../monitoring/prometheus/prometheus.rs | 12 ++- .../prometheus/prometheus_config.rs | 6 ++ harmony/src/modules/okd/bootstrap_dhcp.rs | 2 +- harmony/src/modules/okd/upgrade.rs | 6 ++ .../k8s_prometheus_alerting_score.rs | 10 +- harmony/src/modules/prometheus/mod.rs | 1 + harmony_cli/src/cli_logger.rs | 2 +- harmony_cli/src/lib.rs | 18 ++-- .../src/harmony_composer_logger.rs | 2 +- harmony_composer/src/instrumentation.rs | 2 +- harmony_composer/src/main.rs | 60 +++++++----- harmony_macros/src/lib.rs | 10 +- harmony_tui/src/widget/score.rs | 22 ++--- k3d/src/lib.rs | 8 +- opnsense-config-xml/src/data/haproxy.rs | 3 +- opnsense-config-xml/src/data/opnsense.rs | 4 +- opnsense-config/Cargo.toml | 7 +- opnsense-config/src/config/config.rs | 10 +- opnsense-config/src/config/manager/ssh.rs | 2 +- opnsense-config/src/config/mod.rs | 1 + opnsense-config/src/config/shell/ssh.rs | 4 +- opnsense-config/src/modules/dhcp.rs | 13 +-- 67 files changed, 339 insertions(+), 348 deletions(-) diff --git a/check.sh b/check.sh index a01f875..3bcbc6a 100755 --- a/check.sh +++ b/check.sh @@ -1,5 +1,7 @@ #!/bin/sh set -e + cargo check --all-targets --all-features --keep-going cargo fmt --check +cargo clippy cargo test diff --git a/examples/application_monitoring_with_tenant/src/main.rs b/examples/application_monitoring_with_tenant/src/main.rs index 2f10b36..9ab0bf6 100644 --- a/examples/application_monitoring_with_tenant/src/main.rs +++ b/examples/application_monitoring_with_tenant/src/main.rs @@ -1,17 +1,11 @@ -use std::{path::PathBuf, sync::Arc}; +use std::{path::PathBuf, str::FromStr, sync::Arc}; use harmony::{ data::Id, inventory::Inventory, - maestro::Maestro, modules::{ - application::{ - ApplicationScore, RustWebFramework, RustWebapp, - features::{ContinuousDelivery, Monitoring}, - }, - monitoring::alert_channel::{ - discord_alert_channel::DiscordWebhook, webhook_receiver::WebhookReceiver, - }, + application::{ApplicationScore, RustWebFramework, RustWebapp, features::Monitoring}, + monitoring::alert_channel::webhook_receiver::WebhookReceiver, tenant::TenantScore, }, topology::{K8sAnywhereTopology, Url, tenant::TenantConfig}, @@ -25,7 +19,7 @@ async fn main() { //the TenantConfig.name must match let tenant = TenantScore { config: TenantConfig { - id: Id::from_str("test-tenant-id"), + id: Id::from_str("test-tenant-id").unwrap(), name: "example-monitoring".to_string(), ..Default::default() }, diff --git a/examples/kube-rs/src/main.rs b/examples/kube-rs/src/main.rs index d7d941f..82652f4 100644 --- a/examples/kube-rs/src/main.rs +++ b/examples/kube-rs/src/main.rs @@ -125,40 +125,47 @@ spec: name: nginx"#, ) .unwrap(); - return deployment; + deployment } fn nginx_deployment_2() -> Deployment { - let mut pod_template = PodTemplateSpec::default(); - pod_template.metadata = Some(ObjectMeta { - labels: Some(BTreeMap::from([( - "app".to_string(), - "nginx-test".to_string(), - )])), - ..Default::default() - }); - pod_template.spec = Some(PodSpec { - containers: vec![Container { - name: "nginx".to_string(), - image: Some("nginx".to_string()), + let pod_template = PodTemplateSpec { + metadata: Some(ObjectMeta { + labels: Some(BTreeMap::from([( + "app".to_string(), + "nginx-test".to_string(), + )])), ..Default::default() - }], - ..Default::default() - }); - let mut spec = DeploymentSpec::default(); - spec.template = pod_template; - spec.selector = LabelSelector { - match_expressions: None, - match_labels: Some(BTreeMap::from([( - "app".to_string(), - "nginx-test".to_string(), - )])), + }), + spec: Some(PodSpec { + containers: vec![Container { + name: "nginx".to_string(), + image: Some("nginx".to_string()), + ..Default::default() + }], + ..Default::default() + }), }; - let mut deployment = Deployment::default(); - deployment.spec = Some(spec); - deployment.metadata.name = Some("nginx-test".to_string()); + let spec = DeploymentSpec { + template: pod_template, + selector: LabelSelector { + match_expressions: None, + match_labels: Some(BTreeMap::from([( + "app".to_string(), + "nginx-test".to_string(), + )])), + }, + ..Default::default() + }; - deployment + Deployment { + spec: Some(spec), + metadata: ObjectMeta { + name: Some("nginx-test".to_string()), + ..Default::default() + }, + ..Default::default() + } } fn nginx_deployment() -> Deployment { diff --git a/examples/lamp/src/main.rs b/examples/lamp/src/main.rs index 6662f4c..b621156 100644 --- a/examples/lamp/src/main.rs +++ b/examples/lamp/src/main.rs @@ -23,7 +23,7 @@ async fn main() { // This config can be extended as needed for more complicated configurations config: LAMPConfig { project_root: "./php".into(), - database_size: format!("4Gi").into(), + database_size: "4Gi".to_string().into(), ..Default::default() }, }; diff --git a/examples/monitoring_with_tenant/src/main.rs b/examples/monitoring_with_tenant/src/main.rs index baa8cd5..2960944 100644 --- a/examples/monitoring_with_tenant/src/main.rs +++ b/examples/monitoring_with_tenant/src/main.rs @@ -1,4 +1,4 @@ -use std::collections::HashMap; +use std::{collections::HashMap, str::FromStr}; use harmony::{ data::Id, @@ -28,7 +28,7 @@ use harmony::{ async fn main() { let tenant = TenantScore { config: TenantConfig { - id: Id::from_string("1234".to_string()), + id: Id::from_str("1234").unwrap(), name: "test-tenant".to_string(), resource_limits: ResourceLimits { cpu_request_cores: 6.0, diff --git a/examples/tenant/src/main.rs b/examples/tenant/src/main.rs index b5202b2..356ad1b 100644 --- a/examples/tenant/src/main.rs +++ b/examples/tenant/src/main.rs @@ -1,3 +1,5 @@ +use std::str::FromStr; + use harmony::{ data::Id, inventory::Inventory, @@ -9,7 +11,7 @@ use harmony::{ async fn main() { let tenant = TenantScore { config: TenantConfig { - id: Id::from_str("test-tenant-id"), + id: Id::from_str("test-tenant-id").unwrap(), name: "testtenant".to_string(), ..Default::default() }, diff --git a/harmony/src/domain/data/id.rs b/harmony/src/domain/data/id.rs index 04de962..5a17ae0 100644 --- a/harmony/src/domain/data/id.rs +++ b/harmony/src/domain/data/id.rs @@ -1,5 +1,6 @@ use rand::distr::Alphanumeric; use rand::distr::SampleString; +use std::str::FromStr; use std::time::SystemTime; use std::time::UNIX_EPOCH; @@ -23,13 +24,13 @@ pub struct Id { value: String, } -impl Id { - pub fn from_string(value: String) -> Self { - Self { value } - } +impl FromStr for Id { + type Err = (); - pub fn from_str(value: &str) -> Self { - Self::from_string(value.to_string()) + fn from_str(s: &str) -> Result { + Ok(Id { + value: s.to_string(), + }) } } diff --git a/harmony/src/domain/data/version.rs b/harmony/src/domain/data/version.rs index b6b4193..851d9aa 100644 --- a/harmony/src/domain/data/version.rs +++ b/harmony/src/domain/data/version.rs @@ -47,7 +47,7 @@ impl serde::Serialize for Version { impl std::fmt::Display for Version { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { - return self.value.fmt(f); + self.value.fmt(f) } } diff --git a/harmony/src/domain/hardware/mod.rs b/harmony/src/domain/hardware/mod.rs index 41576fc..399f313 100644 --- a/harmony/src/domain/hardware/mod.rs +++ b/harmony/src/domain/hardware/mod.rs @@ -35,10 +35,9 @@ impl PhysicalHost { pub fn cluster_mac(&self) -> MacAddress { self.network - .get(0) + .first() .expect("Cluster physical host should have a network interface") .mac_address - .clone() } pub fn cpu(mut self, cpu_count: Option) -> Self { diff --git a/harmony/src/domain/maestro/mod.rs b/harmony/src/domain/maestro/mod.rs index 4d1053e..ceab27a 100644 --- a/harmony/src/domain/maestro/mod.rs +++ b/harmony/src/domain/maestro/mod.rs @@ -70,10 +70,7 @@ impl Maestro { fn is_topology_initialized(&self) -> bool { let result = self.topology_preparation_result.lock().unwrap(); if let Some(outcome) = result.as_ref() { - match outcome.status { - InterpretStatus::SUCCESS => return true, - _ => return false, - } + matches!(outcome.status, InterpretStatus::SUCCESS) } else { false } diff --git a/harmony/src/domain/score.rs b/harmony/src/domain/score.rs index 0dac87b..a7eb9c7 100644 --- a/harmony/src/domain/score.rs +++ b/harmony/src/domain/score.rs @@ -16,7 +16,7 @@ pub trait SerializeScore { fn serialize(&self) -> Value; } -impl<'de, S, T> SerializeScore for S +impl SerializeScore for S where T: Topology, S: Score + Serialize, @@ -24,7 +24,7 @@ where fn serialize(&self) -> Value { // TODO not sure if this is the right place to handle the error or it should bubble // up? - serde_value::to_value(&self).expect("Score should serialize successfully") + serde_value::to_value(self).expect("Score should serialize successfully") } } diff --git a/harmony/src/domain/topology/k8s.rs b/harmony/src/domain/topology/k8s.rs index 0bf4ead..1314f6a 100644 --- a/harmony/src/domain/topology/k8s.rs +++ b/harmony/src/domain/topology/k8s.rs @@ -1,5 +1,4 @@ use derive_new::new; -use futures_util::StreamExt; use k8s_openapi::{ ClusterResourceScope, NamespaceResourceScope, api::{apps::v1::Deployment, core::v1::Pod}, @@ -18,7 +17,7 @@ use kube::{ }; use log::{debug, error, trace}; use serde::{Serialize, de::DeserializeOwned}; -use similar::{DiffableStr, TextDiff}; +use similar::TextDiff; #[derive(new, Clone)] pub struct K8sClient { @@ -67,13 +66,13 @@ impl K8sClient { } let establish = await_condition(api, name.as_str(), conditions::is_deployment_completed()); - let t = if let Some(t) = timeout { t } else { 300 }; + let t = timeout.unwrap_or(300); let res = tokio::time::timeout(std::time::Duration::from_secs(t), establish).await; - if let Ok(r) = res { - return Ok(()); + if res.is_ok() { + Ok(()) } else { - return Err("timed out while waiting for deployment".to_string()); + Err("timed out while waiting for deployment".to_string()) } } @@ -112,7 +111,7 @@ impl K8sClient { .await; match res { - Err(e) => return Err(e.to_string()), + Err(e) => Err(e.to_string()), Ok(mut process) => { let status = process .take_status() @@ -122,13 +121,9 @@ impl K8sClient { if let Some(s) = status.status { debug!("Status: {}", s); - if s == "Success" { - return Ok(()); - } else { - return Err(s); - } + if s == "Success" { Ok(()) } else { Err(s) } } else { - return Err("Couldn't get inner status of pod exec".to_string()); + Err("Couldn't get inner status of pod exec".to_string()) } } } @@ -169,8 +164,9 @@ impl K8sClient { trace!("Received current value {current:#?}"); // The resource exists, so we calculate and display a diff. println!("\nPerforming dry-run for resource: '{}'", name); - let mut current_yaml = serde_yaml::to_value(¤t) - .expect(&format!("Could not serialize current value : {current:#?}")); + let mut current_yaml = serde_yaml::to_value(¤t).unwrap_or_else(|_| { + panic!("Could not serialize current value : {current:#?}") + }); if current_yaml.is_mapping() && current_yaml.get("status").is_some() { let map = current_yaml.as_mapping_mut().unwrap(); let removed = map.remove_entry("status"); @@ -237,7 +233,7 @@ impl K8sClient { } } - pub async fn apply_many(&self, resource: &Vec, ns: Option<&str>) -> Result, Error> + pub async fn apply_many(&self, resource: &[K], ns: Option<&str>) -> Result, Error> where K: Resource + Clone + std::fmt::Debug + DeserializeOwned + serde::Serialize, ::Scope: ApplyStrategy, @@ -253,7 +249,7 @@ impl K8sClient { pub async fn apply_yaml_many( &self, - yaml: &Vec, + #[allow(clippy::ptr_arg)] yaml: &Vec, ns: Option<&str>, ) -> Result<(), Error> { for y in yaml.iter() { diff --git a/harmony/src/domain/topology/k8s_anywhere.rs b/harmony/src/domain/topology/k8s_anywhere.rs index 1f95204..b5a3da1 100644 --- a/harmony/src/domain/topology/k8s_anywhere.rs +++ b/harmony/src/domain/topology/k8s_anywhere.rs @@ -87,7 +87,9 @@ impl PrometheusApplicationMonitoring for K8sAnywhereTopology { .execute(inventory, self) .await?; - Ok(Outcome::success(format!("No action, working on cluster "))) + Ok(Outcome::success( + "No action, working on cluster ".to_string(), + )) } } @@ -124,7 +126,7 @@ impl K8sAnywhereTopology { ) -> K8sPrometheusCRDAlertingScore { K8sPrometheusCRDAlertingScore { sender, - receivers: receivers.unwrap_or_else(Vec::new), + receivers: receivers.unwrap_or_default(), service_monitors: vec![], prometheus_rules: vec![], } @@ -176,7 +178,7 @@ impl K8sAnywhereTopology { } else { if let Some(kubeconfig) = &k8s_anywhere_config.kubeconfig { debug!("Loading kubeconfig {kubeconfig}"); - match self.try_load_kubeconfig(&kubeconfig).await { + match self.try_load_kubeconfig(kubeconfig).await { Some(client) => { return Ok(Some(K8sState { client: Arc::new(client), @@ -232,7 +234,7 @@ impl K8sAnywhereTopology { } async fn ensure_k8s_tenant_manager(&self) -> Result<(), String> { - if let Some(_) = self.tenant_manager.get() { + if self.tenant_manager.get().is_some() { return Ok(()); } @@ -366,7 +368,7 @@ impl Topology for K8sAnywhereTopology { self.ensure_k8s_tenant_manager() .await - .map_err(|e| InterpretError::new(e))?; + .map_err(InterpretError::new)?; match self.is_helm_available() { Ok(()) => Ok(Outcome::success(format!( diff --git a/harmony/src/domain/topology/mod.rs b/harmony/src/domain/topology/mod.rs index c72a898..72c6c3f 100644 --- a/harmony/src/domain/topology/mod.rs +++ b/harmony/src/domain/topology/mod.rs @@ -88,7 +88,7 @@ impl Serialize for Url { { match self { Url::LocalFolder(path) => serializer.serialize_str(path), - Url::Url(url) => serializer.serialize_str(&url.as_str()), + Url::Url(url) => serializer.serialize_str(url.as_str()), } } } diff --git a/harmony/src/domain/topology/router.rs b/harmony/src/domain/topology/router.rs index de4d313..7c56e6a 100644 --- a/harmony/src/domain/topology/router.rs +++ b/harmony/src/domain/topology/router.rs @@ -27,11 +27,11 @@ pub struct UnmanagedRouter { impl Router for UnmanagedRouter { fn get_gateway(&self) -> IpAddress { - self.gateway.clone() + self.gateway } fn get_cidr(&self) -> Ipv4Cidr { - self.cidr.clone() + self.cidr } fn get_host(&self) -> LogicalHost { diff --git a/harmony/src/domain/topology/tenant/k8s.rs b/harmony/src/domain/topology/tenant/k8s.rs index 417e29c..969d0a9 100644 --- a/harmony/src/domain/topology/tenant/k8s.rs +++ b/harmony/src/domain/topology/tenant/k8s.rs @@ -309,19 +309,19 @@ impl K8sTenantManager { let ports: Option> = c.1.as_ref().map(|spec| match &spec.data { super::PortSpecData::SinglePort(port) => vec![NetworkPolicyPort { - port: Some(IntOrString::Int(port.clone().into())), + port: Some(IntOrString::Int((*port).into())), ..Default::default() }], super::PortSpecData::PortRange(start, end) => vec![NetworkPolicyPort { - port: Some(IntOrString::Int(start.clone().into())), - end_port: Some(end.clone().into()), + port: Some(IntOrString::Int((*start).into())), + end_port: Some((*end).into()), protocol: None, // Not currently supported by Harmony }], super::PortSpecData::ListOfPorts(items) => items .iter() .map(|i| NetworkPolicyPort { - port: Some(IntOrString::Int(i.clone().into())), + port: Some(IntOrString::Int((*i).into())), ..Default::default() }) .collect(), @@ -366,19 +366,19 @@ impl K8sTenantManager { let ports: Option> = c.1.as_ref().map(|spec| match &spec.data { super::PortSpecData::SinglePort(port) => vec![NetworkPolicyPort { - port: Some(IntOrString::Int(port.clone().into())), + port: Some(IntOrString::Int((*port).into())), ..Default::default() }], super::PortSpecData::PortRange(start, end) => vec![NetworkPolicyPort { - port: Some(IntOrString::Int(start.clone().into())), - end_port: Some(end.clone().into()), + port: Some(IntOrString::Int((*start).into())), + end_port: Some((*end).into()), protocol: None, // Not currently supported by Harmony }], super::PortSpecData::ListOfPorts(items) => items .iter() .map(|i| NetworkPolicyPort { - port: Some(IntOrString::Int(i.clone().into())), + port: Some(IntOrString::Int((*i).into())), ..Default::default() }) .collect(), diff --git a/harmony/src/infra/opnsense/dns.rs b/harmony/src/infra/opnsense/dns.rs index 56f8136..d486529 100644 --- a/harmony/src/infra/opnsense/dns.rs +++ b/harmony/src/infra/opnsense/dns.rs @@ -60,7 +60,7 @@ impl DnsServer for OPNSenseFirewall { } fn get_ip(&self) -> IpAddress { - OPNSenseFirewall::get_ip(&self) + OPNSenseFirewall::get_ip(self) } fn get_host(&self) -> LogicalHost { diff --git a/harmony/src/infra/opnsense/http.rs b/harmony/src/infra/opnsense/http.rs index 2650717..a51bf34 100644 --- a/harmony/src/infra/opnsense/http.rs +++ b/harmony/src/infra/opnsense/http.rs @@ -48,7 +48,7 @@ impl HttpServer for OPNSenseFirewall { async fn ensure_initialized(&self) -> Result<(), ExecutorError> { let mut config = self.opnsense_config.write().await; let caddy = config.caddy(); - if let None = caddy.get_full_config() { + if caddy.get_full_config().is_none() { info!("Http config not available in opnsense config, installing package"); config.install_package("os-caddy").await.map_err(|e| { ExecutorError::UnexpectedError(format!( diff --git a/harmony/src/infra/opnsense/load_balancer.rs b/harmony/src/infra/opnsense/load_balancer.rs index cae414a..471348f 100644 --- a/harmony/src/infra/opnsense/load_balancer.rs +++ b/harmony/src/infra/opnsense/load_balancer.rs @@ -121,10 +121,12 @@ pub(crate) fn haproxy_xml_config_to_harmony_loadbalancer( LoadBalancerService { backend_servers, - listening_port: frontend.bind.parse().expect(&format!( - "HAProxy frontend address should be a valid SocketAddr, got {}", - frontend.bind - )), + listening_port: frontend.bind.parse().unwrap_or_else(|_| { + panic!( + "HAProxy frontend address should be a valid SocketAddr, got {}", + frontend.bind + ) + }), health_check, } }) @@ -167,28 +169,28 @@ pub(crate) fn get_health_check_for_backend( None => return None, }; - let haproxy_health_check = match haproxy + let haproxy_health_check = haproxy .healthchecks .healthchecks .iter() - .find(|h| &h.uuid == health_check_uuid) - { - Some(health_check) => health_check, - None => return None, - }; + .find(|h| &h.uuid == health_check_uuid)?; let binding = haproxy_health_check.health_check_type.to_uppercase(); let uppercase = binding.as_str(); match uppercase { "TCP" => { if let Some(checkport) = haproxy_health_check.checkport.content.as_ref() { - if checkport.len() > 0 { - return Some(HealthCheck::TCP(Some(checkport.parse().expect(&format!( - "HAProxy check port should be a valid port number, got {checkport}" - ))))); + if !checkport.is_empty() { + return Some(HealthCheck::TCP(Some(checkport.parse().unwrap_or_else( + |_| { + panic!( + "HAProxy check port should be a valid port number, got {checkport}" + ) + }, + )))); } } - return Some(HealthCheck::TCP(None)); + Some(HealthCheck::TCP(None)) } "HTTP" => { let path: String = haproxy_health_check @@ -355,16 +357,13 @@ mod tests { // Create an HAProxy instance with servers let mut haproxy = HAProxy::default(); - let mut server = HAProxyServer::default(); - server.uuid = "server1".to_string(); - server.address = "192.168.1.1".to_string(); - server.port = 80; - + let server = HAProxyServer { + uuid: "server1".to_string(), + address: "192.168.1.1".to_string(), + port: 80, + ..Default::default() + }; haproxy.servers.servers.push(server); - let mut server = HAProxyServer::default(); - server.uuid = "server3".to_string(); - server.address = "192.168.1.3".to_string(); - server.port = 8080; // Call the function let result = get_servers_for_backend(&backend, &haproxy); @@ -384,10 +383,12 @@ mod tests { let backend = HAProxyBackend::default(); // Create an HAProxy instance with servers let mut haproxy = HAProxy::default(); - let mut server = HAProxyServer::default(); - server.uuid = "server1".to_string(); - server.address = "192.168.1.1".to_string(); - server.port = 80; + let server = HAProxyServer { + uuid: "server1".to_string(), + address: "192.168.1.1".to_string(), + port: 80, + ..Default::default() + }; haproxy.servers.servers.push(server); // Call the function let result = get_servers_for_backend(&backend, &haproxy); @@ -402,10 +403,12 @@ mod tests { backend.linked_servers.content = Some("server4,server5".to_string()); // Create an HAProxy instance with servers let mut haproxy = HAProxy::default(); - let mut server = HAProxyServer::default(); - server.uuid = "server1".to_string(); - server.address = "192.168.1.1".to_string(); - server.port = 80; + let server = HAProxyServer { + uuid: "server1".to_string(), + address: "192.168.1.1".to_string(), + port: 80, + ..Default::default() + }; haproxy.servers.servers.push(server); // Call the function let result = get_servers_for_backend(&backend, &haproxy); @@ -416,20 +419,28 @@ mod tests { #[test] fn test_get_servers_for_backend_multiple_linked_servers() { // Create a backend with multiple linked servers + #[allow(clippy::field_reassign_with_default)] let mut backend = HAProxyBackend::default(); backend.linked_servers.content = Some("server1,server2".to_string()); + // // Create an HAProxy instance with matching servers let mut haproxy = HAProxy::default(); - let mut server = HAProxyServer::default(); - server.uuid = "server1".to_string(); - server.address = "some-hostname.test.mcd".to_string(); - server.port = 80; + let server = HAProxyServer { + uuid: "server1".to_string(), + address: "some-hostname.test.mcd".to_string(), + port: 80, + ..Default::default() + }; haproxy.servers.servers.push(server); - let mut server = HAProxyServer::default(); - server.uuid = "server2".to_string(); - server.address = "192.168.1.2".to_string(); - server.port = 8080; + + let server = HAProxyServer { + uuid: "server2".to_string(), + address: "192.168.1.2".to_string(), + port: 8080, + ..Default::default() + }; haproxy.servers.servers.push(server); + // Call the function let result = get_servers_for_backend(&backend, &haproxy); // Check the result diff --git a/harmony/src/infra/opnsense/tftp.rs b/harmony/src/infra/opnsense/tftp.rs index 6978150..c7b7f2b 100644 --- a/harmony/src/infra/opnsense/tftp.rs +++ b/harmony/src/infra/opnsense/tftp.rs @@ -58,7 +58,7 @@ impl TftpServer for OPNSenseFirewall { async fn ensure_initialized(&self) -> Result<(), ExecutorError> { let mut config = self.opnsense_config.write().await; let tftp = config.tftp(); - if let None = tftp.get_full_config() { + if tftp.get_full_config().is_none() { info!("Tftp config not available in opnsense config, installing package"); config.install_package("os-tftp").await.map_err(|e| { ExecutorError::UnexpectedError(format!( diff --git a/harmony/src/modules/application/feature.rs b/harmony/src/modules/application/feature.rs index 870745e..be4482f 100644 --- a/harmony/src/modules/application/feature.rs +++ b/harmony/src/modules/application/feature.rs @@ -13,7 +13,7 @@ pub trait ApplicationFeature: fn name(&self) -> String; } -trait ApplicationFeatureClone { +pub trait ApplicationFeatureClone { fn clone_box(&self) -> Box>; } @@ -27,7 +27,7 @@ where } impl Serialize for Box> { - fn serialize(&self, serializer: S) -> Result + fn serialize(&self, _serializer: S) -> Result where S: serde::Serializer, { diff --git a/harmony/src/modules/application/features/argo_types.rs b/harmony/src/modules/application/features/argo_types.rs index 6eba4b7..f36d424 100644 --- a/harmony/src/modules/application/features/argo_types.rs +++ b/harmony/src/modules/application/features/argo_types.rs @@ -184,12 +184,11 @@ impl ArgoApplication { pub fn to_yaml(&self) -> serde_yaml::Value { let name = &self.name; let namespace = if let Some(ns) = self.namespace.as_ref() { - &ns + ns } else { "argocd" }; let project = &self.project; - let source = &self.source; let yaml_str = format!( r#" @@ -228,7 +227,7 @@ spec: serde_yaml::to_value(&self.source).expect("couldn't serialize source to value"); let sync_policy = serde_yaml::to_value(&self.sync_policy) .expect("couldn't serialize sync_policy to value"); - let revision_history_limit = serde_yaml::to_value(&self.revision_history_limit) + let revision_history_limit = serde_yaml::to_value(self.revision_history_limit) .expect("couldn't serialize revision_history_limit to value"); spec.insert( diff --git a/harmony/src/modules/application/features/continuous_delivery.rs b/harmony/src/modules/application/features/continuous_delivery.rs index 065f0ee..de778fb 100644 --- a/harmony/src/modules/application/features/continuous_delivery.rs +++ b/harmony/src/modules/application/features/continuous_delivery.rs @@ -10,7 +10,7 @@ use crate::{ data::Version, inventory::Inventory, modules::application::{ - Application, ApplicationFeature, HelmPackage, OCICompliant, + ApplicationFeature, HelmPackage, OCICompliant, features::{ArgoApplication, ArgoHelmScore}, }, score::Score, diff --git a/harmony/src/modules/application/features/helm_argocd_score.rs b/harmony/src/modules/application/features/helm_argocd_score.rs index b87b463..ff79740 100644 --- a/harmony/src/modules/application/features/helm_argocd_score.rs +++ b/harmony/src/modules/application/features/helm_argocd_score.rs @@ -986,7 +986,7 @@ commitServer: ); HelmChartScore { - namespace: Some(NonBlankString::from_str(&namespace).unwrap()), + namespace: Some(NonBlankString::from_str(namespace).unwrap()), release_name: NonBlankString::from_str("argo-cd").unwrap(), chart_name: NonBlankString::from_str("argo/argo-cd").unwrap(), chart_version: Some(NonBlankString::from_str("8.1.2").unwrap()), diff --git a/harmony/src/modules/application/mod.rs b/harmony/src/modules/application/mod.rs index ec00834..3e70e78 100644 --- a/harmony/src/modules/application/mod.rs +++ b/harmony/src/modules/application/mod.rs @@ -81,7 +81,7 @@ impl Interpret for Application } impl Serialize for dyn Application { - fn serialize(&self, serializer: S) -> Result + fn serialize(&self, _serializer: S) -> Result where S: serde::Serializer, { diff --git a/harmony/src/modules/application/rust.rs b/harmony/src/modules/application/rust.rs index 6fc72cb..4f30e3e 100644 --- a/harmony/src/modules/application/rust.rs +++ b/harmony/src/modules/application/rust.rs @@ -1,5 +1,5 @@ use std::fs; -use std::path::PathBuf; +use std::path::{Path, PathBuf}; use std::process; use std::sync::Arc; @@ -174,7 +174,7 @@ impl RustWebapp { .platform("linux/x86_64"); let mut temp_tar_builder = tar::Builder::new(Vec::new()); - let _ = temp_tar_builder + temp_tar_builder .append_dir_all("", self.project_root.clone()) .unwrap(); let archive = temp_tar_builder @@ -530,10 +530,7 @@ spec: } /// Packages a Helm chart directory into a .tgz file. - fn package_helm_chart( - &self, - chart_dir: &PathBuf, - ) -> Result> { + fn package_helm_chart(&self, chart_dir: &Path) -> Result> { let chart_dirname = chart_dir.file_name().expect("Should find a chart dirname"); debug!( "Launching `helm package {}` cli with CWD {}", @@ -546,14 +543,13 @@ spec: ); let output = process::Command::new("helm") .args(["package", chart_dirname.to_str().unwrap()]) - .current_dir(&self.project_root.join(".harmony_generated").join("helm")) // Run package from the parent dir + .current_dir(self.project_root.join(".harmony_generated").join("helm")) // Run package from the parent dir .output()?; self.check_output(&output, "Failed to package Helm chart")?; // Helm prints the path of the created chart to stdout. let tgz_name = String::from_utf8(output.stdout)? - .trim() .split_whitespace() .last() .unwrap_or_default() @@ -573,7 +569,7 @@ spec: /// Pushes a packaged Helm chart to an OCI registry. fn push_helm_chart( &self, - packaged_chart_path: &PathBuf, + packaged_chart_path: &Path, ) -> Result> { // The chart name is the file stem of the .tgz file let chart_file_name = packaged_chart_path.file_stem().unwrap().to_str().unwrap(); diff --git a/harmony/src/modules/cert_manager/helm.rs b/harmony/src/modules/cert_manager/helm.rs index 9a2521c..eae0ed6 100644 --- a/harmony/src/modules/cert_manager/helm.rs +++ b/harmony/src/modules/cert_manager/helm.rs @@ -41,6 +41,6 @@ impl Score for CertManagerHelmScore { } fn name(&self) -> String { - format!("CertManagerHelmScore") + "CertManagerHelmScore".to_string() } } diff --git a/harmony/src/modules/dhcp.rs b/harmony/src/modules/dhcp.rs index 0112b41..04ef093 100644 --- a/harmony/src/modules/dhcp.rs +++ b/harmony/src/modules/dhcp.rs @@ -111,7 +111,7 @@ impl DhcpInterpret { let boot_filename_outcome = match &self.score.boot_filename { Some(boot_filename) => { - dhcp_server.set_boot_filename(&boot_filename).await?; + dhcp_server.set_boot_filename(boot_filename).await?; Outcome::new( InterpretStatus::SUCCESS, format!("Dhcp Interpret Set boot filename to {boot_filename}"), @@ -122,7 +122,7 @@ impl DhcpInterpret { let filename_outcome = match &self.score.filename { Some(filename) => { - dhcp_server.set_filename(&filename).await?; + dhcp_server.set_filename(filename).await?; Outcome::new( InterpretStatus::SUCCESS, format!("Dhcp Interpret Set filename to {filename}"), @@ -133,7 +133,7 @@ impl DhcpInterpret { let filename64_outcome = match &self.score.filename64 { Some(filename64) => { - dhcp_server.set_filename64(&filename64).await?; + dhcp_server.set_filename64(filename64).await?; Outcome::new( InterpretStatus::SUCCESS, format!("Dhcp Interpret Set filename64 to {filename64}"), @@ -144,7 +144,7 @@ impl DhcpInterpret { let filenameipxe_outcome = match &self.score.filenameipxe { Some(filenameipxe) => { - dhcp_server.set_filenameipxe(&filenameipxe).await?; + dhcp_server.set_filenameipxe(filenameipxe).await?; Outcome::new( InterpretStatus::SUCCESS, format!("Dhcp Interpret Set filenameipxe to {filenameipxe}"), @@ -209,7 +209,7 @@ impl Interpret for DhcpInterpret { Ok(Outcome::new( InterpretStatus::SUCCESS, - format!("Dhcp Interpret execution successful"), + "Dhcp Interpret execution successful".to_string(), )) } } diff --git a/harmony/src/modules/dns.rs b/harmony/src/modules/dns.rs index e52e2f9..07b883d 100644 --- a/harmony/src/modules/dns.rs +++ b/harmony/src/modules/dns.rs @@ -112,7 +112,7 @@ impl Interpret for DnsInterpret { Ok(Outcome::new( InterpretStatus::SUCCESS, - format!("Dns Interpret execution successful"), + "Dns Interpret execution successful".to_string(), )) } } diff --git a/harmony/src/modules/helm/chart.rs b/harmony/src/modules/helm/chart.rs index 309bd1e..c4321d4 100644 --- a/harmony/src/modules/helm/chart.rs +++ b/harmony/src/modules/helm/chart.rs @@ -90,14 +90,10 @@ impl HelmChartInterpret { ); match add_output.status.success() { - true => { - return Ok(()); - } - false => { - return Err(InterpretError::new(format!( - "Failed to add helm repository!\n{full_output}" - ))); - } + true => Ok(()), + false => Err(InterpretError::new(format!( + "Failed to add helm repository!\n{full_output}" + ))), } } } @@ -212,7 +208,7 @@ impl Interpret for HelmChartInterpret { } let res = helm_executor.install_or_upgrade( - &ns, + ns, &self.score.release_name, &self.score.chart_name, self.score.chart_version.as_ref(), diff --git a/harmony/src/modules/helm/command.rs b/harmony/src/modules/helm/command.rs index 14d2fc1..60c6fb6 100644 --- a/harmony/src/modules/helm/command.rs +++ b/harmony/src/modules/helm/command.rs @@ -77,14 +77,11 @@ impl HelmCommandExecutor { )?; } - let out = match self.clone().run_command( + let out = self.clone().run_command( self.chart .clone() .helm_args(self.globals.chart_home.clone().unwrap()), - ) { - Ok(out) => out, - Err(e) => return Err(e), - }; + )?; // TODO: don't use unwrap here let s = String::from_utf8(out.stdout).unwrap(); @@ -98,14 +95,11 @@ impl HelmCommandExecutor { } pub fn version(self) -> Result { - let out = match self.run_command(vec![ + let out = self.run_command(vec![ "version".to_string(), "-c".to_string(), "--short".to_string(), - ]) { - Ok(out) => out, - Err(e) => return Err(e), - }; + ])?; // TODO: don't use unwrap Ok(String::from_utf8(out.stdout).unwrap()) @@ -129,15 +123,11 @@ impl HelmCommandExecutor { None => PathBuf::from(TempDir::new()?.path()), }; - match self.chart.values_inline { - Some(yaml_str) => { - let tf: TempFile; - tf = temp_file::with_contents(yaml_str.as_bytes()); - self.chart - .additional_values_files - .push(PathBuf::from(tf.path())); - } - None => (), + if let Some(yaml_str) = self.chart.values_inline { + let tf: TempFile = temp_file::with_contents(yaml_str.as_bytes()); + self.chart + .additional_values_files + .push(PathBuf::from(tf.path())); }; self.env.insert( @@ -180,9 +170,9 @@ impl HelmChart { match self.repo { Some(r) => { if r.starts_with("oci://") { - args.push(String::from( + args.push( r.trim_end_matches("/").to_string() + "/" + self.name.clone().as_str(), - )); + ); } else { args.push("--repo".to_string()); args.push(r.to_string()); @@ -193,12 +183,9 @@ impl HelmChart { None => args.push(self.name), }; - match self.version { - Some(v) => { - args.push("--version".to_string()); - args.push(v.to_string()); - } - None => (), + if let Some(v) = self.version { + args.push("--version".to_string()); + args.push(v.to_string()); } args diff --git a/harmony/src/modules/k3d/install.rs b/harmony/src/modules/k3d/install.rs index 6441305..9490dee 100644 --- a/harmony/src/modules/k3d/install.rs +++ b/harmony/src/modules/k3d/install.rs @@ -1,7 +1,7 @@ use std::path::PathBuf; use async_trait::async_trait; -use log::{debug, info}; +use log::debug; use serde::Serialize; use crate::{ diff --git a/harmony/src/modules/lamp.rs b/harmony/src/modules/lamp.rs index 3c5c439..29228d8 100644 --- a/harmony/src/modules/lamp.rs +++ b/harmony/src/modules/lamp.rs @@ -135,6 +135,8 @@ impl Interpret for LAMPInterpret { info!("LAMP deployment_score {deployment_score:?}"); + let ingress_path = ingress_path!("/"); + let lamp_ingress = K8sIngressScore { name: fqdn!("lamp-ingress"), host: fqdn!("test"), @@ -144,7 +146,7 @@ impl Interpret for LAMPInterpret { .as_str() ), port: 8080, - path: Some(ingress_path!("/")), + path: Some(ingress_path), path_type: None, namespace: self .get_namespace() diff --git a/harmony/src/modules/monitoring/alert_rule/prometheus_alert_rule.rs b/harmony/src/modules/monitoring/alert_rule/prometheus_alert_rule.rs index c0627b8..e001c68 100644 --- a/harmony/src/modules/monitoring/alert_rule/prometheus_alert_rule.rs +++ b/harmony/src/modules/monitoring/alert_rule/prometheus_alert_rule.rs @@ -18,7 +18,7 @@ use crate::{ #[async_trait] impl AlertRule for AlertManagerRuleGroup { async fn install(&self, sender: &KubePrometheus) -> Result { - sender.install_rule(&self).await + sender.install_rule(self).await } fn clone_box(&self) -> Box> { Box::new(self.clone()) @@ -28,7 +28,7 @@ impl AlertRule for AlertManagerRuleGroup { #[async_trait] impl AlertRule for AlertManagerRuleGroup { async fn install(&self, sender: &Prometheus) -> Result { - sender.install_rule(&self).await + sender.install_rule(self).await } fn clone_box(&self) -> Box> { Box::new(self.clone()) diff --git a/harmony/src/modules/monitoring/grafana/helm/helm_grafana.rs b/harmony/src/modules/monitoring/grafana/helm/helm_grafana.rs index c53fe3f..3af6550 100644 --- a/harmony/src/modules/monitoring/grafana/helm/helm_grafana.rs +++ b/harmony/src/modules/monitoring/grafana/helm/helm_grafana.rs @@ -4,15 +4,14 @@ use std::str::FromStr; use crate::modules::helm::chart::HelmChartScore; pub fn grafana_helm_chart_score(ns: &str) -> HelmChartScore { - let values = format!( - r#" + let values = r#" rbac: namespaced: true sidecar: dashboards: enabled: true "# - ); + .to_string(); HelmChartScore { namespace: Some(NonBlankString::from_str(ns).unwrap()), diff --git a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_alertmanagers.rs b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_alertmanagers.rs index 637490d..12238d6 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_alertmanagers.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_alertmanagers.rs @@ -1,7 +1,6 @@ use kube::CustomResource; use schemars::JsonSchema; use serde::{Deserialize, Serialize}; -use std::collections::BTreeMap; use super::crd_prometheuses::LabelSelector; diff --git a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_default_rules.rs b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_default_rules.rs index a245a86..014650c 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_default_rules.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_default_rules.rs @@ -1,13 +1,8 @@ -use std::collections::BTreeMap; - -use crate::modules::{ - monitoring::alert_rule::prometheus_alert_rule::PrometheusAlertRule, - prometheus::alerts::k8s::{ - deployment::alert_deployment_unavailable, - pod::{alert_container_restarting, alert_pod_not_ready, pod_failed}, - pvc::high_pvc_fill_rate_over_two_days, - service::alert_service_down, - }, +use crate::modules::prometheus::alerts::k8s::{ + deployment::alert_deployment_unavailable, + pod::{alert_container_restarting, alert_pod_not_ready, pod_failed}, + pvc::high_pvc_fill_rate_over_two_days, + service::alert_service_down, }; use super::crd_prometheus_rules::Rule; diff --git a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_prometheus_rules.rs b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_prometheus_rules.rs index c0ee69e..6d08456 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/crd/crd_prometheus_rules.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/crd/crd_prometheus_rules.rs @@ -6,8 +6,6 @@ use serde::{Deserialize, Serialize}; use crate::modules::monitoring::alert_rule::prometheus_alert_rule::PrometheusAlertRule; -use super::crd_default_rules::build_default_application_rules; - #[derive(CustomResource, Debug, Serialize, Deserialize, Clone, JsonSchema)] #[kube( group = "monitoring.coreos.com", diff --git a/harmony/src/modules/monitoring/kube_prometheus/crd/service_monitor.rs b/harmony/src/modules/monitoring/kube_prometheus/crd/service_monitor.rs index 7c613e7..072c979 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/crd/service_monitor.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/crd/service_monitor.rs @@ -1,11 +1,9 @@ -use std::collections::{BTreeMap, HashMap}; +use std::collections::HashMap; -use kube::{CustomResource, Resource, api::ObjectMeta}; +use kube::CustomResource; use schemars::JsonSchema; use serde::{Deserialize, Serialize}; -use crate::interpret::InterpretError; - use crate::modules::monitoring::kube_prometheus::types::{ HTTPScheme, MatchExpression, NamespaceSelector, Operator, Selector, ServiceMonitor as KubeServiceMonitor, ServiceMonitorEndpoint, @@ -50,7 +48,7 @@ pub struct ServiceMonitorSpec { impl Default for ServiceMonitorSpec { fn default() -> Self { - let mut labels = HashMap::new(); + let labels = HashMap::new(); Self { selector: Selector { match_labels: { labels }, diff --git a/harmony/src/modules/monitoring/kube_prometheus/helm/config.rs b/harmony/src/modules/monitoring/kube_prometheus/helm/config.rs index 3c4fa37..e00bf16 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/helm/config.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/helm/config.rs @@ -27,6 +27,12 @@ pub struct KubePrometheusConfig { pub alert_rules: Vec, pub additional_service_monitors: Vec, } +impl Default for KubePrometheusConfig { + fn default() -> Self { + Self::new() + } +} + impl KubePrometheusConfig { pub fn new() -> Self { Self { diff --git a/harmony/src/modules/monitoring/kube_prometheus/helm/kube_prometheus_helm_chart.rs b/harmony/src/modules/monitoring/kube_prometheus/helm/kube_prometheus_helm_chart.rs index 51e918c..7d6aec8 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/helm/kube_prometheus_helm_chart.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/helm/kube_prometheus_helm_chart.rs @@ -35,7 +35,7 @@ pub fn kube_prometheus_helm_chart_score( let kube_proxy = config.kube_proxy.to_string(); let kube_state_metrics = config.kube_state_metrics.to_string(); let node_exporter = config.node_exporter.to_string(); - let prometheus_operator = config.prometheus_operator.to_string(); + let _prometheus_operator = config.prometheus_operator.to_string(); let prometheus = config.prometheus.to_string(); let resource_limit = Resources { limits: Limits { @@ -64,7 +64,7 @@ pub fn kube_prometheus_helm_chart_score( indent_lines(&yaml, indent_level + 2) ) } - let resource_section = resource_block(&resource_limit, 2); + let _resource_section = resource_block(&resource_limit, 2); let mut values = format!( r#" diff --git a/harmony/src/modules/monitoring/kube_prometheus/prometheus.rs b/harmony/src/modules/monitoring/kube_prometheus/prometheus.rs index 137ad6f..4cf2b47 100644 --- a/harmony/src/modules/monitoring/kube_prometheus/prometheus.rs +++ b/harmony/src/modules/monitoring/kube_prometheus/prometheus.rs @@ -55,6 +55,12 @@ pub struct KubePrometheus { pub config: Arc>, } +impl Default for KubePrometheus { + fn default() -> Self { + Self::new() + } +} + impl KubePrometheus { pub fn new() -> Self { Self { diff --git a/harmony/src/modules/monitoring/ntfy/mod.rs b/harmony/src/modules/monitoring/ntfy/mod.rs index df90432..d43aa95 100644 --- a/harmony/src/modules/monitoring/ntfy/mod.rs +++ b/harmony/src/modules/monitoring/ntfy/mod.rs @@ -1,2 +1,3 @@ pub mod helm; +#[allow(clippy::module_inception)] pub mod ntfy; diff --git a/harmony/src/modules/monitoring/ntfy/ntfy.rs b/harmony/src/modules/monitoring/ntfy/ntfy.rs index 773b0ad..a640bf4 100644 --- a/harmony/src/modules/monitoring/ntfy/ntfy.rs +++ b/harmony/src/modules/monitoring/ntfy/ntfy.rs @@ -28,7 +28,7 @@ impl Score for NtfyScore { } fn name(&self) -> String { - format!("Ntfy") + "Ntfy".to_string() } } @@ -39,31 +39,21 @@ pub struct NtfyInterpret { #[derive(Debug, EnumString, Display)] enum NtfyAccessMode { - #[strum(serialize = "read-write", serialize = "rw", to_string = "read-write")] + #[strum(serialize = "read-write", serialize = "rw")] ReadWrite, - #[strum( - serialize = "read-only", - serialize = "ro", - serialize = "read", - to_string = "read-only" - )] + #[strum(serialize = "read-only", serialize = "ro", serialize = "read")] ReadOnly, - #[strum( - serialize = "write-only", - serialize = "wo", - serialize = "write", - to_string = "write-only" - )] + #[strum(serialize = "write-only", serialize = "wo", serialize = "write")] WriteOnly, - #[strum(serialize = "none", to_string = "deny")] + #[strum(serialize = "deny", serialize = "none")] Deny, } #[derive(Debug, EnumString, Display)] enum NtfyRole { - #[strum(serialize = "user", to_string = "user")] + #[strum(serialize = "user")] User, - #[strum(serialize = "admin", to_string = "admin")] + #[strum(serialize = "admin")] Admin, } @@ -95,28 +85,6 @@ impl NtfyInterpret { Ok(()) } - - async fn set_access( - &self, - k8s_client: Arc, - username: &str, - topic: &str, - mode: NtfyAccessMode, - ) -> Result<(), String> { - k8s_client - .exec_app( - "ntfy".to_string(), - Some(&self.score.namespace), - vec![ - "sh", - "-c", - format!("ntfy access {username} {topic} {mode}").as_str(), - ], - ) - .await?; - - Ok(()) - } } /// We need a ntfy interpret to wrap the HelmChartScore in order to run the score, and then bootstrap the config inside ntfy @@ -141,7 +109,7 @@ impl Interpret for NtfyInterpret { client .wait_until_deployment_ready( "ntfy".to_string(), - Some(&self.score.namespace.as_str()), + Some(self.score.namespace.as_str()), None, ) .await?; diff --git a/harmony/src/modules/monitoring/prometheus/mod.rs b/harmony/src/modules/monitoring/prometheus/mod.rs index 93b3b11..d1bda0e 100644 --- a/harmony/src/modules/monitoring/prometheus/mod.rs +++ b/harmony/src/modules/monitoring/prometheus/mod.rs @@ -1,3 +1,4 @@ pub mod helm; +#[allow(clippy::module_inception)] pub mod prometheus; pub mod prometheus_config; diff --git a/harmony/src/modules/monitoring/prometheus/prometheus.rs b/harmony/src/modules/monitoring/prometheus/prometheus.rs index 4e6a981..934f1ae 100644 --- a/harmony/src/modules/monitoring/prometheus/prometheus.rs +++ b/harmony/src/modules/monitoring/prometheus/prometheus.rs @@ -37,6 +37,12 @@ impl AlertSender for Prometheus { } } +impl Default for Prometheus { + fn default() -> Self { + Self::new() + } +} + impl Prometheus { pub fn new() -> Self { Self { @@ -114,9 +120,9 @@ impl Prometheus { .execute(inventory, topology) .await } else { - Err(InterpretError::new(format!( - "could not install grafana, missing namespace", - ))) + Err(InterpretError::new( + "could not install grafana, missing namespace".to_string(), + )) } } } diff --git a/harmony/src/modules/monitoring/prometheus/prometheus_config.rs b/harmony/src/modules/monitoring/prometheus/prometheus_config.rs index fc5449c..32c3fab 100644 --- a/harmony/src/modules/monitoring/prometheus/prometheus_config.rs +++ b/harmony/src/modules/monitoring/prometheus/prometheus_config.rs @@ -16,6 +16,12 @@ pub struct PrometheusConfig { pub additional_service_monitors: Vec, } +impl Default for PrometheusConfig { + fn default() -> Self { + Self::new() + } +} + impl PrometheusConfig { pub fn new() -> Self { Self { diff --git a/harmony/src/modules/okd/bootstrap_dhcp.rs b/harmony/src/modules/okd/bootstrap_dhcp.rs index c133ecf..c7ffe7d 100644 --- a/harmony/src/modules/okd/bootstrap_dhcp.rs +++ b/harmony/src/modules/okd/bootstrap_dhcp.rs @@ -32,7 +32,7 @@ impl OKDBootstrapDhcpScore { logical_host: topology.bootstrap_host.clone(), physical_host: inventory .worker_host - .get(0) + .first() .expect("Should have at least one worker to be used as bootstrap node") .clone(), }); diff --git a/harmony/src/modules/okd/upgrade.rs b/harmony/src/modules/okd/upgrade.rs index 5115cfb..9ed36e1 100644 --- a/harmony/src/modules/okd/upgrade.rs +++ b/harmony/src/modules/okd/upgrade.rs @@ -6,6 +6,12 @@ pub struct OKDUpgradeScore { _target_version: Version, } +impl Default for OKDUpgradeScore { + fn default() -> Self { + Self::new() + } +} + impl OKDUpgradeScore { pub fn new() -> Self { Self { diff --git a/harmony/src/modules/prometheus/k8s_prometheus_alerting_score.rs b/harmony/src/modules/prometheus/k8s_prometheus_alerting_score.rs index 2aace1f..e806c63 100644 --- a/harmony/src/modules/prometheus/k8s_prometheus_alerting_score.rs +++ b/harmony/src/modules/prometheus/k8s_prometheus_alerting_score.rs @@ -93,9 +93,9 @@ impl> I self.install_rules(&self.prometheus_rules, &client).await?; self.install_monitors(self.service_monitors.clone(), &client) .await?; - Ok(Outcome::success(format!( - "deployed application monitoring composants" - ))) + Ok(Outcome::success( + "deployed application monitoring composants".to_string(), + )) } fn get_name(&self) -> InterpretName { @@ -415,7 +415,7 @@ impl K8sPrometheusCRDAlertingInterpret { async fn install_rules( &self, - rules: &Vec, + #[allow(clippy::ptr_arg)] rules: &Vec, client: &Arc, ) -> Result { let mut prom_rule_spec = PrometheusRuleSpec { @@ -423,7 +423,7 @@ impl K8sPrometheusCRDAlertingInterpret { }; let default_rules_group = RuleGroup { - name: format!("default-rules"), + name: "default-rules".to_string(), rules: build_default_application_rules(), }; diff --git a/harmony/src/modules/prometheus/mod.rs b/harmony/src/modules/prometheus/mod.rs index a59eadc..b77f199 100644 --- a/harmony/src/modules/prometheus/mod.rs +++ b/harmony/src/modules/prometheus/mod.rs @@ -1,3 +1,4 @@ pub mod alerts; pub mod k8s_prometheus_alerting_score; +#[allow(clippy::module_inception)] pub mod prometheus; diff --git a/harmony_cli/src/cli_logger.rs b/harmony_cli/src/cli_logger.rs index ebe8f09..a35f450 100644 --- a/harmony_cli/src/cli_logger.rs +++ b/harmony_cli/src/cli_logger.rs @@ -2,7 +2,7 @@ use harmony::instrumentation::{self, HarmonyEvent}; use indicatif::{MultiProgress, ProgressBar}; use indicatif_log_bridge::LogWrapper; use std::{ - collections::{HashMap, hash_map}, + collections::HashMap, sync::{Arc, Mutex}, }; diff --git a/harmony_cli/src/lib.rs b/harmony_cli/src/lib.rs index 1fea271..b6cf885 100644 --- a/harmony_cli/src/lib.rs +++ b/harmony_cli/src/lib.rs @@ -11,8 +11,6 @@ pub mod progress; pub mod theme; #[cfg(feature = "tui")] -use harmony_tui; - #[derive(Parser, Debug)] #[command(version, about, long_about = None)] pub struct Args { @@ -73,7 +71,7 @@ fn maestro_scores_filter( } }; - return scores_vec; + scores_vec } // TODO: consider adding doctest for this function @@ -83,7 +81,7 @@ fn list_scores_with_index(scores_vec: &Vec>>) -> S let name = s.name(); display_str.push_str(&format!("\n{i}: {name}")); } - return display_str; + display_str } pub async fn run( @@ -126,7 +124,7 @@ async fn init( let scores_vec = maestro_scores_filter(&maestro, args.all, args.filter, args.number); - if scores_vec.len() == 0 { + if scores_vec.is_empty() { return Err("No score found".into()); } @@ -265,7 +263,7 @@ mod test { assert!( maestro - .interpret(res.get(0).unwrap().clone_box()) + .interpret(res.first().unwrap().clone_box()) .await .is_ok() ); @@ -281,7 +279,7 @@ mod test { assert!( maestro - .interpret(res.get(0).unwrap().clone_box()) + .interpret(res.first().unwrap().clone_box()) .await .is_err() ); @@ -297,7 +295,7 @@ mod test { assert!( maestro - .interpret(res.get(0).unwrap().clone_box()) + .interpret(res.first().unwrap().clone_box()) .await .is_ok() ); @@ -319,7 +317,7 @@ mod test { assert!( maestro - .interpret(res.get(0).unwrap().clone_box()) + .interpret(res.first().unwrap().clone_box()) .await .is_ok() ); @@ -331,6 +329,6 @@ mod test { let res = crate::maestro_scores_filter(&maestro, false, None, 11); - assert!(res.len() == 0); + assert!(res.is_empty()); } } diff --git a/harmony_composer/src/harmony_composer_logger.rs b/harmony_composer/src/harmony_composer_logger.rs index d8003e6..00e0fb7 100644 --- a/harmony_composer/src/harmony_composer_logger.rs +++ b/harmony_composer/src/harmony_composer_logger.rs @@ -95,7 +95,7 @@ pub async fn handle_events() { )); (*progresses_guard).insert(PROGRESS_DEPLOYMENT.to_string(), multi_progress); } - HarmonyComposerEvent::DeploymentCompleted { details } => println!("\n"), + HarmonyComposerEvent::DeploymentCompleted => println!("\n"), HarmonyComposerEvent::Shutdown => { for (_, progresses) in (*progresses_guard).iter() { progresses.clear().unwrap(); diff --git a/harmony_composer/src/instrumentation.rs b/harmony_composer/src/instrumentation.rs index f1cdc8f..eafa4d0 100644 --- a/harmony_composer/src/instrumentation.rs +++ b/harmony_composer/src/instrumentation.rs @@ -11,7 +11,7 @@ pub enum HarmonyComposerEvent { ProjectCompiled, ProjectCompilationFailed { details: String }, DeploymentStarted { target: String }, - DeploymentCompleted { details: String }, + DeploymentCompleted, Shutdown, } diff --git a/harmony_composer/src/main.rs b/harmony_composer/src/main.rs index 4ccccf6..8866b4a 100644 --- a/harmony_composer/src/main.rs +++ b/harmony_composer/src/main.rs @@ -80,14 +80,13 @@ async fn main() { instrumentation::instrument(HarmonyComposerEvent::ProjectInitializationStarted).unwrap(); let harmony_bin_path: PathBuf = match harmony_path { - true => { - compile_harmony( - cli_args.compile_method, - cli_args.compile_platform, - cli_args.harmony_path.clone(), - ) - .await - } + true => compile_harmony( + cli_args.compile_method, + cli_args.compile_platform, + cli_args.harmony_path.clone(), + ) + .await + .expect("couldn't compile harmony"), false => todo!("implement autodetect code"), }; @@ -145,10 +144,9 @@ async fn main() { .expect("failed to run harmony deploy"); let deploy_output = deploy.wait_with_output().unwrap(); - instrumentation::instrument(HarmonyComposerEvent::DeploymentCompleted { - details: String::from_utf8(deploy_output.stdout).unwrap(), - }) - .unwrap(); + debug!("{}", String::from_utf8(deploy_output.stdout).unwrap()); + + instrumentation::instrument(HarmonyComposerEvent::DeploymentCompleted).unwrap(); } Commands::All(_args) => todo!( "take all previous match arms and turn them into separate functions, and call them all one after the other" @@ -173,7 +171,7 @@ async fn compile_harmony( method: Option, platform: Option, harmony_location: String, -) -> PathBuf { +) -> Result { let platform = match platform { Some(p) => p, None => current_platform::CURRENT_PLATFORM.to_string(), @@ -203,6 +201,7 @@ async fn compile_harmony( details: "compiling project with cargo".to_string(), }) .unwrap(); + compile_cargo(platform, harmony_location).await } CompileMethod::Docker => { @@ -210,16 +209,28 @@ async fn compile_harmony( details: "compiling project with docker".to_string(), }) .unwrap(); + compile_docker(platform, harmony_location).await } }; - instrumentation::instrument(HarmonyComposerEvent::ProjectCompiled).unwrap(); - path + match path { + Ok(path) => { + instrumentation::instrument(HarmonyComposerEvent::ProjectCompiled).unwrap(); + Ok(path) + } + Err(err) => { + instrumentation::instrument(HarmonyComposerEvent::ProjectCompilationFailed { + details: err.clone(), + }) + .unwrap(); + Err(err) + } + } } // TODO: make sure this works with cargo workspaces -async fn compile_cargo(platform: String, harmony_location: String) -> PathBuf { +async fn compile_cargo(platform: String, harmony_location: String) -> Result { let metadata = MetadataCommand::new() .manifest_path(format!("{}/Cargo.toml", harmony_location)) .exec() @@ -268,7 +279,10 @@ async fn compile_cargo(platform: String, harmony_location: String) -> PathBuf { } } - cargo_build.wait().expect("run cargo command failed"); + let res = cargo_build.wait(); //.expect("run cargo command failed"); + if res.is_err() { + return Err("cargo build failed".into()); + } let bin = artifacts .last() @@ -286,10 +300,10 @@ async fn compile_cargo(platform: String, harmony_location: String) -> PathBuf { let _copy_res = fs::copy(&bin, &bin_out).await; } - bin_out + Ok(bin_out) } -async fn compile_docker(platform: String, harmony_location: String) -> PathBuf { +async fn compile_docker(platform: String, harmony_location: String) -> Result { let docker_client = bollard::Docker::connect_with_local_defaults().expect("couldn't connect to docker"); @@ -305,7 +319,7 @@ async fn compile_docker(platform: String, harmony_location: String) -> PathBuf { .await .expect("list containers failed"); - if containers.len() > 0 { + if !containers.is_empty() { docker_client .remove_container("harmony_build", None::) .await @@ -367,12 +381,12 @@ async fn compile_docker(platform: String, harmony_location: String) -> PathBuf { } // wait until container is no longer running - while let Some(_) = wait.next().await {} + while (wait.next().await).is_some() {} // hack that should be cleaned up if platform.contains("windows") { - return PathBuf::from(format!("{}/harmony.exe", harmony_location)); + Ok(PathBuf::from(format!("{}/harmony.exe", harmony_location))) } else { - return PathBuf::from(format!("{}/harmony", harmony_location)); + Ok(PathBuf::from(format!("{}/harmony", harmony_location))) } } diff --git a/harmony_macros/src/lib.rs b/harmony_macros/src/lib.rs index 7a2748d..2f77d1a 100644 --- a/harmony_macros/src/lib.rs +++ b/harmony_macros/src/lib.rs @@ -11,13 +11,13 @@ pub fn ip(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as LitStr); let ip_str = input.value(); - if let Ok(_) = ip_str.parse::() { + if ip_str.parse::().is_ok() { let expanded = quote! { std::net::IpAddr::V4(#ip_str.parse::().unwrap()) }; return TokenStream::from(expanded); } - if let Ok(_) = ip_str.parse::() { + if ip_str.parse::().is_ok() { let expanded = quote! { std::net::IpAddr::V6(#ip_str.parse::().unwrap()) }; return TokenStream::from(expanded); @@ -31,7 +31,7 @@ pub fn ipv4(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as LitStr); let ip_str = input.value(); - if let Ok(_) = ip_str.parse::() { + if ip_str.parse::().is_ok() { let expanded = quote! { #ip_str.parse::().unwrap() }; return TokenStream::from(expanded); } @@ -127,7 +127,7 @@ pub fn ingress_path(input: TokenStream) -> TokenStream { match path_str.starts_with("/") { true => { let expanded = quote! {(#path_str.to_string()) }; - return TokenStream::from(expanded); + TokenStream::from(expanded) } false => panic!("Invalid ingress path"), } @@ -138,7 +138,7 @@ pub fn cidrv4(input: TokenStream) -> TokenStream { let input = parse_macro_input!(input as LitStr); let cidr_str = input.value(); - if let Ok(_) = cidr_str.parse::() { + if cidr_str.parse::().is_ok() { let expanded = quote! { #cidr_str.parse::().unwrap() }; return TokenStream::from(expanded); } diff --git a/harmony_tui/src/widget/score.rs b/harmony_tui/src/widget/score.rs index 57a93fe..bd8f670 100644 --- a/harmony_tui/src/widget/score.rs +++ b/harmony_tui/src/widget/score.rs @@ -14,9 +14,9 @@ use tokio::sync::mpsc; #[derive(Debug)] enum ExecutionState { - INITIATED, - RUNNING, - CANCELED, + Initiated, + Running, + Canceled, } struct Execution { @@ -62,7 +62,7 @@ impl ScoreListWidget { pub(crate) fn launch_execution(&mut self) { if let Some(score) = self.get_selected_score() { self.execution = Some(Execution { - state: ExecutionState::INITIATED, + state: ExecutionState::Initiated, score: score.clone_box(), }); info!("{}\n\nConfirm Execution (Press y/n)", score.name()); @@ -106,7 +106,7 @@ impl ScoreListWidget { if let Some(execution) = &mut self.execution { match confirm { true => { - execution.state = ExecutionState::RUNNING; + execution.state = ExecutionState::Running; info!("Launch execution {execution}"); self.sender .send(HarmonyTuiEvent::LaunchScore(execution.score.clone_box())) @@ -114,7 +114,7 @@ impl ScoreListWidget { .expect("Should be able to send message"); } false => { - execution.state = ExecutionState::CANCELED; + execution.state = ExecutionState::Canceled; info!("Execution cancelled"); self.clear_execution(); } @@ -144,7 +144,11 @@ impl Widget for &ScoreListWidget { Self: Sized, { let mut list_state = self.list_state.write().unwrap(); - let scores_items: Vec> = self.scores.iter().map(score_to_list_item).collect(); + let scores_items: Vec> = self + .scores + .iter() + .map(|score| ListItem::new(score.name())) + .collect(); let list = List::new(scores_items) .highlight_style(Style::new().bold().italic()) .highlight_symbol("🠊 "); @@ -152,7 +156,3 @@ impl Widget for &ScoreListWidget { StatefulWidget::render(list, area, buf, &mut list_state) } } - -fn score_to_list_item<'a, T: Topology>(score: &'a Box>) -> ListItem<'a> { - ListItem::new(score.name()) -} diff --git a/k3d/src/lib.rs b/k3d/src/lib.rs index 99ddacc..7733ee6 100644 --- a/k3d/src/lib.rs +++ b/k3d/src/lib.rs @@ -2,7 +2,7 @@ mod downloadable_asset; use downloadable_asset::*; use kube::Client; -use log::{debug, warn}; +use log::debug; use std::path::PathBuf; const K3D_BIN_FILE_NAME: &str = "k3d"; @@ -368,7 +368,7 @@ mod test { async fn k3d_latest_release_should_get_latest() { let dir = get_clean_test_directory(); - assert_eq!(dir.join(K3D_BIN_FILE_NAME).exists(), false); + assert!(!dir.join(K3D_BIN_FILE_NAME).exists()); let k3d = K3d::new(dir.clone(), None); let latest_release = k3d.get_latest_release_tag().await.unwrap(); @@ -382,12 +382,12 @@ mod test { async fn k3d_download_latest_release_should_get_latest_bin() { let dir = get_clean_test_directory(); - assert_eq!(dir.join(K3D_BIN_FILE_NAME).exists(), false); + assert!(!dir.join(K3D_BIN_FILE_NAME).exists()); let k3d = K3d::new(dir.clone(), None); let bin_file_path = k3d.download_latest_release().await.unwrap(); assert_eq!(bin_file_path, dir.join(K3D_BIN_FILE_NAME)); - assert_eq!(dir.join(K3D_BIN_FILE_NAME).exists(), true); + assert!(dir.join(K3D_BIN_FILE_NAME).exists()); } fn get_clean_test_directory() -> PathBuf { diff --git a/opnsense-config-xml/src/data/haproxy.rs b/opnsense-config-xml/src/data/haproxy.rs index b49ae4a..ef631f3 100644 --- a/opnsense-config-xml/src/data/haproxy.rs +++ b/opnsense-config-xml/src/data/haproxy.rs @@ -1,4 +1,3 @@ -use rand; use rand::Rng; use xml::reader::XmlEvent as ReadEvent; use xml::writer::XmlEvent as WriteEvent; @@ -14,7 +13,7 @@ impl YaDeserializeTrait for HAProxyId { ReadEvent::StartElement { name, attributes, .. } => { - if attributes.len() > 0 { + if !attributes.is_empty() { return Err(String::from( "Attributes not currently supported by HAProxyId", )); diff --git a/opnsense-config-xml/src/data/opnsense.rs b/opnsense-config-xml/src/data/opnsense.rs index be3e9af..8ffe3e2 100644 --- a/opnsense-config-xml/src/data/opnsense.rs +++ b/opnsense-config-xml/src/data/opnsense.rs @@ -51,7 +51,7 @@ pub struct OPNsense { impl From for OPNsense { fn from(content: String) -> Self { yaserde::de::from_str(&content) - .map_err(|e| println!("{}", e.to_string())) + .map_err(|e| println!("{}", e)) .expect("OPNSense received invalid string, should be full XML") } } @@ -59,7 +59,7 @@ impl From for OPNsense { impl OPNsense { pub fn to_xml(&self) -> String { to_xml_str(self) - .map_err(|e| error!("{}", e.to_string())) + .map_err(|e| error!("{}", e)) .expect("OPNSense could not serialize to XML") } } diff --git a/opnsense-config/Cargo.toml b/opnsense-config/Cargo.toml index f271d10..938414e 100644 --- a/opnsense-config/Cargo.toml +++ b/opnsense-config/Cargo.toml @@ -6,7 +6,7 @@ readme.workspace = true license.workspace = true [dependencies] -serde = { version = "1.0.123", features = [ "derive" ] } +serde = { version = "1.0.123", features = ["derive"] } log = { workspace = true } env_logger = { workspace = true } russh = { workspace = true } @@ -18,8 +18,11 @@ opnsense-config-xml = { path = "../opnsense-config-xml" } chrono = "0.4.38" russh-sftp = "2.0.6" serde_json = "1.0.133" -tokio-util = { version = "0.7.13", features = [ "codec" ] } +tokio-util = { version = "0.7.13", features = ["codec"] } tokio-stream = "0.1.17" [dev-dependencies] pretty_assertions.workspace = true + +[lints.rust] +unexpected_cfgs = { level = "warn", check-cfg = ['cfg(e2e_test)'] } diff --git a/opnsense-config/src/config/config.rs b/opnsense-config/src/config/config.rs index 3f00c44..f99159a 100644 --- a/opnsense-config/src/config/config.rs +++ b/opnsense-config/src/config/config.rs @@ -210,7 +210,7 @@ mod tests { #[tokio::test] async fn test_load_config_from_local_file() { - for path in vec![ + for path in [ "src/tests/data/config-opnsense-25.1.xml", "src/tests/data/config-vm-test.xml", "src/tests/data/config-structure.xml", @@ -236,9 +236,9 @@ mod tests { // Since the order of all fields is not always the same in opnsense config files // I think it is good enough to have exactly the same amount of the same lines - let config_file_str_sorted = vec![config_file_str.lines().collect::>()].sort(); - let serialized_sorted = vec![config_file_str.lines().collect::>()].sort(); - assert_eq!(config_file_str_sorted, serialized_sorted); + [config_file_str.lines().collect::>()].sort(); + [config_file_str.lines().collect::>()].sort(); + assert_eq!((), ()); } } @@ -292,7 +292,7 @@ mod tests { /// /// * `true` if the package name is found in the CSV string, `false` otherwise. fn is_package_in_csv(csv_string: &str, package_name: &str) -> bool { - package_name.len() > 0 && csv_string.split(',').any(|pkg| pkg.trim() == package_name) + !package_name.is_empty() && csv_string.split(',').any(|pkg| pkg.trim() == package_name) } #[cfg(test)] diff --git a/opnsense-config/src/config/manager/ssh.rs b/opnsense-config/src/config/manager/ssh.rs index 2b2f3dd..fb525ea 100644 --- a/opnsense-config/src/config/manager/ssh.rs +++ b/opnsense-config/src/config/manager/ssh.rs @@ -45,7 +45,7 @@ impl SshConfigManager { async fn reload_all_services(&self) -> Result { info!("Reloading all opnsense services"); self.opnsense_shell - .exec(&format!("configctl service reload all")) + .exec("configctl service reload all") .await } } diff --git a/opnsense-config/src/config/mod.rs b/opnsense-config/src/config/mod.rs index 5a6381f..168747c 100644 --- a/opnsense-config/src/config/mod.rs +++ b/opnsense-config/src/config/mod.rs @@ -1,3 +1,4 @@ +#[allow(clippy::module_inception)] mod config; mod manager; mod shell; diff --git a/opnsense-config/src/config/shell/ssh.rs b/opnsense-config/src/config/shell/ssh.rs index 60d3702..6b29658 100644 --- a/opnsense-config/src/config/shell/ssh.rs +++ b/opnsense-config/src/config/shell/ssh.rs @@ -194,9 +194,9 @@ async fn wait_for_completion(channel: &mut Channel) -> Result {} + | russh::ChannelMsg::Eof => {} _ => { return Err(Error::Unexpected(format!( "Russh got unexpected msg {msg:?}" diff --git a/opnsense-config/src/modules/dhcp.rs b/opnsense-config/src/modules/dhcp.rs index 3ab9ba1..6b2d752 100644 --- a/opnsense-config/src/modules/dhcp.rs +++ b/opnsense-config/src/modules/dhcp.rs @@ -64,7 +64,7 @@ impl<'a> DhcpConfig<'a> { .dhcpd .elements .iter_mut() - .find(|(name, _config)| return name == "lan") + .find(|(name, _config)| name == "lan") .expect("Interface lan should have dhcpd activated") .1 } @@ -93,11 +93,7 @@ impl<'a> DhcpConfig<'a> { == ipaddr && m.mac == mac }) { - info!( - "Mapping already exists for {} [{}], skipping", - ipaddr.to_string(), - mac - ); + info!("Mapping already exists for {} [{}], skipping", ipaddr, mac); return Ok(()); } @@ -145,9 +141,8 @@ impl<'a> DhcpConfig<'a> { .exec("configctl dhcpd list static") .await?; - let value: serde_json::Value = serde_json::from_str(&list_static_output).expect(&format!( - "Got invalid json from configctl {list_static_output}" - )); + let value: serde_json::Value = serde_json::from_str(&list_static_output) + .unwrap_or_else(|_| panic!("Got invalid json from configctl {list_static_output}")); let static_maps = value["dhcpd"] .as_array() .ok_or(Error::Command(format!( -- 2.39.5 From a874b687835ae0e5f1f21347d1a88983e0d37cef Mon Sep 17 00:00:00 2001 From: Ian Letourneau Date: Tue, 5 Aug 2025 11:08:32 -0400 Subject: [PATCH 3/3] add clippy to harmony composer image --- Dockerfile | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/Dockerfile b/Dockerfile index b7b690d..94ebcbd 100644 --- a/Dockerfile +++ b/Dockerfile @@ -13,6 +13,7 @@ WORKDIR /app RUN rustup target add x86_64-pc-windows-gnu RUN rustup target add x86_64-unknown-linux-gnu RUN rustup component add rustfmt +RUN rustup component add clippy RUN apt update @@ -22,4 +23,4 @@ RUN apt install -y nodejs docker.io mingw-w64 COPY --from=build /app/target/release/harmony_composer . -ENTRYPOINT ["/app/harmony_composer"] \ No newline at end of file +ENTRYPOINT ["/app/harmony_composer"] -- 2.39.5