DatabaseSnapshotPool

A database connection that allows concurrent accesses to an unchanging database content, as it existed at the moment the snapshot was created.

DatabaseSnapshotPool.swift:80
final class DatabaseSnapshotPool

Overview

A DatabaseSnapshotPool never sees any database modification during all its lifetime. All database accesses performed from a snapshot always see the same identical database content.

It creates a pool of up to maximumReaderCount read-only SQLite connections. All read accesses are executed in reader dispatch queues (one per read-only SQLite connection). SQLite connections are closed when the DatabasePool is deallocated.

An SQLite database in the WAL mode is required for creating a DatabaseSnapshotPool.

Usage

You create a DatabaseSnapshotPool from a WAL mode database, such as databases created from a DatabasePool:

let dbPool = try DatabasePool(path: "/path/to/database.sqlite")
let snapshot = try dbPool.makeSnapshotPool()

When you want to control the database state seen by a snapshot, create the snapshot from a database connection, outside of a write transaction. You can for example take snapshots from a ValueObservation:

// An observation of the 'player' table
// that notifies fresh database snapshots:
let observation = ValueObservation.tracking { db in
    // Don't fetch players now, and return a snapshot instead.
    // Register an access to the player table so that the
    // observation tracks changes to this table.
    try db.registerAccess(to: Player.all())
    return try DatabaseSnapshotPool(db)
}

// Start observing the 'player' table
let cancellable = try observation.start(in: dbPool) { error in
    // Handle error
} onChange: { (snapshot: DatabaseSnapshotPool) in
    // Handle a fresh snapshot
}

DatabaseSnapshotPool inherits its database access methods from the DatabaseReader protocols.

Related SQLite documentation:

Creating a DatabaseSnapshotPool

See also makeSnapshotPool.