use malwaredb_server::State;
use std::process::ExitCode;
use anyhow::ensure;
use chrono::{Local, NaiveDate, NaiveDateTime, NaiveTime};
use clap::{Parser, ValueHint};
#[derive(Clone, Debug, Parser, PartialEq)]
pub struct AddGroup {
#[arg(short, long)]
pub gid: u32,
#[arg(short, long)]
pub sid: u32,
}
impl AddGroup {
pub async fn execute(&self, state: State) -> anyhow::Result<ExitCode> {
let groups = state.db_type.list_groups().await?;
ensure!(
groups.iter().any(|g| g.id == self.gid),
"Group ID {} is not valid.",
self.gid
);
let sources = state.db_type.list_sources().await?;
ensure!(
sources.iter().any(|s| s.id == self.sid),
"Source ID {} is not valid.",
self.sid
);
state
.db_type
.add_group_to_source(self.gid, self.sid)
.await?;
Ok(ExitCode::SUCCESS)
}
}
#[derive(Clone, Debug, Parser, PartialEq)]
pub struct Create {
#[arg(long)]
pub name: String,
#[arg(long)]
pub description: Option<String>,
#[arg(long, value_hint = ValueHint::Url)]
pub url: Option<String>,
#[arg(long)]
pub date: NaiveDate,
#[arg(long)]
pub releasable: bool,
#[arg(long)]
pub malicious: Option<bool>,
}
impl Create {
pub async fn execute(&self, state: State) -> anyhow::Result<ExitCode> {
let time = NaiveTime::default();
let datetime = NaiveDateTime::new(self.date, time);
let sid = state
.db_type
.create_source(
&self.name,
self.description.as_deref(),
self.url.as_deref(),
datetime.and_local_timezone(Local).unwrap(),
self.releasable,
self.malicious,
)
.await?;
println!("Source {} created with ID {sid}", self.name);
Ok(ExitCode::SUCCESS)
}
}
#[derive(Clone, Debug, Parser, PartialEq)]
pub struct List {}
impl List {
pub async fn execute(&self, state: State) -> anyhow::Result<ExitCode> {
for source in state.db_type.list_sources().await? {
println!("{source}");
}
Ok(ExitCode::SUCCESS)
}
}