-
Notifications
You must be signed in to change notification settings - Fork 110
/
EnvironmentConfig.java
2948 lines (2710 loc) · 122 KB
/
EnvironmentConfig.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
654
655
656
657
658
659
660
661
662
663
664
665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
785
786
787
788
789
790
791
792
793
794
795
796
797
798
799
800
801
802
803
804
805
806
807
808
809
810
811
812
813
814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
864
865
866
867
868
869
870
871
872
873
874
875
876
877
878
879
880
881
882
883
884
885
886
887
888
889
890
891
892
893
894
895
896
897
898
899
900
901
902
903
904
905
906
907
908
909
910
911
912
913
914
915
916
917
918
919
920
921
922
923
924
925
926
927
928
929
930
931
932
933
934
935
936
937
938
939
940
941
942
943
944
945
946
947
948
949
950
951
952
953
954
955
956
957
958
959
960
961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
979
980
981
982
983
984
985
986
987
988
989
990
991
992
993
994
995
996
997
998
999
1000
/*
* Copyright ${inceptionYear} - ${year} ${owner}
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* https://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package jetbrains.exodus.env;
import jetbrains.exodus.*;
import jetbrains.exodus.core.dataStructures.Pair;
import jetbrains.exodus.crypto.KryptKt;
import jetbrains.exodus.crypto.StreamCipher;
import jetbrains.exodus.crypto.StreamCipherProvider;
import jetbrains.exodus.entitystore.MetaServer;
import jetbrains.exodus.io.DataReader;
import jetbrains.exodus.io.DataReaderWriterProvider;
import jetbrains.exodus.io.DataWriter;
import jetbrains.exodus.io.StorageTypeNotAllowedException;
import jetbrains.exodus.system.JVMConstants;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.Map;
import java.util.concurrent.TimeUnit;
/**
* Specifies settings of {@linkplain Environment}. Default settings are specified by
* {@linkplain #DEFAULT} which is immutable. Any newly created {@code EnvironmentConfig} has the
* same settings as {@linkplain #DEFAULT}.
*
* <p>As a rule, the {@code EnvironmentConfig} instance is created along with the
* {@linkplain Environment} one.
* E.g., creation of {@linkplain Environment} with some tuned garbage collector settings can look as
* follows:
* <pre>
* final EnvironmentConfig config = new EnvironmentConfig();
* final Environment env = Environments.newInstance(""dbDirectory", config.setGcFileMinAge(3).setGcRunPeriod(60000));
* </pre>
* <p>
* Some setting are mutable at runtime and some are immutable. Immutable at runtime settings can be
* changed, but they won't take effect on the {@linkplain Environment} instance. Those settings are
* applicable only during {@linkplain Environment} instance creation.
*
* <p>Some settings can be changed only before the database is physically created on storage device.
* E.g.,
* {@linkplain #LOG_FILE_SIZE} defines the size of a single {@code Log} file (.xd file) which cannot
* be changed for existing databases. It makes sense to choose values of such settings at design
* time and hardcode them.
*
* <p>You can define custom processing of changed settings values by
* {@linkplain #addChangedSettingsListener(ConfigSettingChangeListener)}. Override
* {@linkplain ConfigSettingChangeListener#beforeSettingChanged(String, Object, Map)} to pre-process
* mutations of settings and
* {@linkplain ConfigSettingChangeListener#afterSettingChanged(String, Object, Map)} to post-process
* them.
*
* @see Environment
* @see Environment#getEnvironmentConfig()
*/
@SuppressWarnings({"WeakerAccess", "unused", "AutoBoxing", "AutoUnboxing"})
public class EnvironmentConfig extends AbstractConfig {
public static final EnvironmentConfig DEFAULT = new EnvironmentConfig(
ConfigurationStrategy.IGNORE) {
@Override
public EnvironmentConfig setMutable(boolean isMutable) {
if (!this.isMutable() && isMutable) {
throw new ExodusException("Can't make EnvironmentConfig.DEFAULT mutable");
}
return super.setMutable(isMutable);
}
}.setMutable(false);
/**
* Defines absolute value of memory in bytes that can be used by the LogCache. By default, is not
* set.
* <p>Mutable at runtime: no
*
* @see #MEMORY_USAGE_PERCENTAGE
*/
public static final String MEMORY_USAGE = "exodus.memoryUsage";
/**
* Defines percent of max memory (specified by the "-Xmx" java parameter) that can be used by the
* LogCache. Is applicable only if {@linkplain #MEMORY_USAGE} is not set. Default value is
* {@code 50}.
* <p>Mutable at runtime: no
*
* @see #MEMORY_USAGE
*/
public static final String MEMORY_USAGE_PERCENTAGE = "exodus.memoryUsagePercentage";
public static final String USE_VERSION1_FORMAT = "exodus.useVersion1Format";
/**
* Xodus performs check of consistency of pages loaded from disk. This option allows to
* enable/disable this check.
* <p>
* Disabling this check should improve general performance of database but decreases durability
* guaranties.
* <p>
* Default value is {@code true}.
*
* <p>Mutable at runtime: no</p>
*/
public static final String CHECK_PAGES_AT_RUNTIME = "exodus.checkPagesAtRuntime";
/**
* Defines id of {@linkplain StreamCipherProvider} which will be used to encrypt the database.
* Default value is {@code null}, which means that the database won't be encrypted. The setting
* cannot be changed for existing databases. Default value is {@code null}.
* <p>Mutable at runtime: no
*
* @see #CIPHER_KEY
* @see #CIPHER_BASIC_IV
* @see StreamCipher
* @see StreamCipherProvider
*/
public static final String CIPHER_ID = "exodus.cipherId";
/**
* Defines the key which will be used to encrypt the database. The key is expected to be a hex
* string representing a byte array which is passed to
* {@linkplain StreamCipher#init(byte[], long)}. Is applicable only if {@linkplain #CIPHER_ID} is
* not {@code null}. The setting cannot be changed for existing databases. Default value is
* {@code null}.
* <p>Mutable at runtime: no
*
* @see #CIPHER_ID
* @see #CIPHER_BASIC_IV
* @see StreamCipher
* @see StreamCipher#init(byte[], long)
* @see StreamCipherProvider
*/
public static final String CIPHER_KEY = "exodus.cipherKey";
/**
* Defines basic IV (initialization vector) which will be used to encrypt the database. Basic IV
* is expected to be random (pseudo-random) and unique long value. Basic IV is used to calculate
* relative IVs which are passed to {@linkplain StreamCipher#init(byte[], long)}. Is applicable
* only if {@linkplain #CIPHER_ID} is not {@code null}. The setting cannot be changed for existing
* databases. Default value is {@code 0L}.
* <p>Mutable at runtime: no
*
* @see #CIPHER_ID
* @see #CIPHER_KEY
* @see StreamCipher
* @see StreamCipher#init(byte[], long)
* @see StreamCipherProvider
*/
public static final String CIPHER_BASIC_IV = "exodus.cipherBasicIV";
/**
* If is set to {@code true} database profiler is enabled. By default, it is disabled.
* <p>Mutable at runtime: no
*
* @since 1.4.0
*/
public static final String PROFILER_ENABLED = "exodus.profiler.enabled";
/**
* If is set to {@code true} forces file system's fsync call after each committed or flushed
* transaction. By default, is switched off since it creates great performance overhead and can be
* controlled manually.
* <p>Mutable at runtime: yes
*/
public static final String LOG_DURABLE_WRITE = "exodus.log.durableWrite";
/**
* Defines the maximum size in kilobytes of a single {@code Log} file (.xd file). The setting
* cannot be changed for existing databases. Default value is {@code 8192L}.
* <p>Mutable at runtime: no
*/
public static final String LOG_FILE_SIZE = "exodus.log.fileSize";
/**
* Defines the number of milliseconds the Log constructor waits for the lock file. Default value
* is {@code 0L}.
* <p>Mutable at runtime: no
*/
public static final String LOG_LOCK_TIMEOUT = "exodus.log.lockTimeout";
/**
* Defines the debug identifier to be written to the lock file alongside with other debug
* information. Default value is {@code ManagementFactory.getRuntimeMXBean().getName()} which has
* a form of {@code pid@hostname}.
* <p>Mutable at runtime: no
*/
public static final String LOG_LOCK_ID = "exodus.log.lockID";
/**
* Defines the size in bytes of a single page (byte array) in the LogCache. This number of bytes
* is read from {@linkplain java.nio.MappedByteBuffer} or {@linkplain java.io.RandomAccessFile} at
* a time.
*
* <p>If the LogCache is shared ({@linkplain #LOG_CACHE_SHARED}) all {@linkplain Environment}s
* should be configured
* to use single LogCache page size.
*
* <p>Default value is {@code 64 * 1024}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_PAGE_SIZE = "exodus.log.cache.pageSize";
/**
* Defines the maximum number of open files that LogCache maintains in order to reduce system
* calls to open and close files. The more open files is allowed the less system calls are
* performed in addition to reading or mapping files. This value can notably affect performance of
* database warm-up. Default value is {@code 500}. Open files cache is shared amongst all open
* {@linkplain Environment environments}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_OPEN_FILES = "exodus.log.cache.openFilesCount";
/**
* If is set to {@code true} any immutable file can be mapped in memory provided there is enough
* physical memory. On cache miss, LogCache at first tries to check if there is corresponding
* mapped byte buffer and copies cache page from the buffer, otherwise reads the page from
* {@linkplain java.io.RandomAccessFile}. If is set to {@code false} then LogCache always reads
* {@linkplain java.io.RandomAccessFile} on cache miss. Default value was {@code true} before
* version {@code 1.2.3}. As of {@code 1.2.3}, default value is {@code false}.
*
* <p>Mutable at runtime: no
*
* @see #LOG_CACHE_FREE_PHYSICAL_MEMORY_THRESHOLD
* @deprecated Because of upcoming release of virtual threads feature this property is deprecated.
*/
@SuppressWarnings("DeprecatedIsStillUsed")
@Deprecated
public static final String LOG_CACHE_USE_NIO = "exodus.log.cache.useNIO";
/**
* If {@linkplain #LOG_CACHE_USE_NIO} is {@code true} defines the minimum size in bytes of free
* physical memory maintained by the cache memory-mapped files on the host where the JVM runs. On
* cache miss, LogCache checks if corresponding file is mapped in memory, and if it is not and if
* free physical memory amount is greater than threshold specified by this setting, tries to map
* the file in memory. Default value is {@code 1_000_000_000L} bytes, i.e. ~1GB.
* <p>Mutable at runtime: no
*
* @see #LOG_CACHE_USE_NIO
* @deprecated Because of upcoming release of virtual threads feature this property is deprecated.
*/
@SuppressWarnings("DeprecatedIsStillUsed")
@Deprecated
public static final String LOG_CACHE_FREE_PHYSICAL_MEMORY_THRESHOLD = "exodus.log.cache.freePhysicalMemoryThreshold";
/**
* If is set to {@code true} the LogCache is shared. Shared cache caches raw binary data (contents
* of .xd files) of all {@linkplain Environment} instances created in scope of this class loader.
* By default, the LogCache is shared.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_SHARED = "exodus.log.cache.shared";
/**
* If is set to {@code true} the LogCache uses lock-free data structures. Default value is
* {@code true}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_NON_BLOCKING = "exodus.log.cache.nonBlocking";
/**
* Defines the number of generations of non-blocking LogCache. Is applicable only if
* {@linkplain #LOG_CACHE_NON_BLOCKING} is set to {@code true}. The higher number of generations
* is, the higher the cache hit rate is and CPU ticks necessary to get a single page from the
* cache. Default value is {@code 2}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_GENERATION_COUNT = "exodus.log.cache.generationCount";
/**
* If is set to {@code true} LogCache uses
* {@linkplain java.lang.ref.SoftReference soft references} for holding cached pages. The cache
* still uses not more memory than it is configured by {@linkplain #MEMORY_USAGE} or
* {@linkplain #MEMORY_USAGE_PERCENTAGE} settings, but JVM GC can reclaim memory used by the cache
* on a heavy load surge. On the other hand, use of soft references results in greater JVM GC load
* and greater general CPU consumption by the cache. So one can choose either memory-flexible, or
* CPU-optimal cache. Default value is {@code false}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_USE_SOFT_REFERENCES = "exodus.log.cache.useSoftReferences";
/**
* Defines the number of successive pages to be read at once in case of LogCache miss. Reading
* successive pages can reduce amount of random access to database files. It can be useful in
* workloads like application warm-up. Default value is {@code 1} which means that no read-ahead
* strategy is applied.
* <p>Mutable at runtime: yes
*/
public static final String LOG_CACHE_READ_AHEAD_MULTIPLE = "exodus.log.cache.readAheadMultiple";
/**
* If is set to {@code true} LogCache will populate itself with database file pages right after
* the database is opened using this {@code EnvironmentConfig} instance. Default value is
* {@code false}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CACHE_WARMUP = "exodus.log.cache.warmup";
/**
* If is set to {@code true} then the Log constructor fails if the database directory is not
* clean. Can be useful if an applications expects that the database should always be newly
* created. Default value is {@code false}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CLEAN_DIRECTORY_EXPECTED = "exodus.log.cleanDirectoryExpected";
/**
* If is set to {@code true} then the Log constructor implicitly clears the database if it
* occurred to be invalid when opened. Default value is {@code false}.
* <p>Mutable at runtime: no
*/
public static final String LOG_CLEAR_INVALID = "exodus.log.clearInvalid";
public static final String LOG_SKIP_INVALID_LOGGALE_TYPE = "exodus.log.skipInvalidLoggableType";
/**
* Sets the period in milliseconds to force file system's fsync call that often if
* {@linkplain #LOG_DURABLE_WRITE} is switched off. Default value is {@code 10000L}.
* <p>Mutable at runtime: yes
*
* @see #LOG_DURABLE_WRITE
*/
public static final String LOG_SYNC_PERIOD = "exodus.log.syncPeriod";
/**
* Forces to check data consistency of the database on opening. Default value is {@code false}.
*
* <p>Mutable at runtime: no
*/
public static final String LOG_FORCE_CHECK_DATA_CONSISTENCY = "exodus.log.forceCheckDataConsistency";
/**
* Forces data restore routine to proceed even if it is not possible to restore all the data.
* Default value is {@code false}.
*
* <p>Mutable at runtime: no
*/
public static final String LOG_PROCEED_DATA_RESTORE_AT_ANY_COST = "exodus.log.proceedDataRestoreAtAnyCost";
/**
* If is set to {@code true} then each complete and immutable {@code Log} file (.xd file) is
* marked with read-only attribute. Default value is {@code true}.
* <p>Mutable at runtime: no
*/
public static final String LOG_FULL_FILE_READ_ONLY = "exodus.log.fullFileReadonly";
/**
* For {@linkplain DataReaderWriterProvider#DEFAULT_READER_WRITER_PROVIDER} used as
* {@linkplain DataReaderWriterProvider} service provider interface implementation, if is set to
* {@code true} then the database can be opened on a removable storage. Attempt to open database
* on a storage of not allowed type results in {@linkplain StorageTypeNotAllowedException}.
* Default value is {@code false}.
* <p>Mutable at runtime: no
*
* @since 1.4.0
*/
public static final String LOG_ALLOW_REMOVABLE = "exodus.log.allowRemovable";
/**
* For {@linkplain DataReaderWriterProvider#DEFAULT_READER_WRITER_PROVIDER} used as
* {@linkplain DataReaderWriterProvider} service provider interface implementation, if is set to
* {@code true} then the database can be opened on a remote storage. Attempt to open database on a
* storage of not allowed type results in {@linkplain StorageTypeNotAllowedException}. Default
* value is {@code false}.
* <p>Mutable at runtime: no
*
* @since 1.4.0
*/
public static final String LOG_ALLOW_REMOTE = "exodus.log.allowRemote";
/**
* For {@linkplain DataReaderWriterProvider#DEFAULT_READER_WRITER_PROVIDER} used as
* {@linkplain DataReaderWriterProvider} service provider interface implementation, if is set to
* {@code true} then the database can be opened on RAM-disk. Attempt to open database on a storage
* of not allowed type results in {@linkplain StorageTypeNotAllowedException}. Default value is
* {@code false}.
* <p>Mutable at runtime: no
*
* @since 1.4.0
*/
public static final String LOG_ALLOW_RAM_DISK = "exodus.log.allowRamDisk";
/**
* Defines fully-qualified name of the {@linkplain DataReaderWriterProvider} service provider
* interface implementation which will be used to create {@linkplain DataReader} and
* {@linkplain DataWriter} instances. This setting can be used to customize storageL define
* in-memory one, in-cloud, etc. Default value is
* {@linkplain DataReaderWriterProvider#DEFAULT_READER_WRITER_PROVIDER} which means that file
* system must be used as a storage. Several settings are applicable only to
* FileDataReaderWriterProvider used: {@linkplain #LOG_DURABLE_WRITE},
* {@linkplain #LOG_SYNC_PERIOD}, {@linkplain #LOG_CACHE_OPEN_FILES},
* {@linkplain #LOG_FULL_FILE_READ_ONLY}, {@linkplain #LOG_CACHE_USE_NIO},
* {@linkplain #LOG_CACHE_FREE_PHYSICAL_MEMORY_THRESHOLD}.
* <p>Mutable at runtime: no
*/
public static final String LOG_DATA_READER_WRITER_PROVIDER = "exodus.log.readerWriterProvider";
/**
* If is set to {@code true} then the {@linkplain Environment} instance is read-only. Default
* value is {@code false}.
* <p>Mutable at runtime: yes
*/
public static final String ENV_IS_READONLY = "exodus.env.isReadonly";
/**
* If is set to {@code true} and {@linkplain #ENV_IS_READONLY} is also {@code true} then the
* {@linkplain Environment} obligatorily creates transactions for which
* {@linkplain Transaction#isReadonly()} is {@code true}. Read-only transactions fail-fast with
* {@linkplain ReadonlyTransactionException} on attempt to modify data. If is set to {@code false}
* and {@linkplain #ENV_IS_READONLY} is set to {@code true} then the {@linkplain Environment}
* creates transaction that allow to accumulate changes but cannot be flushed ot committed since
* the {@linkplain Environment} is read-only. Default value is {@code true}.
* <p>Mutable at runtime: yes
*
* @see #ENV_IS_READONLY
*/
public static final String ENV_FAIL_FAST_IN_READONLY = "exodus.env.failFastInReadonly";
/**
* If is set to {@code true} and {@linkplain #ENV_IS_READONLY} is also {@code true} then
* {@linkplain Environment#openStore(String, StoreConfig, Transaction)} doesn't try to create a
* {@linkplain Store}, but returns an empty immutable instance instead. Default value is
* {@code false}.
* <p>Mutable at runtime: yes
*
* @see #ENV_IS_READONLY
*/
public static final String ENV_READONLY_EMPTY_STORES = "exodus.env.readonly.emptyStores";
/**
* Defines the size of the "store-get" cache. The "store-get" cache can increase performance of
* {@linkplain Store#get(Transaction, ByteIterable)} in certain cases. Default value is {@code 0}
* what means that the cache is inactive. If the setting is mutated at runtime the cache is
* invalidated.
* <p>Mutable at runtime: yes
*/
public static final String ENV_STOREGET_CACHE_SIZE = "exodus.env.storeGetCacheSize";
// TODO: document
public static final String ENV_STOREGET_CACHE_MIN_TREE_SIZE = "exodus.env.storeGetCache.minTreeSize";
// TODO: document
public static final String ENV_STOREGET_CACHE_MAX_VALUE_SIZE = "exodus.env.storeGetCache.maxValueSize";
/**
* If is set to {@code true} then {@linkplain Environment#close()} doest't check if there are
* unfinished transactions. Otherwise it checks and throws {@linkplain ExodusException} if there
* are. Default value is {@code false}.
* <p>Mutable at runtime: yes
*
* @see Environment#close()
*/
public static final String ENV_CLOSE_FORCEDLY = "exodus.env.closeForcedly";
/**
* If is set to {@code true} then {@linkplain Environment} performs check of consistency of
* datastructures stored in backup files. Default value is {@code false}. Mutable at runtime: no
*/
public static final String ENV_CHECK_BACKUP_CONSISTENCY = "exodus.env.checkBackupConsistency";
/**
* List of stores to remove before compaction is started on environment.
*/
public static final String ENV_STORES_TO_REMOVE_BEFORE_COMPACTION = "exodus.env.storesToRemoveBeforeCompaction";
public static final String ENV_CHECK_DATA_STRUCTURES_CONSISTENCY = "exodus.env.checkDataStructuresConsistency";
/**
* Defines the number of millisecond which a {@linkplain Transaction} can try to flush without
* attempts to upgrade (switch to an exclusive mode). Default value is {@code 2000L}.
* <p>Mutable at runtime: yes
*
* @see Transaction
* @see #ENV_TXN_REPLAY_MAX_COUNT
* @see #ENV_TXN_DOWNGRADE_AFTER_FLUSH
*/
public static final String ENV_TXN_REPLAY_TIMEOUT = "exodus.env.txn.replayTimeout";
/**
* Defines the number of times which a {@linkplain Transaction} can try to flush without attempts
* to upgrade (switch to an exclusive mode). Default value is {@code 2}.
* <p>Mutable at runtime: yes
*
* @see Transaction
* @see #ENV_TXN_REPLAY_TIMEOUT
* @see #ENV_TXN_DOWNGRADE_AFTER_FLUSH
*/
public static final String ENV_TXN_REPLAY_MAX_COUNT = "exodus.env.txn.replayMaxCount";
/**
* If is set to {@code true} then any upgraded {@linkplain Transaction} will downgrade itself
* after {@linkplain Transaction#flush()}. Default value is {@code true}.
* <p>Mutable at runtime: yes
*
* @see Transaction
* @see #ENV_TXN_REPLAY_TIMEOUT
* @see #ENV_TXN_REPLAY_MAX_COUNT
*/
public static final String ENV_TXN_DOWNGRADE_AFTER_FLUSH = "exodus.env.txn.downgradeAfterFlush";
/**
* If is set to {@code true} then any write operation can be performed only in the thread which
* the transaction was created in. Default value is {@code false}.
* <p>Mutable at runtime: yes
*
* @see Transaction
*/
public static final String ENV_TXN_SINGLE_THREAD_WRITES = "exodus.env.txn.singleThreadWrites";
/**
* If is set to {@code true} then each transaction, read/write or read-only, saves stack trace
* when it is finished (aborted or committed). The stack trace is then reported with
* {@code TransactionFinishedException}. Default value is {@code false}.
* <p>Mutable at runtime: yes
*
* @see Transaction
* @since 1.4.0
*/
public static final String ENV_TXN_TRACE_FINISH = "exodus.env.txn.traceFinish";
/**
* Defines the number of {@linkplain Transaction transactions} that can be started in parallel. It
* is unlimited by default.
* <p>Mutable at runtime: no
*
* @see Transaction
*/
public static final String ENV_MAX_PARALLEL_TXNS = "exodus.env.maxParallelTxns";
/**
* Defines the number of read-only {@linkplain Transaction transactions} that can be started in
* parallel. By default it is unlimited.
* <p>Mutable at runtime: no
* <p>
* As of 1.4.0, is deprecated.
*
* @see Transaction
* @see Transaction#isReadonly()
* @see #ENV_MAX_PARALLEL_TXNS
*/
@Deprecated
public static final String ENV_MAX_PARALLEL_READONLY_TXNS = "exodus.env.maxParallelReadonlyTxns";
/**
* Defines {@linkplain Transaction} timeout in milliseconds. If transaction doesn't finish in this
* timeout then it is reported in logs as stuck along with stack trace which it was created with.
* Default value is {@code 0} which means that no timeout for a {@linkplain Transaction} is
* defined. In that case, no monitor of stuck transactions is started. Otherwise it is started for
* each {@linkplain Environment}, though consuming only a single {@linkplain Thread} amongst all
* environments created within a single class loader.
* <p>Mutable at runtime: no
*
* @see Transaction
* @see #ENV_MONITOR_TXNS_CHECK_FREQ
*/
public static final String ENV_MONITOR_TXNS_TIMEOUT = "exodus.env.monitorTxns.timeout";
/**
* Defines {@linkplain Transaction} expiration timeout in milliseconds. If transaction doesn't
* finish in this timeout then it is forced to be finished. Default value is {@code 8} hours.
* {@code 0} value means that no expiration for a {@linkplain Transaction} is defined. In that
* case, no monitor of stuck transactions is started. Otherwise it is started for each
* {@linkplain Environment}, though consuming only a single {@linkplain Thread} amongst all
* environments created within a single class loader.
* <p>Mutable at runtime: no
*
* @see Transaction
* @see #ENV_MONITOR_TXNS_CHECK_FREQ
*/
public static final String ENV_MONITOR_TXNS_EXPIRATION_TIMEOUT = "exodus.env.monitorTxns.expirationTimeout";
/**
* If {@linkplain #ENV_MONITOR_TXNS_TIMEOUT} is non-zero then stuck transactions monitor starts
* and checks {@linkplain Environment}'s transactions with this frequency (period) specified in
* milliseconds. Default value is {@code 60000}, one minute.
* <p>Mutable at runtime: no
*
* @see Transaction
* @see #ENV_MONITOR_TXNS_TIMEOUT
*/
public static final String ENV_MONITOR_TXNS_CHECK_FREQ = "exodus.env.monitorTxns.checkFreq";
/**
* If is set to {@code true} then the {@linkplain Environment} gathers statistics. If
* {@linkplain #MANAGEMENT_ENABLED} is also {@code true} then the statistics is exposed by the JMX
* managed bean. Default value is {@code true}.
* <p>Mutable at runtime: no
*
* @see Environment#getStatistics()
* @see #MANAGEMENT_ENABLED
*/
public static final String ENV_GATHER_STATISTICS = "exodus.env.gatherStatistics";
/**
* If is set to {@code true} then the {@linkplain Environment} will compact itself on opening.
* Default value is {@code false}.
* <p>Mutable at runtime: no
*/
public static final String ENV_COMPACT_ON_OPEN = "exodus.env.compactOnOpen";
/**
* Internal property. Not for public use.
*/
public static final String ENV_COMPACT_IN_SINGLE_BATCH_ON_OPEN = "exodus.env.compactInSingleBatchOnOpen";
/**
* Defines the maximum size of page of B+Tree. Default value is {@code 128}.
* <p>Mutable at runtime: yes
*/
public static final String TREE_MAX_PAGE_SIZE = "exodus.tree.maxPageSize";
/**
* Defines the maximum size of page of duplicates sub-B+Tree. Default value is {@code 8}.
* <p>Mutable at runtime: yes
*/
public static final String TREE_DUP_MAX_PAGE_SIZE = "exodus.tree.dupMaxPageSize";
/**
* As of 1.0.5, is deprecated and has no effect.
* <p>Mutable at runtime: no
*/
@Deprecated
public static final String TREE_NODES_CACHE_SIZE = "exodus.tree.nodesCacheSize";
/**
* If is set to {@code true} then the database garbage collector is enabled. Default value is
* {@code true}. Switching GC off makes sense only for debugging and troubleshooting purposes.
* <p>Mutable at runtime: yes
*/
public static final String GC_ENABLED = "exodus.gc.enabled";
/**
* Defines the number of milliseconds which the database garbage collector is postponed for after
* the {@linkplain Environment} is created. Default value is {@code 10000}.
* <p>Mutable at runtime: no
*/
public static final String GC_START_IN = "exodus.gc.startIn";
/**
* Defines percent of minimum database utilization. Default value is {@code 50}. That means that
* 50 percent of free space in raw data in {@code Log} files (.xd files) is allowed. If database
* utilization is less than defined (free space percent is more than {@code 50}), the database
* garbage collector is triggered.
* <p>Mutable at runtime: yes
*/
public static final String GC_MIN_UTILIZATION = "exodus.gc.minUtilization";
/**
* If is set to {@code true} the database garbage collector renames files rather than deletes
* them. Default value is {@code false}. It makes sense to change this setting only for debugging
* and troubleshooting purposes.
* <p>Mutable at runtime: yes
*/
public static final String GC_RENAME_FILES = "exodus.gc.renameFiles";
/**
* As of 1.0.2, is deprecated and has no effect.
* <p>Mutable at runtime: no
*/
@Deprecated
public static final String GC_USE_EXPIRATION_CHECKER = "exodus.gc.useExpirationChecker";
/**
* Defines the minimum age of a {@code Log} file (.xd file) to consider it for cleaning by the
* database garbage collector. The age of the last (the newest, the rightmost) {@code Log} file is
* {@code 0}, the age of previous file is {@code 1}, etc. Default value is {@code 2}.
* <p>Mutable at runtime: yes
*/
public static final String GC_MIN_FILE_AGE = "exodus.gc.fileMinAge";
/**
* Defines the number of new {@code Log} files (.xd files) that must be created to trigger if
* necessary (if database utilization is not sufficient) the next background cleaning cycle
* (single run of the database garbage collector) after the previous cycle finished. Default value
* is {@code 3}, i.e. GC can start after each 3 newly created {@code Log} files.
* <p>Mutable at runtime: yes
*/
@SuppressWarnings("DeprecatedIsStillUsed")
@Deprecated
public static final String GC_FILES_INTERVAL = "exodus.gc.filesInterval";
/**
* Defines the number of milliseconds after which background cleaning cycle (single run of the
* database garbage collector) can be repeated if the previous one didn't reach required
* utilization. Default value is {@code 5000}.
* <p>Mutable at runtime: yes
*/
public static final String GC_RUN_PERIOD = "exodus.gc.runPeriod";
/**
* If is set to {@code true} then database utilization will be computed from scratch before the
* first cleaning cycle (single run of the database garbage collector) is triggered, i.e. shortly
* after the database is open. In addition, can be used to compute utilization information at
* runtime by just modifying the setting value. Default value is {@code false}.
* <p>Mutable at runtime: yes
*/
public static final String GC_UTILIZATION_FROM_SCRATCH = "exodus.gc.utilization.fromScratch";
/**
* If is not empty, defines full path to the file with stored utilization. Is used on creation of
* an {@linkplain Environment} to update {@code .xd} files' utilization before the first cleaning
* cycle (single run of the database garbage collector) is triggered. In addition, can be used to
* reload utilization information at runtime by just modifying the setting value. Format of the
* stored utilization is expected to be the same as created by the {@code "-d"} option of the
* {@code Reflect} tool. Default value is empty string.
* <p>Mutable at runtime: yes
*/
public static final String GC_UTILIZATION_FROM_FILE = "exodus.gc.utilization.fromFile";
/**
* If is set to {@code true} the database garbage collector tries to acquire exclusive
* {@linkplain Transaction} for its purposes. In that case, GC transaction never re-plays. In
* order to not block background cleaner thread forever, acquisition of exclusive GC transaction
* is performed with a timeout controlled by the {@linkplain #GC_TRANSACTION_ACQUIRE_TIMEOUT}
* setting. Default value is {@code true}.
* <p>Mutable at runtime: yes
*
* @see #GC_TRANSACTION_ACQUIRE_TIMEOUT
* @see #GC_TRANSACTION_TIMEOUT
* @see Transaction#isExclusive()
*/
public static final String GC_USE_EXCLUSIVE_TRANSACTION = "exodus.gc.useExclusiveTransaction";
/**
* Defines timeout in milliseconds which is used by the database garbage collector to acquire
* exclusive {@linkplain Transaction} for its purposes if
* {@linkplain #GC_USE_EXCLUSIVE_TRANSACTION} is {@code true}. Default value is {@code 1000}.
* <p>Mutable at runtime: yes
*
* @see #GC_USE_EXCLUSIVE_TRANSACTION
* @see #GC_TRANSACTION_TIMEOUT
* @see Transaction#isExclusive()
*/
public static final String GC_TRANSACTION_ACQUIRE_TIMEOUT = "exodus.gc.transactionAcquireTimeout";
/**
* Defines timeout in milliseconds which is used by the database garbage collector to reclaim
* non-expired data in several files inside single GC {@linkplain Transaction} acquired
* exclusively. {@linkplain #GC_USE_EXCLUSIVE_TRANSACTION} should be {@code true}. Default value
* is {@code 500}.
* <p>Mutable at runtime: yes
*
* @see #GC_USE_EXCLUSIVE_TRANSACTION
* @see #GC_TRANSACTION_ACQUIRE_TIMEOUT
* @see Transaction#isExclusive()
*/
public static final String GC_TRANSACTION_TIMEOUT = "exodus.gc.transactionTimeout";
/**
* Defines the number of milliseconds which deletion of any successfully cleaned {@code Log} file
* (.xd file) is postponed for. Default value is {@code 5000}.
* <p>Mutable at runtime: yes
*/
public static final String GC_FILES_DELETION_DELAY = "exodus.gc.filesDeletionDelay";
/**
* If set to nonzero value, GC is forced every this number of seconds. Default value is {@code 0}
* which means that GC is not forced periodically.
* <p>Mutable at runtime: yes
*/
public static final String GC_RUN_EVERY = "exodus.gc.runEvery";
/**
* If is set to {@code true} then the {@linkplain Environment} exposes two JMX managed beans. One
* for {@linkplain Environment#getStatistics() environment statistics} and second for controlling
* the {@code EnvironmentConfig} settings. Default value is {@code true} for non-Android OS, under
* Android it is always {@code false}.
* <p>Mutable at runtime: no
*
* @see Environment#getStatistics()
* @see Environment#getEnvironmentConfig()
*/
public static final String MANAGEMENT_ENABLED = "exodus.managementEnabled";
/**
* If is set to {@code true} then exposed JMX managed beans cannot have operations. Default value
* is {@code true}.
* <p>Mutable at runtime: no
*
* @see #MANAGEMENT_ENABLED
*/
public static final String MANAGEMENT_OPERATIONS_RESTRICTED = "exodus.management.operationsRestricted";
/**
* If set to some value different from {@code null}, expose created environment via given server.
* <p>Mutable at runtime: no
*/
public static final String META_SERVER = "exodus.env.metaServer";
public EnvironmentConfig() {
this(ConfigurationStrategy.SYSTEM_PROPERTY);
}
@SuppressWarnings("rawtypes")
public EnvironmentConfig(@NotNull final ConfigurationStrategy strategy) {
//noinspection unchecked
super(new Pair[]{
new Pair(MEMORY_USAGE_PERCENTAGE, 50),
new Pair(USE_VERSION1_FORMAT, true),
new Pair(CIPHER_ID, null),
new Pair(CIPHER_KEY, null),
new Pair(CIPHER_BASIC_IV, 0L),
new Pair(PROFILER_ENABLED, false),
new Pair(LOG_DURABLE_WRITE, false),
new Pair(LOG_FILE_SIZE, 8192L),
new Pair(LOG_LOCK_TIMEOUT, 0L),
new Pair(LOG_LOCK_ID, null),
new Pair(LOG_CACHE_PAGE_SIZE, 64 << 10),
new Pair(LOG_CACHE_OPEN_FILES, 500),
new Pair(LOG_CACHE_USE_NIO, false),
new Pair(LOG_CACHE_FREE_PHYSICAL_MEMORY_THRESHOLD, 1_000_000_000L), // ~1GB
new Pair(LOG_CACHE_SHARED, true),
new Pair(LOG_CACHE_NON_BLOCKING, true),
new Pair(LOG_CACHE_GENERATION_COUNT, 2),
new Pair(LOG_CACHE_USE_SOFT_REFERENCES, false),
new Pair(LOG_CACHE_READ_AHEAD_MULTIPLE, 1),
new Pair(LOG_CACHE_WARMUP, false),
new Pair(LOG_CLEAN_DIRECTORY_EXPECTED, false),
new Pair(LOG_CLEAR_INVALID, false),
new Pair(LOG_SYNC_PERIOD, 10000L),
new Pair(LOG_FULL_FILE_READ_ONLY, true),
new Pair(LOG_ALLOW_REMOVABLE, false),
new Pair(LOG_ALLOW_REMOTE, false),
new Pair(LOG_ALLOW_RAM_DISK, false),
new Pair(LOG_DATA_READER_WRITER_PROVIDER,
DataReaderWriterProvider.DEFAULT_READER_WRITER_PROVIDER),
new Pair(ENV_IS_READONLY, false),
new Pair(ENV_FAIL_FAST_IN_READONLY, true),
new Pair(ENV_READONLY_EMPTY_STORES, false),
new Pair(ENV_STOREGET_CACHE_SIZE, 0),
new Pair(ENV_STOREGET_CACHE_MIN_TREE_SIZE, 200),
new Pair(ENV_STOREGET_CACHE_MAX_VALUE_SIZE, 200),
new Pair(ENV_CLOSE_FORCEDLY, false),
new Pair(ENV_TXN_REPLAY_TIMEOUT, 2000L),
new Pair(ENV_TXN_REPLAY_MAX_COUNT, 2),
new Pair(ENV_TXN_DOWNGRADE_AFTER_FLUSH, true),
new Pair(ENV_TXN_SINGLE_THREAD_WRITES, false),
new Pair(ENV_CHECK_BACKUP_CONSISTENCY, false),
new Pair(ENV_CHECK_DATA_STRUCTURES_CONSISTENCY, false),
new Pair(ENV_TXN_TRACE_FINISH, false),
new Pair(ENV_MAX_PARALLEL_TXNS, Integer.MAX_VALUE),
new Pair(ENV_MONITOR_TXNS_TIMEOUT, 0),
new Pair(ENV_MONITOR_TXNS_EXPIRATION_TIMEOUT, (int) TimeUnit.HOURS.toMillis(8)),
new Pair(ENV_MONITOR_TXNS_CHECK_FREQ, 60000),
new Pair(ENV_GATHER_STATISTICS, true),
new Pair(ENV_COMPACT_ON_OPEN, false),
new Pair(TREE_MAX_PAGE_SIZE, 128),
new Pair(TREE_DUP_MAX_PAGE_SIZE, 8),
new Pair(GC_ENABLED, true),
new Pair(GC_START_IN, 10000),
new Pair(GC_MIN_UTILIZATION, 50),
new Pair(GC_RENAME_FILES, false),
new Pair(GC_MIN_FILE_AGE, 2),
new Pair(GC_FILES_INTERVAL, 3),
new Pair(GC_RUN_PERIOD, 5000),
new Pair(GC_UTILIZATION_FROM_SCRATCH, false),
new Pair(GC_UTILIZATION_FROM_FILE, ""),
new Pair(GC_FILES_DELETION_DELAY, 5000),
new Pair(GC_RUN_EVERY, 0),
new Pair(GC_USE_EXCLUSIVE_TRANSACTION, true),
new Pair(GC_TRANSACTION_ACQUIRE_TIMEOUT, 1000),
new Pair(GC_TRANSACTION_TIMEOUT, 500),
new Pair(MANAGEMENT_ENABLED, !JVMConstants.getIS_ANDROID()),
new Pair(MANAGEMENT_OPERATIONS_RESTRICTED, true),
new Pair(META_SERVER, null),
new Pair(CHECK_PAGES_AT_RUNTIME, true),
new Pair(LOG_SKIP_INVALID_LOGGALE_TYPE, false),
new Pair(LOG_FORCE_CHECK_DATA_CONSISTENCY, false),
new Pair(LOG_PROCEED_DATA_RESTORE_AT_ANY_COST, false),
new Pair(ENV_COMPACT_IN_SINGLE_BATCH_ON_OPEN, false),new Pair(ENV_COMPACT_IN_SINGLE_BATCH_ON_OPEN, false),
new Pair(ENV_STORES_TO_REMOVE_BEFORE_COMPACTION, null)
}, strategy);
}
/**
* Sets the value of the setting with the specified key.
*
* @param key name of the setting
* @param value the setting value
* @return this {@code EnvironmentConfig} instance
*/
@Override
public EnvironmentConfig setSetting(@NotNull final String key, @NotNull final Object value) {
return (EnvironmentConfig) super.setSetting(key, value);
}
/**
* Set {@code true} for making it possible to change settings of this {@code EnvironmentConfig}
* instance. {@code EnvironmentConfig.DEFAULT} is always immutable.
*
* @param isMutable {@code true} if this {@code EnvironmentConfig} instance can be mutated
* @return this {@code EnvironmentConfig} instance
*/
@Override
public EnvironmentConfig setMutable(boolean isMutable) {
return (EnvironmentConfig) super.setMutable(isMutable);
}
/**
* Returns absolute value of memory in bytes that can be used by the LogCache if it is set. By
* default, is not set.
* <p>Mutable at runtime: no
*
* @return absolute value of memory in bytes that can be used by the LogCache if it is set or
* {@code null}
* @see #getMemoryUsagePercentage()
*/
public Long /* NB! do not change to long */ getMemoryUsage() {
return (Long) getSetting(MEMORY_USAGE);
}
/**
* Sets absolute value of memory in bytes that can be used by the LogCache. Overrides memory
* percent to use by the LogCache set by {@linkplain #setMemoryUsagePercentage(int)}.
* <p>Mutable at runtime: no
*
* @param maxMemory number of bytes that can be used by the LogCache
* @return absolute this {@code EnvironmentConfig} instance
* @see #setMemoryUsagePercentage(int)
*/
public EnvironmentConfig setMemoryUsage(final long maxMemory) {
return setSetting(MEMORY_USAGE, maxMemory);
}
/**
* Returns percent of max memory (specified by the "-Xmx" java parameter) that can be used by the
* LogCache. Is applicable only if {@linkplain #MEMORY_USAGE} is not set. Default value is
* {@code 50}.
* <p>Mutable at runtime: no
*
* @return percent of max memory that can be used by the LogCache
* @see #getMemoryUsage()
*/
public int getMemoryUsagePercentage() {
return (Integer) getSetting(MEMORY_USAGE_PERCENTAGE);
}
/**
* Sets percent of max memory (specified by the "-Xmx" java parameter) that can be used by the
* LogCache. Is applicable only if {@linkplain #MEMORY_USAGE} is not set. Default value is
* {@code 50}.
* <p>Mutable at runtime: no
*
* @param memoryUsagePercentage percent of max memory that can be used by the LogCache
* @return this {@code EnvironmentConfig} instance
* @see #setMemoryUsage(long)
*/
public EnvironmentConfig setMemoryUsagePercentage(final int memoryUsagePercentage) {
return setSetting(MEMORY_USAGE_PERCENTAGE, memoryUsagePercentage);
}
public boolean getUseVersion1Format() {
return (Boolean) getSetting(USE_VERSION1_FORMAT);
}
public EnvironmentConfig setUseVersion1Format(final boolean useVersion1Format) {
return setSetting(USE_VERSION1_FORMAT, useVersion1Format);
}
/**
* Indicates if disk page consistency is checked at runtime.
*
* @see #CHECK_PAGES_AT_RUNTIME
*/
public boolean getCheckPagesAtRuntime() {
return (Boolean) getSetting(CHECK_PAGES_AT_RUNTIME);
}
/**
* Sets if disk page consistency is checked at runtime.
*
* @param checkPagesAtRuntime {@code ture} if consistency of disk pages is checked during runtime
* and {@code false} otherwise.
* @see #CHECK_PAGES_AT_RUNTIME
*/
public EnvironmentConfig setCheckPagesAtRuntime(final boolean checkPagesAtRuntime) {
return setSetting(CHECK_PAGES_AT_RUNTIME, checkPagesAtRuntime);
}
/**
* Returns id of {@linkplain StreamCipherProvider} which will be used to encrypt the database.
* Default value is {@code null}, which means that the database won't be encrypted. The setting
* cannot be changed for existing databases. Default value is {@code null}.
* <p>Mutable at runtime: no
*
* @return id of {@linkplain StreamCipherProvider} which will be used to encrypt the database
* @see #getCipherKey()
* @see #getCipherBasicIV()
* @see StreamCipher
* @see StreamCipherProvider