Skip to content

Commit 77de80e

Browse files
jorki02nvamelichev
authored andcommitted
Add Snapshot-read-only isolation support
You can read more about this type of isolation here https://ydb.tech/docs/en/concepts/transactions#modes
1 parent 56fd568 commit 77de80e

File tree

3 files changed

+37
-1
lines changed

3 files changed

+37
-1
lines changed

repository-ydb-v2/src/main/java/tech/ydb/yoj/repository/ydb/YdbRepositoryTransaction.java

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -233,6 +233,10 @@ private TxControl<?> getTxControl() {
233233
case ONLINE_CONSISTENT_READ_ONLY -> TxControl.onlineRo().setAllowInconsistentReads(false);
234234
case ONLINE_INCONSISTENT_READ_ONLY -> TxControl.onlineRo().setAllowInconsistentReads(true);
235235
case STALE_CONSISTENT_READ_ONLY -> TxControl.staleRo();
236+
case SNAPSHOT -> {
237+
TxControl<?> txControl = (txId != null ? TxControl.id(txId) : TxControl.snapshotRo());
238+
yield txControl.setCommitTx(false);
239+
}
236240
};
237241
}
238242

repository-ydb-v2/src/test/java/tech/ydb/yoj/repository/ydb/YdbRepositoryIntegrationTest.java

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@
3333
import tech.ydb.yoj.databind.schema.Column;
3434
import tech.ydb.yoj.databind.schema.ObjectSchema;
3535
import tech.ydb.yoj.repository.db.EntitySchema;
36+
import tech.ydb.yoj.repository.db.IsolationLevel;
3637
import tech.ydb.yoj.repository.db.Repository;
3738
import tech.ydb.yoj.repository.db.RepositoryTransaction;
3839
import tech.ydb.yoj.repository.db.Tx;
@@ -304,6 +305,30 @@ public void transactionLevel() {
304305
checkSession(sessionManager, firstSession);
305306
}
306307

308+
@Test
309+
public void snapshotTransactionLevel() {
310+
Project expected1 = new Project(new Project.Id("SP1"), "snapshot1");
311+
Project expected2 = new Project(new Project.Id("SP2"), "snapshot2");
312+
313+
db.tx(() -> db.projects().save(expected1));
314+
db.tx(() -> db.projects().save(expected2));
315+
316+
Project actual1 = db.tx(() -> db.projects().find(expected1.getId()));
317+
assertThat(actual1).isEqualTo(expected1);
318+
Project actual2 = db.readOnly().run(() -> db.projects().find(expected2.getId()));
319+
assertThat(actual2).isEqualTo(expected2);
320+
321+
db.readOnly()
322+
.withStatementIsolationLevel(IsolationLevel.SNAPSHOT)
323+
.run(() -> {
324+
Project actualSnapshot1 = db.projects().find(expected1.getId());
325+
assertThat(actualSnapshot1).isEqualTo(expected1);
326+
327+
Project actualSnapshot2 = db.projects().find(expected2.getId());
328+
assertThat(actualSnapshot2).isEqualTo(expected2);
329+
});
330+
}
331+
307332
@SneakyThrows
308333
@Test
309334
public void truncated() {

repository/src/main/java/tech/ydb/yoj/repository/db/IsolationLevel.java

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -32,7 +32,14 @@ public enum IsolationLevel {
3232
* An <em>almost</em> recent consistent state of the database. Read only.
3333
* This level is faster then {@code ONLINE_CONSISTENT_READ_ONLY}, but may return stale data.
3434
*/
35-
STALE_CONSISTENT_READ_ONLY("SC");
35+
STALE_CONSISTENT_READ_ONLY("SC"),
36+
37+
/**
38+
* All the read operations within a transaction access the database snapshot. Read only.
39+
* All the data reads are consistent. The snapshot is taken when the transaction begins,
40+
* meaning the transaction sees all changes committed before it began.
41+
*/
42+
SNAPSHOT("SP");
3643

3744
@Getter
3845
private final String txIdSuffix;

0 commit comments

Comments
 (0)