Skip to main content

WALRecovery

Struct WALRecovery 

Source
pub struct WALRecovery { /* private fields */ }
Expand description

WAL recovery engine

Reconstructs database state by replaying WAL records. Uses in-memory page cache during recovery; actual page operations are deferred until BTreeManager integration.

§Recovery Process

  1. Open WAL file and read header
  2. Read records sequentially until EOF or unrecoverable error
  3. For each valid record, update internal state
  4. Return final header state and statistics

§Note

This is a simplified recovery implementation that works without BTreeManager. Full integration with BTreeManager is deferred to Task 65-04.

Implementations§

Source§

impl WALRecovery

Source

pub fn new(wal_path: PathBuf) -> Self

Create a new WAL recovery engine

Source

pub fn stats(&self) -> &WALRecoveryStats

Get recovery statistics

Source

pub fn checkpoint_header(&self) -> Option<&PersistentHeaderV3>

Get last checkpoint header (if any)

Source

pub fn last_lsn(&self) -> u64

Get last LSN processed

Source

pub fn page_cache(&self) -> &HashMap<u64, Vec<u8>>

Get in-memory page cache

Source

pub fn recover(&mut self) -> NativeResult<()>

Recover from WAL file

Reads WAL file and applies all records sequentially. Returns Ok(()) on successful recovery, even if some records were skipped.

Source

pub fn get_header_state(&self) -> Option<&PersistentHeaderV3>

Get header state from last checkpoint (if available)

Returns the PersistentHeaderV3 that was captured in the most recent checkpoint record. This can be used to restore the database to a consistent state.

Source

pub fn recover_kv(&mut self, kv_store: &mut KvStore) -> NativeResult<usize>

Recover KV state from WAL records

Replays only KV-related records (KvSet, KvDelete, KvTombstone) to rebuild an in-memory KvStore. This is called during V3Backend::open() to restore KV durability across close/reopen cycles.

§V3 KV RECOVERY CONTRACT
§Recovery Precedence (in order):
  1. WAL replay (authoritative): If WAL exists, replay all KV records
    • This captures the latest state including mutations after last flush
  2. Checkpoint fallback: If WAL missing, read checkpoint file
    • This captures the last flushed state (before WAL truncation)
  3. Empty KV: If neither WAL nor checkpoint recoverable
    • Returns Ok(0) to indicate no KV records applied
    • Caller decides whether to continue with empty KV
§Corruption Handling:
  • Corrupt checkpoint files are auto-deleted (see cleanup_corrupt_checkpoint)
  • Checkpoint errors do NOT propagate (return Ok(0) instead)
  • WAL errors DO propagate (WAL is authoritative, corruption is serious)
§Lifecycle Scenarios:
  • After flush(): checkpoint=latest, WAL=empty → checkpoint recovery
  • Before flush(): WAL=latest, checkpoint=stale → WAL recovery
  • Corrupt checkpoint + valid WAL → WAL recovery (checkpoint never checked)
  • Corrupt checkpoint + no WAL → empty KV (checkpoint deleted, logged)
§Arguments
  • kv_store - Mutable reference to the KvStore to rebuild
§Returns
  • Ok(kv_records_applied) - Number of KV records successfully applied
  • Err(NativeBackendError) - If WAL file cannot be read (WAL errors propagate)

Trait Implementations§

Source§

impl Debug for WALRecovery

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more

Auto Trait Implementations§

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> IntoEither for T

Source§

fn into_either(self, into_left: bool) -> Either<Self, Self>

Converts self into a Left variant of Either<Self, Self> if into_left is true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

fn into_either_with<F>(self, into_left: F) -> Either<Self, Self>
where F: FnOnce(&Self) -> bool,

Converts self into a Left variant of Either<Self, Self> if into_left(&self) returns true. Converts self into a Right variant of Either<Self, Self> otherwise. Read more
Source§

impl<T> Pointable for T

Source§

const ALIGN: usize

The alignment of pointer.
Source§

type Init = T

The type for initializers.
Source§

unsafe fn init(init: <T as Pointable>::Init) -> usize

Initializes a with the given initializer. Read more
Source§

unsafe fn deref<'a>(ptr: usize) -> &'a T

Dereferences the given pointer. Read more
Source§

unsafe fn deref_mut<'a>(ptr: usize) -> &'a mut T

Mutably dereferences the given pointer. Read more
Source§

unsafe fn drop(ptr: usize)

Drops the object pointed to by the given pointer. Read more
Source§

impl<T> Same for T

Source§

type Output = T

Should always be Self
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = Infallible

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, <T as TryFrom<U>>::Error>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.
Source§

impl<V, T> VZip<V> for T
where V: MultiLane<T>,

Source§

fn vzip(self) -> V