use crate::esteria::{Encoding, SmsClient, SmsFlags, SmsRequest};
use chrono::{DateTime, Utc};
use clap::Parser;
#[derive(Parser, Debug)]
#[command(name = "esteria-api-client")]
#[command(author, version, about = "Send SMS via Esteria API", long_about = None)]
#[allow(clippy::struct_excessive_bools)]
struct Cli {
#[arg(short = 'u', long, env = "ESTERIA_API_BASE_URL")]
api_url: String,
#[arg(short = 'k', long, env = "ESTERIA_API_KEY")]
api_key: String,
#[arg(short = 's', long)]
sender: String,
#[arg(short = 'n', long)]
number: String,
#[arg(short = 't', long)]
text: String,
#[arg(long)]
time: Option<String>,
#[arg(long)]
dlr_url: Option<String>,
#[arg(long)]
expired: Option<i32>,
#[arg(long)]
user_key: Option<String>,
#[arg(long)]
debug: bool,
#[arg(long)]
nolog: bool,
#[arg(long)]
flash: bool,
#[arg(long)]
test: bool,
#[arg(long)]
nobl: bool,
#[arg(long)]
convert: bool,
#[arg(long, default_value = "default")]
encoding: String,
}
pub async fn run() -> Result<(), Box<dyn std::error::Error>> {
env_logger::init();
let cli = Cli::parse();
let client = SmsClient::with_api_base_url(cli.api_url);
let mut flags = SmsFlags::empty();
if cli.debug {
flags |= SmsFlags::DEBUG;
}
if cli.nolog {
flags |= SmsFlags::NOLOG;
}
if cli.flash {
flags |= SmsFlags::FLASH;
}
if cli.test {
flags |= SmsFlags::TEST;
}
if cli.nobl {
flags |= SmsFlags::NOBL;
}
if cli.convert {
flags |= SmsFlags::CONVERT;
}
let encoding = match cli.encoding.to_lowercase().as_str() {
"default" => Encoding::Default,
"8bit" => Encoding::EightBit,
"udh" => Encoding::Udh,
_ => {
eprintln!("Invalid encoding '{}'. Using 8bit.", cli.encoding);
Encoding::EightBit
}
};
let time = if let Some(time_str) = cli.time {
Some(DateTime::parse_from_rfc3339(&time_str)?.with_timezone(&Utc))
} else {
None
};
let mut request = SmsRequest::new(&cli.api_key, &cli.sender, &cli.number, &cli.text)
.with_flags(flags)
.with_encoding(encoding);
if let Some(t) = time {
request = request.with_time(t);
}
if let Some(url) = cli.dlr_url.as_deref() {
request = request.with_dlr_url(url);
}
if let Some(exp) = cli.expired {
request = request.with_expired(exp);
}
if let Some(key) = cli.user_key.as_deref() {
request = request.with_user_key(key);
}
println!("Sending SMS to {}...", cli.number);
match client.send_sms(request).await {
Ok(code) => {
println!("✓ SMS sent successfully!");
println!("Message ID: {code}");
Ok(())
}
Err(e) => {
eprintln!("✗ Failed to send SMS: {e}");
Err(Box::new(e))
}
}
}