ticket: own typed schema migrations
This commit is contained in:
@@ -131,7 +131,7 @@ impl SqliteWorkspaceAuthority {
|
||||
Ok(Self {
|
||||
workspace_id: workspace_id.clone(),
|
||||
store: SqliteWorkspaceStore::open(&database_path)?,
|
||||
ticket_backend: SqliteTicketBackend::new(database_path, workspace_id),
|
||||
ticket_backend: SqliteTicketBackend::open_verified(database_path, workspace_id)?,
|
||||
})
|
||||
}
|
||||
|
||||
@@ -725,7 +725,8 @@ mod tests {
|
||||
let dir = tempfile::tempdir().unwrap();
|
||||
write_ticket(dir.path(), "00000000001J2", "Read bridge", "ready");
|
||||
let db_path = dir.path().join("workspace.db");
|
||||
SqliteTicketBackend::new(&db_path, "workspace-test")
|
||||
SqliteTicketBackend::open(&db_path, "workspace-test")
|
||||
.unwrap()
|
||||
.import_from_local_backend(&ticket::LocalTicketBackend::new(
|
||||
dir.path().join(".yoi/tickets"),
|
||||
))
|
||||
|
||||
@@ -2383,10 +2383,10 @@ struct BrowserCloseTicketRequest {
|
||||
fn browser_ticket_backend(api: &WorkspaceApi) -> Result<SqliteTicketBackend> {
|
||||
let config = ticket::config::TicketConfig::load_workspace(&api.config.workspace_root)
|
||||
.map_err(|error| Error::Config(format!("load Ticket workspace settings: {error}")))?;
|
||||
Ok(SqliteTicketBackend::new(
|
||||
Ok(SqliteTicketBackend::open_verified(
|
||||
api.config.database_path.clone(),
|
||||
api.config.workspace_id.clone(),
|
||||
)
|
||||
)?
|
||||
.with_record_language(config.ticket_record_language()))
|
||||
}
|
||||
|
||||
@@ -2553,10 +2553,11 @@ async fn execute_worker_ticket_rest_operation(
|
||||
validate_workspace_scope(api, workspace_id)?;
|
||||
let config = ticket::config::TicketConfig::load_workspace(&api.config.workspace_root)
|
||||
.map_err(|error| Error::Config(format!("load Ticket workspace settings: {error}")))?;
|
||||
let mut backend = SqliteTicketBackend::new(
|
||||
let mut backend = SqliteTicketBackend::open_verified(
|
||||
api.config.database_path.clone(),
|
||||
api.config.workspace_id.clone(),
|
||||
)
|
||||
.map_err(Error::from)?
|
||||
.with_record_language(config.ticket_record_language());
|
||||
let operation_kind = ticket_mutation_operation_kind(&operation);
|
||||
let is_mutation = operation_kind != "read";
|
||||
@@ -15225,7 +15226,7 @@ mod tests {
|
||||
) {
|
||||
use ticket::TicketBackend as _;
|
||||
|
||||
let backend = ticket::SqliteTicketBackend::new(database_path, workspace_id);
|
||||
let backend = ticket::SqliteTicketBackend::open(database_path, workspace_id).unwrap();
|
||||
let mut input = ticket::NewTicket::new(title);
|
||||
input.workflow_state = Some(state);
|
||||
backend.create(input).unwrap();
|
||||
|
||||
@@ -754,6 +754,7 @@ impl SqliteWorkspaceStore {
|
||||
pub fn from_connection(conn: Connection) -> Result<Self> {
|
||||
configure_sqlite(&conn)?;
|
||||
apply_migrations(&conn)?;
|
||||
ticket::migrate_sqlite_ticket_schema(&conn)?;
|
||||
Ok(Self {
|
||||
conn: Arc::new(Mutex::new(conn)),
|
||||
})
|
||||
@@ -4526,6 +4527,45 @@ mod tests {
|
||||
use super::*;
|
||||
use std::collections::BTreeSet;
|
||||
|
||||
#[test]
|
||||
fn startup_composes_ticket_migrations_when_control_plane_is_current() {
|
||||
let conn = Connection::open_in_memory().unwrap();
|
||||
configure_sqlite(&conn).unwrap();
|
||||
apply_migrations(&conn).unwrap();
|
||||
assert!(!table_exists(&conn, "ticket_schema_migrations").unwrap());
|
||||
|
||||
let store = SqliteWorkspaceStore::from_connection(conn).unwrap();
|
||||
store
|
||||
.with_conn(|conn| {
|
||||
ticket::verify_sqlite_ticket_schema(conn)?;
|
||||
let latest = conn.query_row(
|
||||
"SELECT MAX(version) FROM ticket_schema_migrations",
|
||||
[],
|
||||
|row| row.get::<_, i64>(0),
|
||||
)?;
|
||||
assert_eq!(latest, ticket::LATEST_SQLITE_TICKET_SCHEMA_VERSION);
|
||||
Ok(())
|
||||
})
|
||||
.unwrap();
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn startup_fails_closed_when_current_ticket_schema_has_drifted() {
|
||||
let conn = Connection::open_in_memory().unwrap();
|
||||
configure_sqlite(&conn).unwrap();
|
||||
apply_migrations(&conn).unwrap();
|
||||
ticket::migrate_sqlite_ticket_schema(&conn).unwrap();
|
||||
conn.execute_batch("DROP TABLE typed_ticket_artifacts")
|
||||
.unwrap();
|
||||
|
||||
let result = SqliteWorkspaceStore::from_connection(conn);
|
||||
let error = match result {
|
||||
Ok(_) => panic!("schema drift unexpectedly passed startup verification"),
|
||||
Err(error) => error,
|
||||
};
|
||||
assert!(error.to_string().contains("typed_ticket_artifacts"));
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn removes_unused_control_plane_ticket_tables() {
|
||||
let conn = Connection::open_in_memory().unwrap();
|
||||
|
||||
Reference in New Issue
Block a user