rocksdb/transactions/options.rs
1// Copyright 2021 Yiyuan Liu
2//
3// Licensed under the Apache License, Version 2.0 (the "License");
4// you may not use this file except in compliance with the License.
5// You may obtain a copy of the License at
6//
7// http://www.apache.org/licenses/LICENSE-2.0
8//
9// Unless required by applicable law or agreed to in writing, software
10// distributed under the License is distributed on an "AS IS" BASIS,
11// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12// See the License for the specific language governing permissions and
13// limitations under the License.
14//
15
16use crate::ffi;
17
18pub struct TransactionOptions {
19 pub(crate) inner: *mut ffi::rocksdb_transaction_options_t,
20}
21
22unsafe impl Send for TransactionOptions {}
23unsafe impl Sync for TransactionOptions {}
24
25impl Default for TransactionOptions {
26 fn default() -> Self {
27 let txn_opts = unsafe { ffi::rocksdb_transaction_options_create() };
28 assert!(
29 !txn_opts.is_null(),
30 "Could not create RocksDB transaction options"
31 );
32 Self { inner: txn_opts }
33 }
34}
35
36impl TransactionOptions {
37 pub fn new() -> TransactionOptions {
38 TransactionOptions::default()
39 }
40
41 /// In pessimistic transaction, if this is true, then you can skip Prepare
42 /// before Commit, otherwise, you must Prepare before Commit.
43 ///
44 /// Default: true
45 ///
46 pub fn set_skip_prepare(&mut self, skip_prepare: bool) {
47 unsafe {
48 ffi::rocksdb_transaction_options_set_skip_prepare(self.inner, u8::from(skip_prepare));
49 }
50 }
51
52 /// Specifies use snapshot or not.
53 ///
54 /// Default: false.
55 ///
56 /// If a transaction has a snapshot set, the transaction will ensure that
57 /// any keys successfully written(or fetched via `get_for_update`) have not
58 /// been modified outside this transaction since the time the snapshot was
59 /// set.
60 /// If a snapshot has not been set, the transaction guarantees that keys have
61 /// not been modified since the time each key was first written (or fetched via
62 /// `get_for_update`).
63 ///
64 /// Using snapshot will provide stricter isolation guarantees at the
65 /// expense of potentially more transaction failures due to conflicts with
66 /// other writes.
67 ///
68 /// Calling `set_snapshot` will not affect the version of Data returned by `get`
69 /// methods.
70 pub fn set_snapshot(&mut self, snapshot: bool) {
71 unsafe {
72 ffi::rocksdb_transaction_options_set_set_snapshot(self.inner, u8::from(snapshot));
73 }
74 }
75
76 /// Specifies whether detect deadlock or not.
77 ///
78 /// Setting to true means that before acquiring locks, this transaction will
79 /// check if doing so will cause a deadlock. If so, it will return with
80 /// Status::Busy. The user should retry their transaction.
81 ///
82 /// Default: false.
83 pub fn set_deadlock_detect(&mut self, deadlock_detect: bool) {
84 unsafe {
85 ffi::rocksdb_transaction_options_set_deadlock_detect(
86 self.inner,
87 u8::from(deadlock_detect),
88 );
89 }
90 }
91
92 /// Specifies the wait timeout in milliseconds when a transaction attempts to lock a key.
93 ///
94 /// If 0, no waiting is done if a lock cannot instantly be acquired.
95 /// If negative, transaction lock timeout in `TransactionDBOptions` will be used.
96 ///
97 /// Default: -1.
98 pub fn set_lock_timeout(&mut self, lock_timeout: i64) {
99 unsafe {
100 ffi::rocksdb_transaction_options_set_lock_timeout(self.inner, lock_timeout);
101 }
102 }
103
104 /// Specifies expiration duration in milliseconds.
105 ///
106 /// If non-negative, transactions that last longer than this many milliseconds will fail to commit.
107 /// If not set, a forgotten transaction that is never committed, rolled back, or deleted
108 /// will never relinquish any locks it holds. This could prevent keys from being accessed by other writers.
109 ///
110 /// Default: -1.
111 pub fn set_expiration(&mut self, expiration: i64) {
112 unsafe {
113 ffi::rocksdb_transaction_options_set_expiration(self.inner, expiration);
114 }
115 }
116
117 /// Specifies the number of traversals to make during deadlock detection.
118 ///
119 /// Default: 50.
120 pub fn set_deadlock_detect_depth(&mut self, depth: i64) {
121 unsafe {
122 ffi::rocksdb_transaction_options_set_deadlock_detect_depth(self.inner, depth);
123 }
124 }
125
126 /// Specifies the maximum number of bytes used for the write batch. 0 means no limit.
127 ///
128 /// Default: 0.
129 pub fn set_max_write_batch_size(&mut self, size: usize) {
130 unsafe {
131 ffi::rocksdb_transaction_options_set_max_write_batch_size(self.inner, size);
132 }
133 }
134}
135
136impl Drop for TransactionOptions {
137 fn drop(&mut self) {
138 unsafe {
139 ffi::rocksdb_transaction_options_destroy(self.inner);
140 }
141 }
142}
143
144pub struct TransactionDBOptions {
145 pub(crate) inner: *mut ffi::rocksdb_transactiondb_options_t,
146}
147
148unsafe impl Send for TransactionDBOptions {}
149unsafe impl Sync for TransactionDBOptions {}
150
151impl Default for TransactionDBOptions {
152 fn default() -> Self {
153 let txn_db_opts = unsafe { ffi::rocksdb_transactiondb_options_create() };
154 assert!(
155 !txn_db_opts.is_null(),
156 "Could not create RocksDB transaction_db options"
157 );
158 Self { inner: txn_db_opts }
159 }
160}
161
162impl TransactionDBOptions {
163 pub fn new() -> TransactionDBOptions {
164 TransactionDBOptions::default()
165 }
166
167 /// Specifies the wait timeout in milliseconds when writing a key
168 /// outside a transaction (i.e. by calling `TransactionDB::put` directly).
169 ///
170 /// If 0, no waiting is done if a lock cannot instantly be acquired.
171 /// If negative, there is no timeout and will block indefinitely when acquiring
172 /// a lock.
173 ///
174 /// Not using a timeout can lead to deadlocks. Currently, there
175 /// is no deadlock-detection to recover from a deadlock. While DB writes
176 /// cannot deadlock with other DB writes, they can deadlock with a transaction.
177 /// A negative timeout should only be used if all transactions have a small
178 /// expiration set.
179 ///
180 /// Default: 1000(1s).
181 pub fn set_default_lock_timeout(&mut self, default_lock_timeout: i64) {
182 unsafe {
183 ffi::rocksdb_transactiondb_options_set_default_lock_timeout(
184 self.inner,
185 default_lock_timeout,
186 );
187 }
188 }
189
190 /// Specifies the default wait timeout in milliseconds when a transaction
191 /// attempts to lock a key if not specified in `TransactionOptions`.
192 ///
193 /// If 0, no waiting is done if a lock cannot instantly be acquired.
194 /// If negative, there is no timeout. Not using a timeout is not recommended
195 /// as it can lead to deadlocks. Currently, there is no deadlock-detection to
196 /// recover from a deadlock.
197 ///
198 /// Default: 1000(1s).
199 pub fn set_txn_lock_timeout(&mut self, txn_lock_timeout: i64) {
200 unsafe {
201 ffi::rocksdb_transactiondb_options_set_transaction_lock_timeout(
202 self.inner,
203 txn_lock_timeout,
204 );
205 }
206 }
207
208 /// Specifies the maximum number of keys that can be locked at the same time
209 /// per column family.
210 ///
211 /// If the number of locked keys is greater than `max_num_locks`, transaction
212 /// `writes` (or `get_for_update`) will return an error.
213 /// If this value is not positive, no limit will be enforced.
214 ///
215 /// Default: -1.
216 pub fn set_max_num_locks(&mut self, max_num_locks: i64) {
217 unsafe {
218 ffi::rocksdb_transactiondb_options_set_max_num_locks(self.inner, max_num_locks);
219 }
220 }
221
222 /// Specifies lock table stripes count.
223 ///
224 /// Increasing this value will increase the concurrency by dividing the lock
225 /// table (per column family) into more sub-tables, each with their own
226 /// separate mutex.
227 ///
228 /// Default: 16.
229 pub fn set_num_stripes(&mut self, num_stripes: usize) {
230 unsafe {
231 ffi::rocksdb_transactiondb_options_set_num_stripes(self.inner, num_stripes);
232 }
233 }
234}
235
236impl Drop for TransactionDBOptions {
237 fn drop(&mut self) {
238 unsafe {
239 ffi::rocksdb_transactiondb_options_destroy(self.inner);
240 }
241 }
242}
243
244pub struct OptimisticTransactionOptions {
245 pub(crate) inner: *mut ffi::rocksdb_optimistictransaction_options_t,
246}
247
248unsafe impl Send for OptimisticTransactionOptions {}
249unsafe impl Sync for OptimisticTransactionOptions {}
250
251impl Default for OptimisticTransactionOptions {
252 fn default() -> Self {
253 let txn_opts = unsafe { ffi::rocksdb_optimistictransaction_options_create() };
254 assert!(
255 !txn_opts.is_null(),
256 "Could not create RocksDB optimistic transaction options"
257 );
258 Self { inner: txn_opts }
259 }
260}
261
262impl OptimisticTransactionOptions {
263 pub fn new() -> OptimisticTransactionOptions {
264 OptimisticTransactionOptions::default()
265 }
266
267 /// Specifies use snapshot or not.
268 ///
269 /// Default: false.
270 ///
271 /// If a transaction has a snapshot set, the transaction will ensure that
272 /// any keys successfully written(or fetched via `get_for_update`) have not
273 /// been modified outside the transaction since the time the snapshot was
274 /// set.
275 /// If a snapshot has not been set, the transaction guarantees that keys have
276 /// not been modified since the time each key was first written (or fetched via
277 /// `get_for_update`).
278 ///
279 /// Using snapshot will provide stricter isolation guarantees at the
280 /// expense of potentially more transaction failures due to conflicts with
281 /// other writes.
282 ///
283 /// Calling `set_snapshot` will not affect the version of Data returned by `get`
284 /// methods.
285 pub fn set_snapshot(&mut self, snapshot: bool) {
286 unsafe {
287 ffi::rocksdb_optimistictransaction_options_set_set_snapshot(
288 self.inner,
289 u8::from(snapshot),
290 );
291 }
292 }
293}
294
295impl Drop for OptimisticTransactionOptions {
296 fn drop(&mut self) {
297 unsafe {
298 ffi::rocksdb_optimistictransaction_options_destroy(self.inner);
299 }
300 }
301}