Skip to content

Commit 064b794

Browse files
committed
libsql: Make sync_db_if_needed() work in offline mode
In preparation for erroring database open if boostrap fails, make sure sync_db_if_needed() is robust in offline mode and does not probe the server if we already have a database and metadata files.
1 parent 7fbef83 commit 064b794

File tree

1 file changed

+11
-10
lines changed

1 file changed

+11
-10
lines changed

libsql/src/sync.rs

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -621,7 +621,14 @@ impl SyncContext {
621621
Ok(info)
622622
}
623623

624-
async fn sync_db_if_needed(&mut self, generation: u32) -> Result<()> {
624+
async fn sync_db_if_needed(&mut self) -> Result<()> {
625+
let db_file_exists = check_if_file_exists(&self.db_path)?;
626+
let metadata_exists = check_if_file_exists(&format!("{}-info", self.db_path))?;
627+
if db_file_exists && metadata_exists {
628+
return Ok(());
629+
}
630+
let info = self.get_remote_info().await?;
631+
let generation = info.current_generation;
625632
// somehow we are ahead of the remote in generations. following should not happen because
626633
// we checkpoint only if the remote server tells us to do so.
627634
if self.durable_generation > generation {
@@ -641,8 +648,6 @@ impl SyncContext {
641648
// then local db is in an incorrect state. we stop and return with an error
642649
// 3. if the db file exists and the metadata file exists, then we don't need to do the
643650
// sync
644-
let metadata_exists = check_if_file_exists(&format!("{}-info", self.db_path))?;
645-
let db_file_exists = check_if_file_exists(&self.db_path)?;
646651
match (metadata_exists, db_file_exists) {
647652
(false, false) => {
648653
// neither the db file nor the metadata file exists, lets bootstrap from remote
@@ -675,8 +680,8 @@ impl SyncContext {
675680
.into())
676681
}
677682
(true, true) => {
678-
// both files exists, no need to sync
679-
Ok(())
683+
// We already handled this case earlier in the function.
684+
unreachable!();
680685
}
681686
}
682687
}
@@ -820,11 +825,7 @@ pub async fn bootstrap_db(sync_ctx: &mut SyncContext) -> Result<()> {
820825
// we need to do this when we notice a large gap in generations, when bootstrapping is cheaper
821826
// than pulling each frame
822827
if !sync_ctx.initial_server_sync {
823-
// sync is being called first time. so we will call remote, get the generation information
824-
// if we are lagging behind, then we will call the export API and get to the latest
825-
// generation directly.
826-
let info = sync_ctx.get_remote_info().await?;
827-
sync_ctx.sync_db_if_needed(info.current_generation).await?;
828+
sync_ctx.sync_db_if_needed().await?;
828829
// when sync_ctx is initialised, we set durable_generation to 0. however, once
829830
// sync_db is called, it should be > 0.
830831
assert!(sync_ctx.durable_generation > 0, "generation should be > 0");

0 commit comments

Comments
 (0)