use crate::control::catalog_entry::CatalogEntry;
use crate::control::catalog_entry::apply::local::apply_locally_if_needed;
use crate::control::metadata_proposer::propose_catalog_entry;
use crate::control::server::shared::ddl::result::{DdlError, DdlResult};
use crate::control::state::SharedState;
pub(super) fn err(sqlstate: &str, message: impl Into<String>) -> DdlError {
DdlError {
sqlstate: sqlstate.to_string(),
message: message.into(),
}
}
pub(super) fn status(command: &str) -> Vec<DdlResult> {
vec![DdlResult::Status {
command: command.to_string(),
rows_affected: None,
}]
}
pub(super) fn propose_and_apply(
state: &SharedState,
entry: &CatalogEntry,
) -> Result<u64, DdlError> {
let log_index = propose_catalog_entry(state, entry)
.map_err(|e| err("XX000", format!("metadata propose: {e}")))?;
apply_locally_if_needed(state, entry, log_index);
Ok(log_index)
}
pub(super) async fn propose_and_apply_async(
state: &SharedState,
entry: CatalogEntry,
) -> Result<u64, DdlError> {
let log_index = propose_catalog_entry(state, &entry)
.map_err(|e| err("XX000", format!("metadata propose: {e}")))?;
if log_index == 0 {
let catalog = state.credentials.catalog().clone();
tokio::task::spawn_blocking(move || {
crate::control::catalog_entry::apply::apply_to(&entry, &catalog)
})
.await
.map_err(|e| err("XX000", format!("catalog apply join: {e}")))?;
}
Ok(log_index)
}