use fsqlite_core::connection::Connection;
use fsqlite_types::SqliteValue;
const RENAME_SCRIPT: &[&str] = &[
"CREATE TABLE t(id INTEGER PRIMARY KEY AUTOINCREMENT, v TEXT)",
"INSERT INTO t(v) VALUES('a'),('b'),('c')",
"ALTER TABLE t RENAME TO t2",
"INSERT INTO t2(v) VALUES('d')",
];
const DROP_SCRIPT: &[&str] = &[
"CREATE TABLE t(id INTEGER PRIMARY KEY AUTOINCREMENT, v TEXT)",
"INSERT INTO t(v) VALUES('a'),('b'),('c')",
"ALTER TABLE t RENAME TO t2",
"DROP TABLE t2",
];
fn oracle_seq_rows(script: &[&str]) -> Vec<(String, i64)> {
let conn = rusqlite::Connection::open_in_memory().unwrap();
for s in script {
conn.execute(s, []).unwrap();
}
conn.prepare("SELECT name, seq FROM sqlite_sequence ORDER BY name")
.unwrap()
.query_map([], |r| Ok((r.get::<_, String>(0)?, r.get::<_, i64>(1)?)))
.unwrap()
.map(Result::unwrap)
.collect()
}
async fn fsqlite_seq_rows(script: &[&str]) -> Vec<(String, i64)> {
let conn = Connection::open(":memory:").await.unwrap();
for s in script {
conn.execute(s)
.await
.unwrap_or_else(|e| panic!("`{s}`: {e:?}"));
}
let rows = conn
.query("SELECT name, seq FROM sqlite_sequence ORDER BY name")
.await
.expect("select sqlite_sequence");
rows.iter()
.map(|r| {
let name = match r.values()[0] {
SqliteValue::Text(ref s) => s.as_ref().to_owned(),
ref other => panic!("name not text: {other:?}"),
};
let seq = match r.values()[1] {
SqliteValue::Integer(n) => n,
ref other => panic!("seq not int: {other:?}"),
};
(name, seq)
})
.collect()
}
#[test]
fn alter_rename_sqlite_sequence_matches_rusqlite_oracle() {
asupersync::test_utils::run_test(|| async {
let expected_rename = oracle_seq_rows(RENAME_SCRIPT);
assert_eq!(
expected_rename,
vec![("t2".to_owned(), 4)],
"oracle premise (rename)"
);
assert_eq!(
fsqlite_seq_rows(RENAME_SCRIPT).await,
expected_rename,
"ALTER RENAME must move the sqlite_sequence row (no stale 't' entry)"
);
let expected_drop = oracle_seq_rows(DROP_SCRIPT);
assert_eq!(expected_drop, Vec::new(), "oracle premise (drop)");
assert_eq!(
fsqlite_seq_rows(DROP_SCRIPT).await,
expected_drop,
"DROP after RENAME must leave no orphan sqlite_sequence row"
);
});
}