]> git.proxmox.com Git - ceph.git/blob - ceph/src/rocksdb/java/samples/src/main/java/OptimisticTransactionSample.java
update sources to ceph Nautilus 14.2.1
[ceph.git] / ceph / src / rocksdb / java / samples / src / main / java / OptimisticTransactionSample.java
1 // Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
2 // This source code is licensed under both the GPLv2 (found in the
3 // COPYING file in the root directory) and Apache 2.0 License
4 // (found in the LICENSE.Apache file in the root directory).
5
6 import org.rocksdb.*;
7
8 import static java.nio.charset.StandardCharsets.UTF_8;
9
10 /**
11 * Demonstrates using Transactions on an OptimisticTransactionDB with
12 * varying isolation guarantees
13 */
14 public class OptimisticTransactionSample {
15 private static final String dbPath = "/tmp/rocksdb_optimistic_transaction_example";
16
17 public static final void main(final String args[]) throws RocksDBException {
18
19 try(final Options options = new Options()
20 .setCreateIfMissing(true);
21 final OptimisticTransactionDB txnDb =
22 OptimisticTransactionDB.open(options, dbPath)) {
23
24 try (final WriteOptions writeOptions = new WriteOptions();
25 final ReadOptions readOptions = new ReadOptions()) {
26
27 ////////////////////////////////////////////////////////
28 //
29 // Simple OptimisticTransaction Example ("Read Committed")
30 //
31 ////////////////////////////////////////////////////////
32 readCommitted(txnDb, writeOptions, readOptions);
33
34
35 ////////////////////////////////////////////////////////
36 //
37 // "Repeatable Read" (Snapshot Isolation) Example
38 // -- Using a single Snapshot
39 //
40 ////////////////////////////////////////////////////////
41 repeatableRead(txnDb, writeOptions, readOptions);
42
43
44 ////////////////////////////////////////////////////////
45 //
46 // "Read Committed" (Monotonic Atomic Views) Example
47 // --Using multiple Snapshots
48 //
49 ////////////////////////////////////////////////////////
50 readCommitted_monotonicAtomicViews(txnDb, writeOptions, readOptions);
51 }
52 }
53 }
54
55 /**
56 * Demonstrates "Read Committed" isolation
57 */
58 private static void readCommitted(final OptimisticTransactionDB txnDb,
59 final WriteOptions writeOptions, final ReadOptions readOptions)
60 throws RocksDBException {
61 final byte key1[] = "abc".getBytes(UTF_8);
62 final byte value1[] = "def".getBytes(UTF_8);
63
64 final byte key2[] = "xyz".getBytes(UTF_8);
65 final byte value2[] = "zzz".getBytes(UTF_8);
66
67 // Start a transaction
68 try(final Transaction txn = txnDb.beginTransaction(writeOptions)) {
69 // Read a key in this transaction
70 byte[] value = txn.get(readOptions, key1);
71 assert(value == null);
72
73 // Write a key in this transaction
74 txn.put(key1, value1);
75
76 // Read a key OUTSIDE this transaction. Does not affect txn.
77 value = txnDb.get(readOptions, key1);
78 assert(value == null);
79
80 // Write a key OUTSIDE of this transaction.
81 // Does not affect txn since this is an unrelated key.
82 // If we wrote key 'abc' here, the transaction would fail to commit.
83 txnDb.put(writeOptions, key2, value2);
84
85 // Commit transaction
86 txn.commit();
87 }
88 }
89
90 /**
91 * Demonstrates "Repeatable Read" (Snapshot Isolation) isolation
92 */
93 private static void repeatableRead(final OptimisticTransactionDB txnDb,
94 final WriteOptions writeOptions, final ReadOptions readOptions)
95 throws RocksDBException {
96
97 final byte key1[] = "ghi".getBytes(UTF_8);
98 final byte value1[] = "jkl".getBytes(UTF_8);
99
100 // Set a snapshot at start of transaction by setting setSnapshot(true)
101 try(final OptimisticTransactionOptions txnOptions =
102 new OptimisticTransactionOptions().setSetSnapshot(true);
103 final Transaction txn =
104 txnDb.beginTransaction(writeOptions, txnOptions)) {
105
106 final Snapshot snapshot = txn.getSnapshot();
107
108 // Write a key OUTSIDE of transaction
109 txnDb.put(writeOptions, key1, value1);
110
111 // Read a key using the snapshot.
112 readOptions.setSnapshot(snapshot);
113 final byte[] value = txn.getForUpdate(readOptions, key1, true);
114 assert(value == value1);
115
116 try {
117 // Attempt to commit transaction
118 txn.commit();
119 throw new IllegalStateException();
120 } catch(final RocksDBException e) {
121 // Transaction could not commit since the write outside of the txn
122 // conflicted with the read!
123 assert(e.getStatus().getCode() == Status.Code.Busy);
124 }
125
126 txn.rollback();
127 } finally {
128 // Clear snapshot from read options since it is no longer valid
129 readOptions.setSnapshot(null);
130 }
131 }
132
133 /**
134 * Demonstrates "Read Committed" (Monotonic Atomic Views) isolation
135 *
136 * In this example, we set the snapshot multiple times. This is probably
137 * only necessary if you have very strict isolation requirements to
138 * implement.
139 */
140 private static void readCommitted_monotonicAtomicViews(
141 final OptimisticTransactionDB txnDb, final WriteOptions writeOptions,
142 final ReadOptions readOptions) throws RocksDBException {
143
144 final byte keyX[] = "x".getBytes(UTF_8);
145 final byte valueX[] = "x".getBytes(UTF_8);
146
147 final byte keyY[] = "y".getBytes(UTF_8);
148 final byte valueY[] = "y".getBytes(UTF_8);
149
150 try (final OptimisticTransactionOptions txnOptions =
151 new OptimisticTransactionOptions().setSetSnapshot(true);
152 final Transaction txn =
153 txnDb.beginTransaction(writeOptions, txnOptions)) {
154
155 // Do some reads and writes to key "x"
156 Snapshot snapshot = txnDb.getSnapshot();
157 readOptions.setSnapshot(snapshot);
158 byte[] value = txn.get(readOptions, keyX);
159 txn.put(valueX, valueX);
160
161 // Do a write outside of the transaction to key "y"
162 txnDb.put(writeOptions, keyY, valueY);
163
164 // Set a new snapshot in the transaction
165 txn.setSnapshot();
166 snapshot = txnDb.getSnapshot();
167 readOptions.setSnapshot(snapshot);
168
169 // Do some reads and writes to key "y"
170 // Since the snapshot was advanced, the write done outside of the
171 // transaction does not conflict.
172 value = txn.getForUpdate(readOptions, keyY, true);
173 txn.put(keyY, valueY);
174
175 // Commit. Since the snapshot was advanced, the write done outside of the
176 // transaction does not prevent this transaction from Committing.
177 txn.commit();
178
179 } finally {
180 // Clear snapshot from read options since it is no longer valid
181 readOptions.setSnapshot(null);
182 }
183 }
184 }