pub(crate) mod children;
pub(crate) mod comment;
pub(crate) mod create;
pub(crate) mod delete;
pub(crate) mod download;
pub(crate) mod edit;
pub(crate) mod label;
pub(crate) mod read;
pub(crate) mod search;
pub(crate) mod user;
pub(crate) mod write;
use anyhow::Result;
use clap::{Parser, Subcommand};
#[derive(Parser)]
pub struct ConfluenceCommand {
#[command(subcommand)]
pub command: ConfluenceSubcommands,
}
#[derive(Subcommand)]
pub enum ConfluenceSubcommands {
Comment(comment::CommentCommand),
Read(read::ReadCommand),
Write(write::WriteCommand),
Edit(edit::EditCommand),
Search(search::SearchCommand),
Create(create::CreateCommand),
Delete(delete::DeleteCommand),
Label(label::LabelCommand),
Download(download::DownloadCommand),
Children(children::ChildrenCommand),
User(user::UserCommand),
}
impl ConfluenceCommand {
pub async fn execute(self) -> Result<()> {
match self.command {
ConfluenceSubcommands::Comment(cmd) => cmd.execute().await,
ConfluenceSubcommands::Read(cmd) => cmd.execute().await,
ConfluenceSubcommands::Write(cmd) => cmd.execute().await,
ConfluenceSubcommands::Edit(cmd) => cmd.execute().await,
ConfluenceSubcommands::Search(cmd) => cmd.execute().await,
ConfluenceSubcommands::Create(cmd) => cmd.execute().await,
ConfluenceSubcommands::Label(cmd) => cmd.execute().await,
ConfluenceSubcommands::Delete(cmd) => cmd.execute().await,
ConfluenceSubcommands::Download(cmd) => cmd.execute().await,
ConfluenceSubcommands::Children(cmd) => cmd.execute().await,
ConfluenceSubcommands::User(cmd) => cmd.execute().await,
}
}
}
#[cfg(test)]
mod tests {
use super::*;
use crate::cli::atlassian::format::{ContentFormat, OutputFormat};
#[test]
fn confluence_subcommands_comment_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Comment(comment::CommentCommand {
command: comment::CommentSubcommands::List(comment::ListCommand {
id: "12345".to_string(),
limit: 25,
output: OutputFormat::Table,
}),
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Comment(_)));
}
#[test]
fn confluence_subcommands_read_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Read(read::ReadCommand {
id: "12345".to_string(),
output: None,
format: ContentFormat::Jfm,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Read(_)));
}
#[test]
fn confluence_subcommands_write_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Write(write::WriteCommand {
id: "12345".to_string(),
file: None,
format: ContentFormat::Adf,
force: false,
dry_run: false,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Write(_)));
}
#[test]
fn confluence_subcommands_edit_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Edit(edit::EditCommand {
id: "12345".to_string(),
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Edit(_)));
}
#[test]
fn confluence_subcommands_search_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Search(search::SearchCommand {
cql: Some("space = ENG".to_string()),
space: None,
title: None,
limit: 25,
output: OutputFormat::Table,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Search(_)));
}
#[test]
fn confluence_subcommands_create_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Create(create::CreateCommand {
file: None,
format: ContentFormat::Jfm,
space: Some("ENG".to_string()),
title: Some("Test".to_string()),
parent: None,
dry_run: false,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Create(_)));
}
#[test]
fn confluence_subcommands_label_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Label(label::LabelCommand {
command: label::LabelSubcommands::List(label::ListCommand {
id: "12345".to_string(),
output: OutputFormat::Table,
}),
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Label(_)));
}
#[test]
fn confluence_subcommands_delete_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Delete(delete::DeleteCommand {
id: "12345".to_string(),
force: true,
purge: false,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Delete(_)));
}
#[test]
fn confluence_subcommands_user_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::User(user::UserCommand {
command: user::UserSubcommands::Search(user::UserSearchCommand {
query: "alice".to_string(),
limit: 25,
output: OutputFormat::Table,
}),
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::User(_)));
}
#[test]
fn confluence_subcommands_children_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Children(children::ChildrenCommand {
id: Some("12345".to_string()),
space: None,
recursive: false,
max_depth: 0,
output: OutputFormat::Table,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Children(_)));
}
#[tokio::test]
async fn confluence_command_execute_children_dispatch() {
std::env::set_var("ATLASSIAN_INSTANCE_URL", "http://127.0.0.1:1");
std::env::set_var("ATLASSIAN_EMAIL", "test@example.com");
std::env::set_var("ATLASSIAN_API_TOKEN", "fake-token");
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Children(children::ChildrenCommand {
id: Some("12345".to_string()),
space: None,
recursive: false,
max_depth: 0,
output: OutputFormat::Table,
}),
};
let _ = cmd.execute().await;
std::env::remove_var("ATLASSIAN_INSTANCE_URL");
std::env::remove_var("ATLASSIAN_EMAIL");
std::env::remove_var("ATLASSIAN_API_TOKEN");
}
#[test]
fn confluence_subcommands_download_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Download(download::DownloadCommand {
id: Some("12345".to_string()),
space: None,
output_dir: std::path::PathBuf::from("."),
format: ContentFormat::Jfm,
concurrency: 8,
max_depth: 0,
title_filter: None,
resume: false,
on_conflict: download::OnConflict::Backup,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Download(_)));
}
#[test]
fn confluence_subcommands_download_space_variant() {
let cmd = ConfluenceCommand {
command: ConfluenceSubcommands::Download(download::DownloadCommand {
id: None,
space: Some("AD".to_string()),
output_dir: std::path::PathBuf::from("./AD"),
format: ContentFormat::Jfm,
concurrency: 8,
max_depth: 0,
title_filter: Some("architecture".to_string()),
resume: false,
on_conflict: download::OnConflict::Backup,
}),
};
assert!(matches!(cmd.command, ConfluenceSubcommands::Download(_)));
}
}