client: don't leave interface behind on failed install
parent
dcf553c8fd
commit
c15db6f833
|
@ -183,7 +183,7 @@ fn update_hosts_file(
|
||||||
|
|
||||||
fn install(invite: &Path, hosts_file: Option<PathBuf>) -> Result<(), Error> {
|
fn install(invite: &Path, hosts_file: Option<PathBuf>) -> Result<(), Error> {
|
||||||
shared::ensure_dirs_exist(&[*CLIENT_CONFIG_PATH])?;
|
shared::ensure_dirs_exist(&[*CLIENT_CONFIG_PATH])?;
|
||||||
let mut config = InterfaceConfig::from_file(invite)?;
|
let config = InterfaceConfig::from_file(invite)?;
|
||||||
|
|
||||||
let iface = Input::with_theme(&*prompts::THEME)
|
let iface = Input::with_theme(&*prompts::THEME)
|
||||||
.with_prompt("Interface name")
|
.with_prompt("Interface name")
|
||||||
|
@ -196,7 +196,59 @@ fn install(invite: &Path, hosts_file: Option<PathBuf>) -> Result<(), Error> {
|
||||||
}
|
}
|
||||||
|
|
||||||
let iface = iface.parse()?;
|
let iface = iface.parse()?;
|
||||||
|
redeem_invite(&iface, config, target_conf).map_err(|e| {
|
||||||
|
println!("{} bringing down the interface.", "[*]".dimmed());
|
||||||
|
if let Err(e) = wg::down(&iface) {
|
||||||
|
println!("{} failed to bring down interface: {}.", "[*]".yellow(), e.to_string());
|
||||||
|
};
|
||||||
|
println!("{} Failed to redeem invite. Now's a good time to make sure the server is started and accessible!", "[!]".red());
|
||||||
|
e
|
||||||
|
})?;
|
||||||
|
|
||||||
|
fetch(&iface, false, hosts_file)?;
|
||||||
|
|
||||||
|
if Confirm::with_theme(&*prompts::THEME)
|
||||||
|
.with_prompt(&format!(
|
||||||
|
"Delete invitation file \"{}\" now? (It's no longer needed)",
|
||||||
|
invite.to_string_lossy().yellow()
|
||||||
|
))
|
||||||
|
.default(true)
|
||||||
|
.interact()?
|
||||||
|
{
|
||||||
|
std::fs::remove_file(invite).with_path(invite)?;
|
||||||
|
}
|
||||||
|
|
||||||
|
printdoc!(
|
||||||
|
"
|
||||||
|
{star} Done!
|
||||||
|
|
||||||
|
{interface} has been {installed}.
|
||||||
|
|
||||||
|
It's recommended to now keep the interface automatically refreshing via systemd:
|
||||||
|
|
||||||
|
{systemctl_enable}{interface}
|
||||||
|
|
||||||
|
By default, innernet will write to your /etc/hosts file for peer name
|
||||||
|
resolution. To disable this behavior, use the --no-write-hosts or --write-hosts [PATH]
|
||||||
|
options.
|
||||||
|
|
||||||
|
See the manpage or innernet GitHub repo for more detailed instruction on managing your
|
||||||
|
interface and network. Have fun!
|
||||||
|
|
||||||
|
",
|
||||||
|
star = "[*]".dimmed(),
|
||||||
|
interface = iface.to_string().yellow(),
|
||||||
|
installed = "installed".green(),
|
||||||
|
systemctl_enable = "systemctl enable --now innernet@".yellow(),
|
||||||
|
);
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
|
||||||
|
fn redeem_invite(
|
||||||
|
iface: &InterfaceName,
|
||||||
|
mut config: InterfaceConfig,
|
||||||
|
target_conf: PathBuf,
|
||||||
|
) -> Result<(), Error> {
|
||||||
println!("{} bringing up the interface.", "[*]".dimmed());
|
println!("{} bringing up the interface.", "[*]".dimmed());
|
||||||
wg::up(
|
wg::up(
|
||||||
&iface,
|
&iface,
|
||||||
|
@ -243,43 +295,6 @@ fn install(invite: &Path, hosts_file: Option<PathBuf>) -> Result<(), Error> {
|
||||||
.set_private_key(keypair.private)
|
.set_private_key(keypair.private)
|
||||||
.apply(&iface)?;
|
.apply(&iface)?;
|
||||||
|
|
||||||
fetch(&iface, false, hosts_file)?;
|
|
||||||
|
|
||||||
if Confirm::with_theme(&*prompts::THEME)
|
|
||||||
.with_prompt(&format!(
|
|
||||||
"Delete invitation file \"{}\" now? (It's no longer needed)",
|
|
||||||
invite.to_string_lossy().yellow()
|
|
||||||
))
|
|
||||||
.default(true)
|
|
||||||
.interact()?
|
|
||||||
{
|
|
||||||
std::fs::remove_file(invite).with_path(invite)?;
|
|
||||||
}
|
|
||||||
|
|
||||||
printdoc!(
|
|
||||||
"
|
|
||||||
{star} Done!
|
|
||||||
|
|
||||||
{interface} has been {installed}.
|
|
||||||
|
|
||||||
It's recommended to now keep the interface automatically refreshing via systemd:
|
|
||||||
|
|
||||||
{systemctl_enable}{interface}
|
|
||||||
|
|
||||||
By default, innernet will write to your /etc/hosts file for peer name
|
|
||||||
resolution. To disable this behavior, use the --no-write-hosts or --write-hosts [PATH]
|
|
||||||
options.
|
|
||||||
|
|
||||||
See the manpage or innernet GitHub repo for more detailed instruction on managing your
|
|
||||||
interface and network. Have fun!
|
|
||||||
|
|
||||||
",
|
|
||||||
star = "[*]".dimmed(),
|
|
||||||
interface = iface.to_string().yellow(),
|
|
||||||
installed = "installed".green(),
|
|
||||||
systemctl_enable = "systemctl enable --now innernet@".yellow(),
|
|
||||||
);
|
|
||||||
|
|
||||||
Ok(())
|
Ok(())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@ use crate::{ClientError, Error};
|
||||||
use colored::*;
|
use colored::*;
|
||||||
use serde::{de::DeserializeOwned, Serialize};
|
use serde::{de::DeserializeOwned, Serialize};
|
||||||
use shared::{interface_config::ServerInfo, INNERNET_PUBKEY_HEADER};
|
use shared::{interface_config::ServerInfo, INNERNET_PUBKEY_HEADER};
|
||||||
|
use ureq::{Agent, AgentBuilder};
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
pub fn human_duration(duration: Duration) -> String {
|
pub fn human_duration(duration: Duration) -> String {
|
||||||
|
@ -48,12 +49,17 @@ pub fn human_size(bytes: u64) -> String {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct Api<'a> {
|
pub struct Api<'a> {
|
||||||
|
agent: Agent,
|
||||||
server: &'a ServerInfo,
|
server: &'a ServerInfo,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a> Api<'a> {
|
impl<'a> Api<'a> {
|
||||||
pub fn new(server: &'a ServerInfo) -> Self {
|
pub fn new(server: &'a ServerInfo) -> Self {
|
||||||
Self { server }
|
let agent = AgentBuilder::new()
|
||||||
|
.timeout(Duration::from_secs(5))
|
||||||
|
.redirects(0)
|
||||||
|
.build();
|
||||||
|
Self { agent, server }
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn http<T: DeserializeOwned>(&self, verb: &str, endpoint: &str) -> Result<T, Error> {
|
pub fn http<T: DeserializeOwned>(&self, verb: &str, endpoint: &str) -> Result<T, Error> {
|
||||||
|
@ -75,7 +81,7 @@ impl<'a> Api<'a> {
|
||||||
endpoint: &str,
|
endpoint: &str,
|
||||||
form: Option<S>,
|
form: Option<S>,
|
||||||
) -> Result<T, Error> {
|
) -> Result<T, Error> {
|
||||||
let request = ureq::request(
|
let request = self.agent.request(
|
||||||
verb,
|
verb,
|
||||||
&format!("http://{}/v1{}", self.server.internal_endpoint, endpoint),
|
&format!("http://{}/v1{}", self.server.internal_endpoint, endpoint),
|
||||||
)
|
)
|
||||||
|
|
Loading…
Reference in New Issue