public static Engine createSnapshotFor(Engine engine) { if (engine.isReadOnly()) return engine; if (engine instanceof TxEngine) return ((TxEngine) engine).snapshot(); if (engine instanceof EngineWrapper) createSnapshotFor(((EngineWrapper) engine).getWrappedEngine()); throw new UnsupportedOperationException( "Snapshots are not enabled, use DBMaker.snapshotEnable()"); }
/** constructs Engine using current settings */ public Engine makeEngine() { final boolean readOnly = propsGetBool(Keys.readOnly); final File file = props.containsKey(Keys.file) ? new File(props.getProperty(Keys.file)) : null; final String volume = props.getProperty(Keys.volume); final String store = props.getProperty(Keys.store); if (readOnly && file == null) throw new UnsupportedOperationException("Can not open in-memory DB in read-only mode."); if (readOnly && !file.exists() && !Keys.store_append.equals(store)) { throw new UnsupportedOperationException("Can not open non-existing file in read-only mode."); } if (propsGetLong(Keys.sizeLimit, 0) > 0 && Keys.store_append.equals(store)) throw new UnsupportedOperationException("Append-Only store does not support Size Limit"); extendArgumentCheck(); Engine engine; if (!Keys.store_append.equals(store)) { Volume.Factory folFac = extendStoreVolumeFactory(); engine = propsGetBool(Keys.transactionDisable) ? extendStoreDirect(folFac) : extendStoreWAL(folFac); } else { if (Keys.volume_heap.equals(volume) || Keys.volume_offheap.equals(volume)) throw new UnsupportedOperationException( "Append Storage format is not supported with in-memory dbs"); engine = extendStoreAppend(); } engine = extendWrapStore(engine); if (propsGetBool(Keys.asyncWrite) && !readOnly) { engine = extendAsyncWriteEngine(engine); } final String cache = props.getProperty(Keys.cache, CC.DEFAULT_CACHE); if (Keys.cache_disable.equals(cache)) { // do not wrap engine in cache } else if (Keys.cache_hashTable.equals(cache)) { engine = extendCacheHashTable(engine); } else if (Keys.cache_hardRef.equals(cache)) { engine = extendCacheHardRef(engine); } else if (Keys.cache_weakRef.equals(cache)) { engine = extendCacheWeakRef(engine); } else if (Keys.cache_softRef.equals(cache)) { engine = extendCacheSoftRef(engine); } else if (Keys.cache_lru.equals(cache)) { engine = extendCacheLRU(engine); } else { throw new IllegalArgumentException("unknown cache type: " + cache); } engine = extendWrapCache(engine); if (propsGetBool(Keys.snapshots)) engine = extendSnapshotEngine(engine); engine = extendWrapSnapshotEngine(engine); if (readOnly) engine = new ReadOnlyEngine(engine); if (propsGetBool(Keys.closeOnJvmShutdown)) { engine = new EngineWrapper.CloseOnJVMShutdown(engine); } // try to read one record from DB, to make sure encryption and compression are correctly set. Fun.Tuple2<Integer, byte[]> check = null; try { check = (Fun.Tuple2<Integer, byte[]>) engine.get(Engine.CHECK_RECORD, Serializer.BASIC); if (check != null) { if (check.a.intValue() != Arrays.hashCode(check.b)) throw new RuntimeException("invalid checksum"); } } catch (Throwable e) { throw new IllegalArgumentException( "Error while opening store. Make sure you have right password, compression or encryption is well configured.", e); } if (check == null && !engine.isReadOnly()) { // new db, so insert testing record byte[] b = new byte[127]; new Random().nextBytes(b); check = Fun.t2(Arrays.hashCode(b), b); engine.update(Engine.CHECK_RECORD, check, Serializer.BASIC); engine.commit(); } return engine; }