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:
parent
a49b9b4ecb
commit
07d17c9e93
10 changed files with 94 additions and 65 deletions
58
migra-cli/src/app.rs
Normal file
58
migra-cli/src/app.rs
Normal 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(())
|
||||||
|
}
|
||||||
|
}
|
|
@ -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");
|
||||||
}
|
}
|
||||||
|
|
|
@ -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();
|
||||||
|
|
|
@ -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() {
|
||||||
|
|
|
@ -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(
|
||||||
|
|
|
@ -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
|
||||||
|
|
|
@ -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();
|
||||||
|
|
||||||
|
|
|
@ -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(),
|
||||||
|
|
|
@ -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(())
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -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,
|
||||||
|
|
Reference in a new issue