[][src]Trait async_raft::storage::RaftStorage

pub trait RaftStorage<D, R>: Send + Sync + 'static where
    D: AppData,
    R: AppDataResponse
{ type Snapshot: AsyncRead + AsyncWrite + AsyncSeek + Send + Unpin + 'static; type ShutdownError: Error + Send + Sync + 'static; #[must_use] pub fn get_membership_config<'life0, 'async_trait>(
        &'life0 self
    ) -> Pin<Box<dyn Future<Output = Result<MembershipConfig>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn get_initial_state<'life0, 'async_trait>(
        &'life0 self
    ) -> Pin<Box<dyn Future<Output = Result<InitialState>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn save_hard_state<'life0, 'life1, 'async_trait>(
        &'life0 self,
        hs: &'life1 HardState
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        'life1: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn get_log_entries<'life0, 'async_trait>(
        &'life0 self,
        start: u64,
        stop: u64
    ) -> Pin<Box<dyn Future<Output = Result<Vec<Entry<D>>>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn delete_logs_from<'life0, 'async_trait>(
        &'life0 self,
        start: u64,
        stop: Option<u64>
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn append_entry_to_log<'life0, 'life1, 'async_trait>(
        &'life0 self,
        entry: &'life1 Entry<D>
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        'life1: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn replicate_to_log<'life0, 'life1, 'async_trait>(
        &'life0 self,
        entries: &'life1 [Entry<D>]
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        'life1: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn apply_entry_to_state_machine<'life0, 'life1, 'life2, 'async_trait>(
        &'life0 self,
        index: &'life1 u64,
        data: &'life2 D
    ) -> Pin<Box<dyn Future<Output = Result<R>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        'life1: 'async_trait,
        'life2: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn replicate_to_state_machine<'life0, 'life1, 'life2, 'life3, 'async_trait>(
        &'life0 self,
        entries: &'life1 [(&'life2 u64, &'life3 D)]
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        'life1: 'async_trait,
        'life2: 'async_trait,
        'life3: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn do_log_compaction<'life0, 'async_trait>(
        &'life0 self
    ) -> Pin<Box<dyn Future<Output = Result<CurrentSnapshotData<Self::Snapshot>>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn create_snapshot<'life0, 'async_trait>(
        &'life0 self
    ) -> Pin<Box<dyn Future<Output = Result<(String, Box<Self::Snapshot>)>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn finalize_snapshot_installation<'life0, 'async_trait>(
        &'life0 self,
        index: u64,
        term: u64,
        delete_through: Option<u64>,
        id: String,
        snapshot: Box<Self::Snapshot>
    ) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
;
#[must_use] pub fn get_current_snapshot<'life0, 'async_trait>(
        &'life0 self
    ) -> Pin<Box<dyn Future<Output = Result<Option<CurrentSnapshotData<Self::Snapshot>>>> + Send + 'async_trait>>
    where
        'life0: 'async_trait,
        Self: 'async_trait
; }

A trait defining the interface for a Raft storage system.

See the storage chapter of the guide for details and discussion on this trait and how to implement it.

Associated Types

type Snapshot: AsyncRead + AsyncWrite + AsyncSeek + Send + Unpin + 'static[src]

The storage engine's associated type used for exposing a snapshot for reading & writing.

See the storage chapter of the guide for details on where and how this is used.

type ShutdownError: Error + Send + Sync + 'static[src]

The error type used to indicate to Raft that shutdown is needed when calling the apply_entry_to_state_machine method.

This error type is only considered for the apply_entry_to_state_machine method as it is the only method which is allowed to return errors normally as part of application logic.

For all other methods of this trait, returning an error will cause Raft to shutdown.

Loading content...

Required methods

#[must_use]pub fn get_membership_config<'life0, 'async_trait>(
    &'life0 self
) -> Pin<Box<dyn Future<Output = Result<MembershipConfig>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Get the latest membership config found in the log.

This must always be implemented as a reverse search through the log to find the most recent membership config to be appended to the log.

If a snapshot pointer is encountered, then the membership config embedded in that snapshot pointer should be used.

If the system is pristine, then it should return the value of calling MembershipConfig::new_initial(node_id). It is required that the storage engine persist the node's ID so that it is consistent across restarts.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn get_initial_state<'life0, 'async_trait>(
    &'life0 self
) -> Pin<Box<dyn Future<Output = Result<InitialState>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Get Raft's state information from storage.

When the Raft node is first started, it will call this interface on the storage system to fetch the last known state from stable storage. If no such entry exists due to being the first time the node has come online, then InitialState::new_initial should be used.

Pro tip: the storage impl may need to look in a few different places to accurately respond to this request: the last entry in the log for last_log_index & last_log_term; the node's hard state record; and the index of the last log applied to the state machine.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn save_hard_state<'life0, 'life1, 'async_trait>(
    &'life0 self,
    hs: &'life1 HardState
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    'life1: 'async_trait,
    Self: 'async_trait, 
[src]

Save Raft's hard-state.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn get_log_entries<'life0, 'async_trait>(
    &'life0 self,
    start: u64,
    stop: u64
) -> Pin<Box<dyn Future<Output = Result<Vec<Entry<D>>>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Get a series of log entries from storage.

The start value is inclusive in the search and the stop value is non-inclusive: [start, stop).

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn delete_logs_from<'life0, 'async_trait>(
    &'life0 self,
    start: u64,
    stop: Option<u64>
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Delete all logs starting from start and stopping at stop, else continuing to the end of the log if stop is None.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn append_entry_to_log<'life0, 'life1, 'async_trait>(
    &'life0 self,
    entry: &'life1 Entry<D>
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    'life1: 'async_trait,
    Self: 'async_trait, 
[src]

Append a new entry to the log.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn replicate_to_log<'life0, 'life1, 'async_trait>(
    &'life0 self,
    entries: &'life1 [Entry<D>]
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    'life1: 'async_trait,
    Self: 'async_trait, 
[src]

Replicate a payload of entries to the log.

Though the entries will always be presented in order, each entry's index should be used to determine its location to be written in the log.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn apply_entry_to_state_machine<'life0, 'life1, 'life2, 'async_trait>(
    &'life0 self,
    index: &'life1 u64,
    data: &'life2 D
) -> Pin<Box<dyn Future<Output = Result<R>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    'life1: 'async_trait,
    'life2: 'async_trait,
    Self: 'async_trait, 
[src]

Apply the given log entry to the state machine.

The Raft protocol guarantees that only logs which have been committed, that is, logs which have been replicated to a majority of the cluster, will be applied to the state machine.

This is where the business logic of interacting with your application's state machine should live. This is 100% application specific. Perhaps this is where an application specific transaction is being started, or perhaps committed. This may be where a key/value is being stored. This may be where an entry is being appended to an immutable log.

Error handling for this method is note worthy. If an error is returned from a call to this method, the error will be inspected, and if the error is an instance of RaftStorage::ShutdownError, then Raft will go into shutdown in order to preserve the safety of the data and avoid corruption. Any other errors will be propagated back up to the Raft.client_write call point.

It is important to note that even in cases where an application specific error is returned, implementations should still record that the entry has been applied to the state machine.

#[must_use]pub fn replicate_to_state_machine<'life0, 'life1, 'life2, 'life3, 'async_trait>(
    &'life0 self,
    entries: &'life1 [(&'life2 u64, &'life3 D)]
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    'life1: 'async_trait,
    'life2: 'async_trait,
    'life3: 'async_trait,
    Self: 'async_trait, 
[src]

Apply the given payload of entries to the state machine, as part of replication.

The Raft protocol guarantees that only logs which have been committed, that is, logs which have been replicated to a majority of the cluster, will be applied to the state machine.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn do_log_compaction<'life0, 'async_trait>(
    &'life0 self
) -> Pin<Box<dyn Future<Output = Result<CurrentSnapshotData<Self::Snapshot>>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Perform log compaction, returning a handle to the generated snapshot.

implementation guide

When performing log compaction, the compaction can only cover the breadth of the log up to the last applied log and under write load this value may change quickly. As such, the storage implementation should export/checkpoint/snapshot its state machine, and then use the value of that export's last applied log as the metadata indicating the breadth of the log covered by the snapshot.

Errors returned from this method will be logged and retried.

#[must_use]pub fn create_snapshot<'life0, 'async_trait>(
    &'life0 self
) -> Pin<Box<dyn Future<Output = Result<(String, Box<Self::Snapshot>)>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Create a new blank snapshot, returning a writable handle to the snapshot object along with the ID of the snapshot.

implementation guide

See the storage chapter of the guide for details on log compaction / snapshotting.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn finalize_snapshot_installation<'life0, 'async_trait>(
    &'life0 self,
    index: u64,
    term: u64,
    delete_through: Option<u64>,
    id: String,
    snapshot: Box<Self::Snapshot>
) -> Pin<Box<dyn Future<Output = Result<()>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Finalize the installation of a snapshot which has finished streaming from the cluster leader.

Delete all entries in the log through delete_through, unless None, in which case all entries of the log are to be deleted.

Write a new snapshot pointer to the log at the given index. The snapshot pointer should be constructed via the Entry::new_snapshot_pointer constructor and the other parameters provided to this method.

All other snapshots should be deleted at this point.

snapshot

A snapshot created from an earlier call to created_snapshot which provided the snapshot. By the time ownership of the snapshot object is returned here, its AsyncWriteExt.shutdown() method will have been called, so no additional writes should be made to the snapshot.

Errors returned from this method will cause Raft to go into shutdown.

#[must_use]pub fn get_current_snapshot<'life0, 'async_trait>(
    &'life0 self
) -> Pin<Box<dyn Future<Output = Result<Option<CurrentSnapshotData<Self::Snapshot>>>> + Send + 'async_trait>> where
    'life0: 'async_trait,
    Self: 'async_trait, 
[src]

Get a readable handle to the current snapshot, along with its metadata.

implementation algorithm

Implementing this method should be straightforward. Check the configured snapshot directory for any snapshot files. A proper implementation will only ever have one active snapshot, though another may exist while it is being created. As such, it is recommended to use a file naming pattern which will allow for easily distinguishing between the current live snapshot, and any new snapshot which is being created.

A proper snapshot implementation will store the term, index and membership config as part of the snapshot, which should be decoded for creating this method's response data.

Errors returned from this method will cause Raft to go into shutdown.

Loading content...

Implementors

Loading content...