Archived
1
0
Fork 0

refac: preparatory work for subsequent changes

Moved the main logic such as running a command or getting a config
into it.

Changed incoming paramenters for commands.
This commit is contained in:
Dmitriy Pleshevskiy 2021-04-08 01:26:30 +03:00
parent a49b9b4ecb
commit 07d17c9e93
10 changed files with 94 additions and 65 deletions

58
migra-cli/src/app.rs Normal file
View file

@ -0,0 +1,58 @@
use crate::commands;
use crate::error::*;
use crate::opts::Command;
use crate::AppOpt;
use crate::Config;
use std::path::PathBuf;
use structopt::StructOpt;
#[derive(Debug, Clone)]
pub(crate) struct App {
app_opt: AppOpt,
}
impl App {
pub fn new(app_opt: AppOpt) -> Self {
App { app_opt }
}
pub fn config_path(&self) -> Option<&PathBuf> {
self.app_opt.config_path.as_ref()
}
pub fn config(&self) -> MigraResult<Config> {
Config::read(self.config_path())
}
pub fn run_command(&self) -> StdResult<()> {
match self.app_opt.command.clone() {
Command::Init => {
commands::initialize_migra_manifest(self)?;
}
Command::Apply(cmd_opts) => {
commands::apply_sql(self, cmd_opts)?;
}
Command::Make(cmd_opts) => {
commands::make_migration(self, cmd_opts)?;
}
Command::List => {
commands::print_migration_lists(self)?;
}
Command::Upgrade(cmd_opts) => {
commands::upgrade_pending_migrations(self, cmd_opts)?;
}
Command::Downgrade(cmd_opts) => {
commands::rollback_applied_migrations(self, cmd_opts)?;
}
Command::Completions(cmd_opts) => {
AppOpt::clap().gen_completions_to(
env!("CARGO_BIN_NAME"),
cmd_opts.into(),
&mut std::io::stdout(),
);
}
}
Ok(())
}
}

View file

@ -1,18 +1,19 @@
use crate::config::Config; use crate::app::App;
use crate::database::prelude::*; use crate::database::prelude::*;
use crate::database::transaction::with_transaction; use crate::database::transaction::with_transaction;
use crate::database::{DatabaseConnectionManager, MigrationManager}; use crate::database::{DatabaseConnectionManager, MigrationManager};
use crate::opts::ApplyCommandOpt; use crate::opts::ApplyCommandOpt;
use crate::StdResult; use crate::StdResult;
pub(crate) fn apply_sql(config: Config, opts: ApplyCommandOpt) -> StdResult<()> { pub(crate) fn apply_sql(app: &App, cmd_opts: ApplyCommandOpt) -> StdResult<()> {
let config = app.config()?;
let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?; let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?;
let conn = connection_manager.connection(); let conn = connection_manager.connection();
let migration_manager = MigrationManager::new(); let migration_manager = MigrationManager::new();
let file_path = { let file_path = {
let mut file_path = config.directory_path().join(opts.file_name); let mut file_path = config.directory_path().join(cmd_opts.file_name);
if file_path.extension().is_none() { if file_path.extension().is_none() {
file_path.set_extension("sql"); file_path.set_extension("sql");
} }

View file

@ -1,4 +1,4 @@
use crate::config::Config; use crate::app::App;
use crate::database::prelude::*; use crate::database::prelude::*;
use crate::database::transaction::with_transaction; use crate::database::transaction::with_transaction;
use crate::database::{DatabaseConnectionManager, MigrationManager}; use crate::database::{DatabaseConnectionManager, MigrationManager};
@ -6,10 +6,8 @@ use crate::opts::DowngradeCommandOpt;
use crate::StdResult; use crate::StdResult;
use std::cmp; use std::cmp;
pub(crate) fn rollback_applied_migrations( pub(crate) fn rollback_applied_migrations(app: &App, opts: DowngradeCommandOpt) -> StdResult<()> {
config: Config, let config = app.config()?;
opts: DowngradeCommandOpt,
) -> StdResult<()> {
let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?; let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?;
let conn = connection_manager.connection(); let conn = connection_manager.connection();
let migration_manager = MigrationManager::new(); let migration_manager = MigrationManager::new();

View file

@ -1,9 +1,12 @@
use crate::app::App;
use crate::config::{Config, MIGRA_TOML_FILENAME}; use crate::config::{Config, MIGRA_TOML_FILENAME};
use crate::StdResult; use crate::StdResult;
use std::path::PathBuf; use std::path::PathBuf;
pub(crate) fn initialize_migra_manifest(config_path: Option<PathBuf>) -> StdResult<()> { pub(crate) fn initialize_migra_manifest(app: &App) -> StdResult<()> {
let config_path = config_path let config_path = app
.config_path()
.cloned()
.map(|mut config_path| { .map(|mut config_path| {
let ext = config_path.extension(); let ext = config_path.extension();
if config_path.is_dir() || ext.is_none() { if config_path.is_dir() || ext.is_none() {

View file

@ -1,4 +1,4 @@
use crate::config::Config; use crate::app::App;
use crate::database::migration::filter_pending_migrations; use crate::database::migration::filter_pending_migrations;
use crate::database::prelude::*; use crate::database::prelude::*;
use crate::database::{DatabaseConnectionManager, Migration, MigrationManager}; use crate::database::{DatabaseConnectionManager, Migration, MigrationManager};
@ -6,7 +6,8 @@ use crate::error::{Error, StdResult};
const EM_DASH: char = '—'; const EM_DASH: char = '—';
pub(crate) fn print_migration_lists(config: Config) -> StdResult<()> { pub(crate) fn print_migration_lists(app: &App) -> StdResult<()> {
let config = app.config()?;
let applied_migration_names = match config.database.connection_string() { let applied_migration_names = match config.database.connection_string() {
Ok(ref database_connection_string) => { Ok(ref database_connection_string) => {
let mut connection_manager = DatabaseConnectionManager::connect_with_string( let mut connection_manager = DatabaseConnectionManager::connect_with_string(

View file

@ -1,10 +1,11 @@
use crate::app::App;
use crate::opts::MakeCommandOpt; use crate::opts::MakeCommandOpt;
use crate::Config;
use crate::StdResult; use crate::StdResult;
use chrono::Local; use chrono::Local;
use std::fs; use std::fs;
pub(crate) fn make_migration(config: Config, opts: MakeCommandOpt) -> StdResult<()> { pub(crate) fn make_migration(app: &App, opts: MakeCommandOpt) -> StdResult<()> {
let config = app.config()?;
let now = Local::now().format("%y%m%d%H%M%S"); let now = Local::now().format("%y%m%d%H%M%S");
let migration_name: String = opts let migration_name: String = opts

View file

@ -1,11 +1,12 @@
use crate::app::App;
use crate::database::migration::*; use crate::database::migration::*;
use crate::database::transaction::with_transaction; use crate::database::transaction::with_transaction;
use crate::database::DatabaseConnectionManager; use crate::database::DatabaseConnectionManager;
use crate::opts::UpgradeCommandOpt; use crate::opts::UpgradeCommandOpt;
use crate::Config;
use crate::StdResult; use crate::StdResult;
pub(crate) fn upgrade_pending_migrations(config: Config, opts: UpgradeCommandOpt) -> StdResult<()> { pub(crate) fn upgrade_pending_migrations(app: &App, opts: UpgradeCommandOpt) -> StdResult<()> {
let config = app.config()?;
let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?; let mut connection_manager = DatabaseConnectionManager::connect(&config.database)?;
let conn = connection_manager.connection(); let conn = connection_manager.connection();

View file

@ -134,12 +134,12 @@ fn recursive_find_project_root() -> MigraResult<PathBuf> {
} }
impl Config { impl Config {
pub fn read(config_path: Option<PathBuf>) -> MigraResult<Config> { pub fn read(config_path: Option<&PathBuf>) -> MigraResult<Config> {
let config_path = match config_path { let config_path = match config_path {
Some(config_path) if config_path.is_dir() => { Some(config_path) if config_path.is_dir() => {
Some(config_path.join(MIGRA_TOML_FILENAME)) Some(config_path.join(MIGRA_TOML_FILENAME))
} }
Some(config_path) => Some(config_path), Some(config_path) => Some(config_path.clone()),
None => recursive_find_project_root() None => recursive_find_project_root()
.map(|path| path.join(MIGRA_TOML_FILENAME)) .map(|path| path.join(MIGRA_TOML_FILENAME))
.ok(), .ok(),

View file

@ -7,6 +7,7 @@ extern crate cfg_if;
#[cfg(not(any(feature = "postgres", feature = "mysql")))] #[cfg(not(any(feature = "postgres", feature = "mysql")))]
compile_error!(r#"Either features "postgres" or "mysql" must be enabled for "migra" crate"#); compile_error!(r#"Either features "postgres" or "mysql" must be enabled for "migra" crate"#);
mod app;
mod commands; mod commands;
mod config; mod config;
mod database; mod database;
@ -14,48 +15,13 @@ mod error;
mod opts; mod opts;
use crate::error::StdResult; use crate::error::StdResult;
use app::App;
use config::Config; use config::Config;
use opts::{AppOpt, Command, StructOpt}; use opts::{AppOpt, StructOpt};
use std::io;
fn main() -> StdResult<()> { fn main() -> StdResult<()> {
#[cfg(feature = "dotenv")] #[cfg(feature = "dotenv")]
dotenv::dotenv().ok(); dotenv::dotenv().ok();
let opt = AppOpt::from_args(); App::new(AppOpt::from_args()).run_command()
match opt.command {
Command::Init => {
commands::initialize_migra_manifest(opt.config)?;
}
Command::Apply(opts) => {
let config = Config::read(opt.config)?;
commands::apply_sql(config, opts)?;
}
Command::Make(opts) => {
let config = Config::read(opt.config)?;
commands::make_migration(config, opts)?;
}
Command::List => {
let config = Config::read(opt.config)?;
commands::print_migration_lists(config)?;
}
Command::Upgrade(opts) => {
let config = Config::read(opt.config)?;
commands::upgrade_pending_migrations(config, opts)?;
}
Command::Downgrade(opts) => {
let config = Config::read(opt.config)?;
commands::rollback_applied_migrations(config, opts)?;
}
Command::Completions(opts) => {
AppOpt::clap().gen_completions_to(
env!("CARGO_BIN_NAME"),
opts.into(),
&mut io::stdout(),
);
}
}
Ok(())
} }

View file

@ -2,17 +2,17 @@ use std::path::PathBuf;
use structopt::clap; use structopt::clap;
pub use structopt::StructOpt; pub use structopt::StructOpt;
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
#[structopt(bin_name = "migra", name = "Migra")] #[structopt(bin_name = "migra", name = "Migra")]
pub(crate) struct AppOpt { pub(crate) struct AppOpt {
#[structopt(short, long)] #[structopt(name = "config", short, long)]
pub config: Option<PathBuf>, pub config_path: Option<PathBuf>,
#[structopt(subcommand)] #[structopt(subcommand)]
pub command: Command, pub command: Command,
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) enum Command { pub(crate) enum Command {
Init, Init,
@ -32,20 +32,20 @@ pub(crate) enum Command {
Completions(CompletionsShell), Completions(CompletionsShell),
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) struct ApplyCommandOpt { pub(crate) struct ApplyCommandOpt {
#[structopt(parse(from_str))] #[structopt(parse(from_str))]
pub file_name: String, pub file_name: String,
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) struct MakeCommandOpt { pub(crate) struct MakeCommandOpt {
/// Name of the migration to create in specify directory. /// Name of the migration to create in specify directory.
#[structopt(parse(from_str))] #[structopt(parse(from_str))]
pub migration_name: String, pub migration_name: String,
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) struct UpgradeCommandOpt { pub(crate) struct UpgradeCommandOpt {
/// Name of the existing migration that will update the schema /// Name of the existing migration that will update the schema
/// in the database. /// in the database.
@ -57,7 +57,7 @@ pub(crate) struct UpgradeCommandOpt {
pub migrations_number: Option<usize>, pub migrations_number: Option<usize>,
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) struct DowngradeCommandOpt { pub(crate) struct DowngradeCommandOpt {
/// How many applied migrations do we have to rollback. /// How many applied migrations do we have to rollback.
#[structopt(long = "number", short = "n", default_value = "1")] #[structopt(long = "number", short = "n", default_value = "1")]
@ -68,7 +68,7 @@ pub(crate) struct DowngradeCommandOpt {
pub all_migrations: bool, pub all_migrations: bool,
} }
#[derive(Debug, StructOpt)] #[derive(Debug, StructOpt, Clone)]
pub(crate) enum CompletionsShell { pub(crate) enum CompletionsShell {
Bash, Bash,
Fish, Fish,