use clap::{Parser, Subcommand};
use localtunnel_client::{open_tunnel, broadcast};
use localtunnel_server::start;
use tokio::signal;
use anyhow::Result;
mod config;
#[derive(Parser)]
#[clap(author, version, about)]
#[clap(propagate_version = true)]
struct Cli {
#[clap(subcommand)]
command: Command,
}
#[derive(Subcommand)]
enum Command {
Client {
#[clap(long)]
host: String,
#[clap(long)]
subdomain: String,
#[clap(long, default_value = "localhost")]
local_host: String,
#[clap(short, long)]
port: u16,
#[clap(long, default_value = "10")]
max_conn: u8,
#[clap(long)]
credential: Option<String>,
},
Server {
#[clap(long)]
domain: String,
#[clap(short, long, default_value = "3000")]
port: u16,
#[clap(long)]
secure: bool,
#[clap(long, default_value = "10")]
max_sockets: u8,
#[clap(long, default_value = "3001")]
proxy_port: u16,
#[clap(long)]
require_auth: bool,
},
}
#[tokio::main]
async fn main() -> Result<()> {
config::setup();
log::info!("Run localtunnel CLI!");
let command = Cli::parse().command;
match command {
Command::Client {
host,
subdomain,
local_host,
port,
max_conn,
credential,
} => {
let (notify_shutdown, _) = broadcast::channel(1);
let result = open_tunnel(
Some(&host),
Some(&subdomain),
Some(&local_host),
port,
notify_shutdown.clone(),
max_conn,
credential
)
.await?;
log::info!("Tunnel url: {:?}", result);
signal::ctrl_c().await?;
log::info!("Quit");
}
Command::Server {
domain,
port,
secure,
max_sockets,
proxy_port,
require_auth,
} => {
start(domain, port, secure, max_sockets, proxy_port, require_auth).await?;
}
}
Ok(())
}