From 280d07974831ae52d3810d42c23771adf5a1e7d0 Mon Sep 17 00:00:00 2001 From: Lars Wirzenius Date: Wed, 21 Apr 2021 07:35:59 +0300 Subject: refactor: move subcommand implementations into src/cmd.rs The command line interface definition (for structopt) and implementation are now both in src/cmd.rs. This seems tidier than having them split between src/opt.rs and src/bin/jt2.rs. --- src/bin/jt2.rs | 63 ++++----------------------------- src/cmd.rs | 110 +++++++++++++++++++++++++++++++++++++++++++++++++++++++++ src/lib.rs | 1 + src/opt.rs | 42 +++++----------------- 4 files changed, 126 insertions(+), 90 deletions(-) create mode 100644 src/cmd.rs diff --git a/src/bin/jt2.rs b/src/bin/jt2.rs index 677bb35..8ef0728 100644 --- a/src/bin/jt2.rs +++ b/src/bin/jt2.rs @@ -1,9 +1,6 @@ use jt2::config::Configuration; -use jt2::error::JournalError; -use jt2::journal::Journal; use jt2::opt::{Opt, SubCommand}; -use std::path::{Path, PathBuf}; use structopt::StructOpt; fn main() -> anyhow::Result<()> { @@ -11,59 +8,13 @@ fn main() -> anyhow::Result<()> { let opt = Opt::from_args(); let config = Configuration::read(&opt)?; match opt.cmd { - SubCommand::Config => config.dump(), - SubCommand::Init { - journalname, - description, - } => init(&config.dirname, &journalname, &description, &config)?, - SubCommand::IsJournal => is_journal(&config)?, - SubCommand::New { title, topic } => new_draft(&title, &topic, &config)?, - SubCommand::NewTopic { path, title } => new_topic(&path, &title, &config)?, - SubCommand::Edit { draft } => edit_draft(&draft, &config)?, - SubCommand::Finish { draft, basename } => finish_draft(&draft, &basename, &config)?, + SubCommand::Config(x) => x.run(&config)?, + SubCommand::Init(x) => x.run(&config)?, + SubCommand::IsJournal(x) => x.run(&config)?, + SubCommand::New(x) => x.run(&config)?, + SubCommand::NewTopic(x) => x.run(&config)?, + SubCommand::Edit(x) => x.run(&config)?, + SubCommand::Finish(x) => x.run(&config)?, } Ok(()) } - -fn init( - dirname: &Path, - _journalname: &str, - _description: &str, - config: &Configuration, -) -> anyhow::Result<()> { - Journal::init(dirname, &config.entries)?; - Ok(()) -} - -fn is_journal(config: &Configuration) -> anyhow::Result<()> { - if !Journal::is_journal(&config.dirname, &config.entries) { - return Err(JournalError::NotAJournal(config.dirname.display().to_string()).into()); - } - Ok(()) -} - -fn new_draft(title: &str, topic: &Option, config: &Configuration) -> anyhow::Result<()> { - let journal = Journal::new(&config.dirname, &config.entries)?; - journal.new_draft(title, topic, &config.editor)?; - Ok(()) -} - -fn new_topic(path: &Path, title: &str, config: &Configuration) -> anyhow::Result<()> { - let journal = Journal::new(&config.dirname, &config.entries)?; - journal.new_topic(path, title, &config.editor)?; - Ok(()) -} - -fn edit_draft(draft: &str, config: &Configuration) -> anyhow::Result<()> { - let journal = Journal::new(&config.dirname, &config.entries)?; - let filename = journal.pick_draft(draft)?; - journal.edit_draft(&config.editor, &filename)?; - Ok(()) -} - -fn finish_draft(draft: &str, basename: &str, config: &Configuration) -> anyhow::Result<()> { - let journal = Journal::new(&config.dirname, &config.entries)?; - let filename = journal.pick_draft(draft)?; - journal.finish_draft(&filename, basename)?; - Ok(()) -} diff --git a/src/cmd.rs b/src/cmd.rs new file mode 100644 index 0000000..c1606e0 --- /dev/null +++ b/src/cmd.rs @@ -0,0 +1,110 @@ +use crate::config::Configuration; +use crate::error::JournalError; +use crate::journal::Journal; +use std::path::PathBuf; +use structopt::StructOpt; + +#[derive(Debug, StructOpt)] +pub struct Config {} + +impl Config { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + config.dump(); + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct Init { + #[structopt(help = "Short name for journal")] + journalname: String, + + #[structopt(help = "Short description of journal, its title")] + description: String, +} + +impl Init { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + Journal::init(&config.dirname, &config.entries)?; + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct IsJournal {} + +impl IsJournal { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + if !Journal::is_journal(&config.dirname, &config.entries) { + return Err(JournalError::NotAJournal(config.dirname.display().to_string()).into()); + } + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct New { + #[structopt(help = "Title of new draft")] + title: String, + + #[structopt(long, help = "Add link to a topic page")] + topic: Option, +} + +impl New { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + let journal = Journal::new(&config.dirname, &config.entries)?; + journal.new_draft(&self.title, &self.topic, &config.editor)?; + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct NewTopic { + #[structopt(help = "Path to topic page in journal")] + path: PathBuf, + + #[structopt(help = "Title of topic page")] + title: String, +} + +impl NewTopic { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + let journal = Journal::new(&config.dirname, &config.entries)?; + journal.new_topic(&self.path, &self.title, &config.editor)?; + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct Edit { + /// Draft id. + draft: String, +} + +impl Edit { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + let journal = Journal::new(&config.dirname, &config.entries)?; + let filename = journal.pick_draft(&self.draft)?; + journal.edit_draft(&config.editor, &filename)?; + Ok(()) + } +} + +#[derive(Debug, StructOpt)] +pub struct Finish { + /// Draft id. + draft: String, + + /// Set base name of published file. + basename: String, +} + +impl Finish { + pub fn run(&self, config: &Configuration) -> Result<(), JournalError> { + let journal = Journal::new(&config.dirname, &config.entries)?; + let filename = journal.pick_draft(&self.draft)?; + journal.finish_draft(&filename, &self.basename)?; + Ok(()) + } +} diff --git a/src/lib.rs b/src/lib.rs index d9b0801..a634111 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -1,3 +1,4 @@ +pub mod cmd; pub mod config; pub mod error; pub mod journal; diff --git a/src/opt.rs b/src/opt.rs index 4e6f46d..7d3dcda 100644 --- a/src/opt.rs +++ b/src/opt.rs @@ -1,5 +1,6 @@ //! Command line options. +use crate::cmd; use std::path::PathBuf; use structopt::StructOpt; @@ -46,50 +47,23 @@ pub struct GlobalOptions { #[derive(Debug, StructOpt)] pub enum SubCommand { /// Show configuration. - Config, + Config(cmd::Config), /// Create a new journal in the chosen directory. - Init { - #[structopt(help = "Short name for journal")] - journalname: String, - - #[structopt(help = "Short description of journal, its title")] - description: String, - }, + Init(cmd::Init), /// Check if a directory is a journal. - IsJournal, + IsJournal(cmd::IsJournal), /// Create draft for a new journal entry. - New { - #[structopt(help = "Title of new draft")] - title: String, - - #[structopt(long, help = "Add link to a topic page")] - topic: Option, - }, + New(cmd::New), /// Create topic page. - NewTopic { - #[structopt(help = "Path to topic page in journal")] - path: PathBuf, - - #[structopt(help = "Title of topic page")] - title: String, - }, + NewTopic(cmd::NewTopic), /// Invoke editor on journal entry draft. - Edit { - /// Draft id. - draft: String, - }, + Edit(cmd::Edit), /// Finish a journal entry draft. - Finish { - /// Draft id. - draft: String, - - /// Set base name of published file. - basename: String, - }, + Finish(cmd::Finish), } -- cgit v1.2.1