From 58d2f63f4577bc701b6bd655064cefebb65118b4 Mon Sep 17 00:00:00 2001 From: Melody Horn / boringcactus Date: Wed, 16 Jun 2021 14:22:50 -0600 Subject: actually run migrations --- src/db/migration/change.rs | 62 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 62 insertions(+) create mode 100644 src/db/migration/change.rs (limited to 'src/db/migration/change.rs') diff --git a/src/db/migration/change.rs b/src/db/migration/change.rs new file mode 100644 index 0000000..b5d0dd5 --- /dev/null +++ b/src/db/migration/change.rs @@ -0,0 +1,62 @@ +use diesel::Connection; + +use crate::db::backend::Connectable; +use crate::db::models::Field; + +pub enum DatabaseChange { + CreateModel { + name: &'static str, + fields: &'static [Field], + options: &'static [CreateModelOption] + }, +} + +impl DatabaseChange { + pub fn apply(&self, app_name: &str, connection: &C::Connection) { + use barrel::{Migration, Table, types}; + + match self { + DatabaseChange::CreateModel { name, fields, options } => { + let mut m = Migration::new(); + + let columns: Vec<(&'static str, _)> = fields.iter().map(|field| match field { + Field::CharField { name, max_length } => { + let name = *name; + let _type = match max_length { + None => types::text(), + Some(max_length) => types::varchar(*max_length), + }; + (name, _type) + } + Field::DateTimeField { name } => { + (*name, types::text()) // TODO do smart things on non-sqlite + } + Field::IntField { name } => { + (*name, types::integer()) + } + }).collect(); + + let callback = move |t: &mut Table| { + for (name, _type) in &columns { + t.add_column(*name, _type.clone()); + } + }; + + let table_name = format!("{}-{}", app_name, name); + + if options.contains(&CreateModelOption::IfNotExist) { + m.create_table_if_not_exists(table_name, callback); + } else { + m.create_table(table_name, callback); + } + + connection.execute(&m.make::()).unwrap(); + } + } + } +} + +#[derive(PartialEq)] +pub enum CreateModelOption { + IfNotExist, +} -- cgit v1.2.3