use std::fmt::Write;
use cratestack_sql::ModelDescriptor;
pub fn create_table_sql<M, PK>(descriptor: &ModelDescriptor<M, PK>) -> String {
let mut sql = format!("CREATE TABLE IF NOT EXISTS {} (\n", descriptor.table_name);
for (idx, column) in descriptor.columns.iter().enumerate() {
if idx > 0 {
sql.push_str(",\n");
}
let _ = write!(&mut sql, " {} BLOB", column.sql_name);
if column.sql_name == descriptor.primary_key {
sql.push_str(" PRIMARY KEY");
}
}
if let Some(deleted_at) = descriptor.soft_delete_column
&& !descriptor.columns.iter().any(|c| c.sql_name == deleted_at)
{
sql.push_str(",\n ");
sql.push_str(deleted_at);
sql.push_str(" BLOB");
}
sql.push_str("\n)");
sql
}
#[cfg(test)]
mod tests {
use super::*;
use cratestack_sql::ModelColumn;
fn descriptor() -> ModelDescriptor<(), i64> {
const COLUMNS: &[ModelColumn] = &[
ModelColumn {
rust_name: "id",
sql_name: "id",
},
ModelColumn {
rust_name: "title",
sql_name: "title",
},
];
ModelDescriptor::new(
"Post",
"posts",
COLUMNS,
"id",
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
&[],
None,
false,
&[],
&[],
None,
None,
&[],
)
}
#[test]
fn create_table_marks_primary_key_inline() {
let sql = create_table_sql(&descriptor());
assert!(sql.contains("id BLOB PRIMARY KEY"), "got: {sql}");
assert!(sql.contains("title BLOB"), "got: {sql}");
}
#[test]
fn soft_delete_column_is_added_when_not_in_columns() {
let mut d = descriptor();
d.soft_delete_column = Some("deleted_at");
let sql = create_table_sql(&d);
assert!(sql.contains("deleted_at BLOB"), "got: {sql}");
}
}