feat(opnsense-config): dnsmasq dhcp static mappings (#130)
All checks were successful
Run Check Script / check (pull_request) Successful in 59s
All checks were successful
Run Check Script / check (pull_request) Successful in 59s
Co-authored-by: Jean-Gabriel Gill-Couture <jeangabriel.gc@gmail.com> Co-authored-by: Ian Letourneau <ian@noma.to> Reviewed-on: #130 Reviewed-by: Ian Letourneau <ian@noma.to> Co-authored-by: Jean-Gabriel Gill-Couture <jg@nationtech.io> Co-committed-by: Jean-Gabriel Gill-Couture <jg@nationtech.io>
This commit is contained in:
@@ -1,8 +1,9 @@
|
||||
use crate::config::{manager::ConfigManager, OPNsenseShell};
|
||||
use crate::error::Error;
|
||||
use async_trait::async_trait;
|
||||
use log::info;
|
||||
use log::{info, warn};
|
||||
use russh_keys::key::KeyPair;
|
||||
use sha2::Digest;
|
||||
use std::sync::Arc;
|
||||
|
||||
#[derive(Debug)]
|
||||
@@ -35,10 +36,10 @@ impl SshConfigManager {
|
||||
.await
|
||||
}
|
||||
|
||||
async fn move_to_live_config(&self, new_config_path: &str) -> Result<String, Error> {
|
||||
async fn copy_to_live_config(&self, new_config_path: &str) -> Result<String, Error> {
|
||||
info!("Overwriting OPNSense /conf/config.xml with {new_config_path}");
|
||||
self.opnsense_shell
|
||||
.exec(&format!("mv {new_config_path} /conf/config.xml"))
|
||||
.exec(&format!("cp {new_config_path} /conf/config.xml"))
|
||||
.await
|
||||
}
|
||||
|
||||
@@ -56,19 +57,41 @@ impl ConfigManager for SshConfigManager {
|
||||
self.opnsense_shell.exec("cat /conf/config.xml").await
|
||||
}
|
||||
|
||||
async fn save_config(&self, content: &str) -> Result<(), Error> {
|
||||
async fn save_config(&self, content: &str, hash: &str) -> Result<(), Error> {
|
||||
let current_content = self.load_as_str().await?;
|
||||
|
||||
if !check_hash(¤t_content, hash) {
|
||||
warn!("OPNSense config file changed since loading it! Hash when loading : {hash}");
|
||||
// return Err(Error::Config(format!(
|
||||
// "OPNSense config file changed since loading it! Hash when loading : {hash}"
|
||||
// )));
|
||||
}
|
||||
|
||||
let temp_filename = self
|
||||
.opnsense_shell
|
||||
.write_content_to_temp_file(content)
|
||||
.await?;
|
||||
self.backup_config_remote().await?;
|
||||
self.move_to_live_config(&temp_filename).await?;
|
||||
self.copy_to_live_config(&temp_filename).await?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
async fn apply_new_config(&self, content: &str) -> Result<(), Error> {
|
||||
self.save_config(content).await?;
|
||||
async fn apply_new_config(&self, content: &str, hash: &str) -> Result<(), Error> {
|
||||
self.save_config(content, &hash).await?;
|
||||
self.reload_all_services().await?;
|
||||
Ok(())
|
||||
}
|
||||
}
|
||||
|
||||
pub fn get_hash(content: &str) -> String {
|
||||
let mut hasher = sha2::Sha256::new();
|
||||
hasher.update(content.as_bytes());
|
||||
let hash_bytes = hasher.finalize();
|
||||
let hash_string = format!("{:x}", hash_bytes);
|
||||
info!("Loaded OPNSense config.xml with hash {hash_string:?}");
|
||||
hash_string
|
||||
}
|
||||
|
||||
pub fn check_hash(content: &str, source_hash: &str) -> bool {
|
||||
get_hash(content) == source_hash
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user