blob: fb77530907543caf8ab4019cace2ed4774ea56e3 [file] [log] [blame]
mod config;
use clap::Parser;
use env_logger::Env;
use log::error;
use rtnetlink::Handle;
use std::{path::PathBuf, process};
#[derive(Parser, Debug)]
#[command(version, about, long_about = None)]
struct Cli {
#[arg(default_value = "/tmp/auto_bridge_add", help = "Path to the JSON file")]
config: PathBuf,
}
#[tokio::main]
async fn main() {
let cli = Cli::parse();
let env = Env::default()
.filter_or("MY_LOG_LEVEL", "info")
.write_style_or("MY_LOG_STYLE", "always");
env_logger::init_from_env(env);
let network_config = match config::NetworkConfig::from_path(&cli.config) {
Ok(network_config) => network_config,
Err(e) => {
error!("Failed to load network config: {}", e);
process::exit(1);
}
};
let (connection, handle, _) = rtnetlink::new_connection().expect("Failed to create connection");
tokio::spawn(connection);
for (bridge_name, interface_name) in network_config.bridges_with_interfaces_iter() {
let interface = get_interface(&handle, interface_name).await;
let bridge = get_interface(&handle, bridge_name).await;
if let Err(e) = bridge.migrate_from_interface(&handle, &interface).await {
error!(
"Failed to migrate from {} to {}: {}",
interface_name, bridge_name, e
);
process::exit(1);
}
}
}
async fn get_interface(handle: &Handle, name: &str) -> ovsinit::Interface {
match ovsinit::Interface::new(handle, name.to_string()).await {
Ok(interface) => interface,
Err(ovsinit::InterfaceError::NotFound(name)) => {
error!(interface = name.as_str(); "Interface not found.");
process::exit(1);
}
Err(e) => {
error!(error = e.to_string().as_str(); "Failed to lookup interface.");
process::exit(1);
}
}
}