TLDR: The conflict range is the entire SQLite database. mvsqlite does not support concurrent read-write transactions to the same DB. If multiple RW transactions with overlapping [read_version, commit_version] ranges are are requested to be committed, only one of the commits will succeed.
To scale out writes, you can use smaller databases - one database per user, for example. It is possible to do multi-database serializable transactions with mvsqlite (not yet implemented, but the logic shouldn't be complex).
mvsqlite actually doesn't just use FDB's native transaction, as I would like to avoid FDB's low txn size and time limits. Instead, there are two separate keyspaces for each SQLite DB - one "page index" keyspace, and one content-addressed store keyspace.
For reads: Pages are fully versioned, so they are always snapshot-readable in the future. The read version is fetched from `mvstore` when each SQLite transaction starts, and is used as the page index per-page range scan upper bound in future read requests.
For writes: Pages are first written to the content-addressed store keyed by the page's hash. At commit, hashes of each written page in the SQLite transaction is written to the page index in a single FDB transaction to preserve atomicity. With 8K pages and ~60B per key-value entry in the page index, each SQLite transaction can be as large as 1.3 GB (compared to FDB's native txn size limit of 10 MB).
So actually, you can do one page read or write per FDB transaction and still preserve ACID properties.