diff --git a/dependencies/lmdb/libraries/liblmdb/lmdb.h b/dependencies/lmdb/libraries/liblmdb/lmdb.h index 745460818..d8f5c53e3 100644 --- a/dependencies/lmdb/libraries/liblmdb/lmdb.h +++ b/dependencies/lmdb/libraries/liblmdb/lmdb.h @@ -378,6 +378,7 @@ typedef void (MDB_sum_func)(const MDB_val *src, MDB_val *dst, const MDB_val *key #define MDB_SAFE_RESTORE 0x800 /** Track metrics for this env */ #define MDB_TRACK_METRICS 0x400 +#define MDB_USE_NEW_FREESPACE 0x200 /** Use the overlapping sync strategy */ #define MDB_OVERLAPPINGSYNC_SYNC = 0x02 /** @} */ diff --git a/dependencies/lmdb/libraries/liblmdb/mdb.c b/dependencies/lmdb/libraries/liblmdb/mdb.c index 113c6ce98..7accd4712 100644 --- a/dependencies/lmdb/libraries/liblmdb/mdb.c +++ b/dependencies/lmdb/libraries/liblmdb/mdb.c @@ -2886,7 +2886,19 @@ mdb_page_alloc(MDB_cursor *mc, int num, MDB_page **mp) rc = mdb_cursor_get(&m2, &key, NULL, op); op = MDB_NEXT; // now iterate forwards through the txns of free list last = *(txnid_t *) key.mv_data; - } else { + } else if (!(MDB_USE_NEW_FREESPACE & env->me_flags)) { + if (env->me_freelist_end) { // if we are only reading forward, and we have already read the latest transactions, then nothing to do + break; + } else { + env->me_freelist_end = last = 1; + env->me_freelist_start = 1; + key.mv_data = &last; // start at the beginning of the freelist and read oldest txns first + key.mv_size = sizeof(last); + rc = mdb_cursor_get(&m2, &key, NULL, op); + op = MDB_NEXT; // now iterate forwards through the txns of free list + last = *(txnid_t *) key.mv_data; + } + } else { // no more transactions to read going forward through newest, we are now going // to switch to reading older transactions. However, first we set the op // to forward to ensure that we fall into the switch into previous iterations below @@ -2912,6 +2924,9 @@ mdb_page_alloc(MDB_cursor *mc, int num, MDB_page **mp) // iterating forward from the freelist range to find newer transactions if (last >= oldest || rc == MDB_NOTFOUND) { env->me_freelist_end = oldest; + if (!(MDB_USE_NEW_FREESPACE & env->me_flags)) { + break; + } // no more newer transactions, go to the beginning of the range and look for older txns op = MDB_SET_RANGE; if (env->me_freelist_start <= 1) break; // should be no zero entry, break out diff --git a/open.js b/open.js index 23086d135..90bcc5919 100644 --- a/open.js +++ b/open.js @@ -1,5 +1,19 @@ -import { Compression, getAddress, arch, fs, path as pathModule, lmdbError, EventEmitter, MsgpackrEncoder, Env, - Dbi, tmpdir, os, nativeAddon, version } from './native.js'; +import { + Compression, + getAddress, + arch, + fs, + path as pathModule, + lmdbError, + EventEmitter, + MsgpackrEncoder, + Env, + Dbi, + tmpdir, + os, + nativeAddon, + version, +} from './native.js'; import { CachingStore, setGetLastVersion } from './caching.js'; import { addReadMethods, makeReusableBuffer } from './read.js'; import { addWriteMethods } from './write.js'; @@ -12,11 +26,10 @@ export function setRequire(require) { setGetLastVersion(getLastVersion, getLastTxnId); let keyBytes, keyBytesView; const buffers = []; -const { onExit, getEnvsPointer, setEnvsPointer, getEnvFlags, setJSFlags } = nativeAddon; -if (globalThis.__lmdb_envs__) - setEnvsPointer(globalThis.__lmdb_envs__); -else - globalThis.__lmdb_envs__ = getEnvsPointer(); +const { onExit, getEnvsPointer, setEnvsPointer, getEnvFlags, setJSFlags } = + nativeAddon; +if (globalThis.__lmdb_envs__) setEnvsPointer(globalThis.__lmdb_envs__); +else globalThis.__lmdb_envs__ = getEnvsPointer(); // this is hard coded as an upper limit because it is important assumption of the fixed buffers in writing instructions // this corresponds to the max key size for 8KB pages @@ -45,7 +58,8 @@ export function open(path, options) { nativeAddon.getLastVersion = getLastVersion; nativeAddon.getLastTxnId = getLastTxnId; } - if (!keyBytes) // TODO: Consolidate get buffer and key buffer (don't think we need both) + if (!keyBytes) + // TODO: Consolidate get buffer and key buffer (don't think we need both) allocateFixedBuffer(); if (typeof path == 'object' && !options) { options = path; @@ -55,39 +69,63 @@ export function open(path, options) { let noFSAccess = options.noFSAccess; // this can only be configured on open, can't let users change it let userOptions = options; if (path == null) { - options = Object.assign({ - deleteOnClose: true, - noSync: true, - }, options); - path = tmpdir() + '/' + Math.floor(Math.random() * 2821109907455).toString(36) + '.mdb' - } else if (!options) - options = {}; + options = Object.assign( + { + deleteOnClose: true, + noSync: true, + }, + options, + ); + path = + tmpdir() + + '/' + + Math.floor(Math.random() * 2821109907455).toString(36) + + '.mdb'; + } else if (!options) options = {}; let extension = pathModule.extname(path); let name = pathModule.basename(path, extension); let is32Bit = arch().endsWith('32'); let isLegacyLMDB = version.patch < 90; - let remapChunks = (options.remapChunks || options.encryptionKey || (options.mapSize ? - (is32Bit && options.mapSize > 0x100000000) : // larger than fits in address space, must use dynamic maps - is32Bit)) && !isLegacyLMDB; // without a known map size, we default to being able to handle large data correctly/well*/ + let remapChunks = + (options.remapChunks || + options.encryptionKey || + (options.mapSize + ? is32Bit && options.mapSize > 0x100000000 // larger than fits in address space, must use dynamic maps + : is32Bit)) && + !isLegacyLMDB; // without a known map size, we default to being able to handle large data correctly/well*/ let userMapSize = options.mapSize; - options = Object.assign({ - noSubdir: Boolean(extension), - isRoot: true, - maxDbs: 12, - remapChunks, - keyBytes, - overlappingSync: (options.noSync || options.readOnly) ? false : (os != 'win32'), - // default map size limit of 4 exabytes when using remapChunks, since it is not preallocated and we can - // make it super huge. - mapSize: remapChunks ? 0x10000000000000 : - isLegacyLMDB ? is32Bit ? 0x1000000 : 0x100000000 : 0x20000, // Otherwise we start small with 128KB - safeRestore: process.env.LMDB_RESTORE == 'safe', - }, options); + options = Object.assign( + { + noSubdir: Boolean(extension), + isRoot: true, + maxDbs: 12, + remapChunks, + keyBytes, + overlappingSync: + options.noSync || options.readOnly ? false : os != 'win32', + // default map size limit of 4 exabytes when using remapChunks, since it is not preallocated and we can + // make it super huge. + mapSize: remapChunks + ? 0x10000000000000 + : isLegacyLMDB + ? is32Bit + ? 0x1000000 + : 0x100000000 + : 0x20000, // Otherwise we start small with 128KB + safeRestore: process.env.LMDB_RESTORE == 'safe', + }, + options, + ); options.path = path; if (options.asyncTransactionOrder == 'strict') { options.strictAsyncOrder = true; } - if (nativeAddon.version.major + nativeAddon.version.minor / 100 + nativeAddon.version.patch / 10000 < 0.0980) { + if ( + nativeAddon.version.major + + nativeAddon.version.minor / 100 + + nativeAddon.version.patch / 10000 < + 0.098 + ) { options.overlappingSync = false; // not support on older versions options.trackMetrics = false; options.usePreviousSnapshot = false; @@ -97,27 +135,40 @@ export function open(path, options) { } if (!exists(options.noSubdir ? pathModule.dirname(path) : path)) - fs.mkdirSync(options.noSubdir ? pathModule.dirname(path) : path, { recursive: true } - ); + fs.mkdirSync(options.noSubdir ? pathModule.dirname(path) : path, { + recursive: true, + }); function makeCompression(compressionOptions) { - if (compressionOptions instanceof Compression) - return compressionOptions; + if (compressionOptions instanceof Compression) return compressionOptions; let useDefault = typeof compressionOptions != 'object'; - if (useDefault && defaultCompression) - return defaultCompression; - compressionOptions = Object.assign({ - threshold: 1000, - dictionary: fs.readFileSync(new URL('./dict/dict.txt', import.meta.url.replace(/dist[\\\/]index.cjs$/, ''))), - getValueBytes: makeReusableBuffer(0), - }, compressionOptions); - let compression = Object.assign(new Compression(compressionOptions), compressionOptions); - if (useDefault) - defaultCompression = compression; + if (useDefault && defaultCompression) return defaultCompression; + compressionOptions = Object.assign( + { + threshold: 1000, + dictionary: fs.readFileSync( + new URL( + './dict/dict.txt', + import.meta.url.replace(/dist[\\\/]index.cjs$/, ''), + ), + ), + getValueBytes: makeReusableBuffer(0), + }, + compressionOptions, + ); + let compression = Object.assign( + new Compression(compressionOptions), + compressionOptions, + ); + if (useDefault) defaultCompression = compression; return compression; } if (isLegacyLMDB) { // legacy LMDB, turn off these options - Object.assign(options, { overlappingSync: false, remapChunks: false, safeRestore: false }); + Object.assign(options, { + overlappingSync: false, + remapChunks: false, + safeRestore: false, + }); } if (options.compression) options.compression = makeCompression(options.compression); @@ -134,29 +185,37 @@ export function open(path, options) { (options.usePreviousSnapshot ? 0x2000000 : 0) | (options.remapChunks ? 0x4000000 : 0) | (options.safeRestore ? 0x800 : 0) | - (options.trackMetrics ? 0x400 : 0); + (options.trackMetrics ? 0x400 : 0) | + (options.useNewFreespace ? 0x200 : 0); let env = new Env(); - let jsFlags = (options.overlappingSync ? 0x1000 : 0) | + let jsFlags = + (options.overlappingSync ? 0x1000 : 0) | (options.separateFlushed ? 1 : 0) | (options.deleteOnClose ? 2 : 0); let rc = env.open(options, flags, jsFlags); env.path = path; - if (rc) - lmdbError(rc); - delete options.keyBytes // no longer needed, don't copy to stores + if (rc) lmdbError(rc); + delete options.keyBytes; // no longer needed, don't copy to stores let maxKeySize = env.getMaxKeySize(); - maxKeySize = Math.min(maxKeySize, options.pageSize ? MAX_KEY_SIZE : DEFAULT_MAX_KEY_SIZE); + maxKeySize = Math.min( + maxKeySize, + options.pageSize ? MAX_KEY_SIZE : DEFAULT_MAX_KEY_SIZE, + ); flags = getEnvFlags(env.address); // re-retrieve them, they are not necessarily the same if we are connecting to an existing env if (flags & 0x1000) { if (userOptions.noSync) { env.close(); - throw new Error('Can not set noSync on a database that was opened with overlappingSync'); + throw new Error( + 'Can not set noSync on a database that was opened with overlappingSync', + ); } } else if (options.overlappingSync) { if (userOptions.overlappingSync) { env.close(); - throw new Error('Can not enable overlappingSync on a database that was opened without this flag'); + throw new Error( + 'Can not enable overlappingSync on a database that was opened without this flag', + ); } options.overlappingSync = false; jsFlags = jsFlags & 0xff; // clear overlapping sync @@ -164,7 +223,11 @@ export function open(path, options) { } env.readerCheck(); // clear out any stale entries - if ((options.overlappingSync || options.deleteOnClose) && !hasRegisteredOnExit && process.on) { + if ( + (options.overlappingSync || options.deleteOnClose) && + !hasRegisteredOnExit && + process.on + ) { hasRegisteredOnExit = true; process.on('exit', onExit); } @@ -173,37 +236,49 @@ export function open(path, options) { constructor(dbName, dbOptions) { super(); if (dbName === undefined) - throw new Error('Database name must be supplied in name property (may be null for root database)'); + throw new Error( + 'Database name must be supplied in name property (may be null for root database)', + ); - if (options.compression && dbOptions.compression !== false && typeof dbOptions.compression != 'object') + if ( + options.compression && + dbOptions.compression !== false && + typeof dbOptions.compression != 'object' + ) dbOptions.compression = options.compression; // use the parent compression if available else if (dbOptions.compression) dbOptions.compression = makeCompression(dbOptions.compression); if (dbOptions.dupSort && (dbOptions.useVersions || dbOptions.cache)) { - throw new Error('The dupSort flag can not be combined with versions or caching'); + throw new Error( + 'The dupSort flag can not be combined with versions or caching', + ); } - let keyIsBuffer = dbOptions.keyIsBuffer + let keyIsBuffer = dbOptions.keyIsBuffer; if (dbOptions.keyEncoding == 'uint32') { dbOptions.keyIsUint32 = true; } else if (dbOptions.keyEncoder) { if (dbOptions.keyEncoder.enableNullTermination) { - dbOptions.keyEncoder.enableNullTermination() - } else - keyIsBuffer = true; + dbOptions.keyEncoder.enableNullTermination(); + } else keyIsBuffer = true; } else if (dbOptions.keyEncoding == 'binary') { keyIsBuffer = true; } - let flags = (dbOptions.reverseKey ? 0x02 : 0) | + let flags = + (dbOptions.reverseKey ? 0x02 : 0) | (dbOptions.dupSort ? 0x04 : 0) | (dbOptions.dupFixed ? 0x10 : 0) | (dbOptions.integerDup ? 0x20 : 0) | (dbOptions.reverseDup ? 0x40 : 0) | (!options.readOnly && dbOptions.create !== false ? 0x40000 : 0) | (dbOptions.useVersions ? 0x100 : 0); - let keyType = (dbOptions.keyIsUint32 || dbOptions.keyEncoding == 'uint32') ? 2 : keyIsBuffer ? 3 : 0; - if (keyType == 2) - flags |= 0x08; // integer key + let keyType = + dbOptions.keyIsUint32 || dbOptions.keyEncoding == 'uint32' + ? 2 + : keyIsBuffer + ? 3 + : 0; + if (keyType == 2) flags |= 0x08; // integer key if (options.readOnly) { // in read-only mode we use a read-only txn to open the database @@ -215,15 +290,25 @@ export function open(path, options) { this.ensureReadTxn(); this.db = new Dbi(env, flags, dbName, keyType, dbOptions.compression); } else { - this.transactionSync(() => { - this.db = new Dbi(env, flags, dbName, keyType, dbOptions.compression); - }, options.overlappingSync ? 0x10002 : 2); // no flush-sync, but synchronously commit + this.transactionSync( + () => { + this.db = new Dbi( + env, + flags, + dbName, + keyType, + dbOptions.compression, + ); + }, + options.overlappingSync ? 0x10002 : 2, + ); // no flush-sync, but synchronously commit } this._commitReadTxn(); // current read transaction becomes invalid after opening another db - if (!this.db || this.db.dbi == 0xffffffff) {// not found - throw new Error('Database not found') + if (!this.db || this.db.dbi == 0xffffffff) { + // not found + throw new Error('Database not found'); } - this.dbAddress = this.db.address + this.dbAddress = this.db.address; this.db.name = dbName || null; this.name = dbName; this.status = 'open'; @@ -237,25 +322,69 @@ export function open(path, options) { if (dbOptions.immediateBatchThreshold) console.warn('immediateBatchThreshold is no longer supported'); this.commitDelay = DEFAULT_COMMIT_DELAY; - Object.assign(this, { // these are the options that are inherited - path: options.path, - encoding: options.encoding, - strictAsyncOrder: options.strictAsyncOrder, - }, dbOptions); + Object.assign( + this, + { + // these are the options that are inherited + path: options.path, + encoding: options.encoding, + strictAsyncOrder: options.strictAsyncOrder, + }, + dbOptions, + ); let Encoder; if (this.encoder && this.encoder.Encoder) { Encoder = this.encoder.Encoder; this.encoder = null; // don't copy everything from the module } - if (!Encoder && !(this.encoder && this.encoder.encode) && (!this.encoding || this.encoding == 'msgpack' || this.encoding == 'cbor')) { - Encoder = (this.encoding == 'cbor' ? moduleRequire('cbor-x').Encoder : MsgpackrEncoder); + if ( + !Encoder && + !(this.encoder && this.encoder.encode) && + (!this.encoding || + this.encoding == 'msgpack' || + this.encoding == 'cbor') + ) { + Encoder = + this.encoding == 'cbor' + ? moduleRequire('cbor-x').Encoder + : MsgpackrEncoder; } if (Encoder) { - this.encoder = new Encoder(Object.assign( - assignConstrainedProperties(['copyBuffers', 'getStructures', 'saveStructures', 'useFloat32', 'useRecords', 'structuredClone', 'variableMapSize', 'useTimestamp32', 'largeBigIntToFloat', 'encodeUndefinedAsNil', 'int64AsNumber', 'onInvalidDate', 'mapsAsObjects', 'useTag259ForMaps', 'pack', 'maxSharedStructures', 'shouldShareStructure', 'randomAccessStructure', 'freezeData'], - this.sharedStructuresKey !== undefined ? this.setupSharedStructures() : { - copyBuffers: true, // need to copy any embedded buffers that are found since we use unsafe buffers - }, options, dbOptions), this.encoder)); + this.encoder = new Encoder( + Object.assign( + assignConstrainedProperties( + [ + 'copyBuffers', + 'getStructures', + 'saveStructures', + 'useFloat32', + 'useRecords', + 'structuredClone', + 'variableMapSize', + 'useTimestamp32', + 'largeBigIntToFloat', + 'encodeUndefinedAsNil', + 'int64AsNumber', + 'onInvalidDate', + 'mapsAsObjects', + 'useTag259ForMaps', + 'pack', + 'maxSharedStructures', + 'shouldShareStructure', + 'randomAccessStructure', + 'freezeData', + ], + this.sharedStructuresKey !== undefined + ? this.setupSharedStructures() + : { + copyBuffers: true, // need to copy any embedded buffers that are found since we use unsafe buffers + }, + options, + dbOptions, + ), + this.encoder, + ), + ); } if (this.encoding == 'json') { this.encoder = { @@ -263,7 +392,7 @@ export function open(path, options) { }; } else if (this.encoder) { this.decoder = this.encoder; - this.decoderCopies = !this.encoder.needsStableBuffer + this.decoderCopies = !this.encoder.needsStableBuffer; } this.maxKeySize = maxKeySize; applyKeyHandling(this); @@ -271,19 +400,19 @@ export function open(path, options) { } openDB(dbName, dbOptions) { if (this.dupSort && this.name == null) - throw new Error('Can not open named databases if the main database is dupSort') + throw new Error( + 'Can not open named databases if the main database is dupSort', + ); if (typeof dbName == 'object' && !dbOptions) { dbOptions = dbName; dbName = dbOptions.name; - } else - dbOptions = dbOptions || {}; + } else dbOptions = dbOptions || {}; try { - return dbOptions.cache ? - new (CachingStore(LMDBStore, env))(dbName, dbOptions) : - new LMDBStore(dbName, dbOptions); - } catch(error) { - if (error.message == 'Database not found') - return; // return undefined to indicate db not found + return dbOptions.cache + ? new (CachingStore(LMDBStore, env))(dbName, dbOptions) + : new LMDBStore(dbName, dbOptions); + } catch (error) { + if (error.message == 'Database not found') return; // return undefined to indicate db not found if (error.message.indexOf('MDB_DBS_FULL') > -1) { error.message += ' (increase your maxDbs option)'; } @@ -292,59 +421,67 @@ export function open(path, options) { } open(dbOptions, callback) { let db = this.openDB(dbOptions); - if (callback) - callback(null, db); + if (callback) callback(null, db); return db; } backup(path, compact) { - if (noFSAccess) - return; + if (noFSAccess) return; fs.mkdirSync(pathModule.dirname(path), { recursive: true }); - return new Promise((resolve, reject) => env.copy(path, compact, (error) => { - if (error) { - reject(error); - } else { - resolve(); - } - })); + return new Promise((resolve, reject) => + env.copy(path, compact, (error) => { + if (error) { + reject(error); + } else { + resolve(); + } + }), + ); } isOperational() { return this.status == 'open'; } sync(callback) { - return env.sync(callback || function(error) { - if (error) { - console.error(error); - } - }); + return env.sync( + callback || + function (error) { + if (error) { + console.error(error); + } + }, + ); } deleteDB() { console.warn('deleteDB() is deprecated, use drop or dropSync instead'); return this.dropSync(); } dropSync() { - this.transactionSync(() => - this.db.drop({ - justFreePages: false - }), options.overlappingSync ? 0x10002 : 2); + this.transactionSync( + () => + this.db.drop({ + justFreePages: false, + }), + options.overlappingSync ? 0x10002 : 2, + ); } clear(callback) { - if (typeof callback == 'function') - return this.clearAsync(callback); - console.warn('clear() is deprecated, use clearAsync or clearSync instead'); + if (typeof callback == 'function') return this.clearAsync(callback); + console.warn( + 'clear() is deprecated, use clearAsync or clearSync instead', + ); this.clearSync(); } clearSync() { if (this.encoder) { - if (this.encoder.clearSharedData) - this.encoder.clearSharedData() - else if (this.encoder.structures) - this.encoder.structures = [] + if (this.encoder.clearSharedData) this.encoder.clearSharedData(); + else if (this.encoder.structures) this.encoder.structures = []; } - this.transactionSync(() => - this.db.drop({ - justFreePages: true - }), options.overlappingSync ? 0x10002 : 2); + this.transactionSync( + () => + this.db.drop({ + justFreePages: true, + }), + options.overlappingSync ? 0x10002 : 2, + ); } readerCheck() { return env.readerCheck(); @@ -355,24 +492,32 @@ export function open(path, options) { setupSharedStructures() { const getStructures = () => { let lastVersion; // because we are doing a read here, we may need to save and restore the lastVersion from the last read - if (this.useVersions) - lastVersion = getLastVersion(); + if (this.useVersions) lastVersion = getLastVersion(); let buffer = this.getBinary(this.sharedStructuresKey); - if (this.useVersions) - setLastVersion(lastVersion); + if (this.useVersions) setLastVersion(lastVersion); return buffer && this.decoder.decode(buffer); }; return { saveStructures: (structures, isCompatible) => { - return this.transactionSync(() => { - let existingStructuresBuffer = this.getBinary(this.sharedStructuresKey); - let existingStructures = existingStructuresBuffer && this.decoder.decode(existingStructuresBuffer); - if (typeof isCompatible == 'function' ? - !isCompatible(existingStructures) : - (existingStructures && existingStructures.length != isCompatible)) - return false; // it changed, we need to indicate that we couldn't update - this.put(this.sharedStructuresKey, structures); - }, options.overlappingSync ? 0x10000 : 0); + return this.transactionSync( + () => { + let existingStructuresBuffer = this.getBinary( + this.sharedStructuresKey, + ); + let existingStructures = + existingStructuresBuffer && + this.decoder.decode(existingStructuresBuffer); + if ( + typeof isCompatible == 'function' + ? !isCompatible(existingStructures) + : existingStructures && + existingStructures.length != isCompatible + ) + return false; // it changed, we need to indicate that we couldn't update + this.put(this.sharedStructuresKey, structures); + }, + options.overlappingSync ? 0x10000 : 0, + ); }, getStructures, copyBuffers: true, // need to copy any embedded buffers that are found since we use unsafe buffers @@ -382,10 +527,21 @@ export function open(path, options) { // if caching class overrides putSync, don't want to double call the caching code const putSync = LMDBStore.prototype.putSync; const removeSync = LMDBStore.prototype.removeSync; - addReadMethods(LMDBStore, { env, maxKeySize, keyBytes, keyBytesView, getLastVersion }); + addReadMethods(LMDBStore, { + env, + maxKeySize, + keyBytes, + keyBytesView, + getLastVersion, + }); if (!options.readOnly) - addWriteMethods(LMDBStore, { env, maxKeySize, fixedBuffer: keyBytes, - resetReadTxn: LMDBStore.prototype.resetReadTxn, ...options }); + addWriteMethods(LMDBStore, { + env, + maxKeySize, + fixedBuffer: keyBytes, + resetReadTxn: LMDBStore.prototype.resetReadTxn, + ...options, + }); LMDBStore.prototype.supports = { permanence: true, bufferKeys: true, @@ -394,7 +550,7 @@ export function open(path, options) { clear: true, status: true, deferredOpen: true, - openCallback: true, + openCallback: true, }; let Class = options.cache ? CachingStore(LMDBStore, env) : LMDBStore; return options.asClass ? Class : new Class(options.name || null, options); @@ -422,21 +578,28 @@ export function getLastTxnId() { const KEY_BUFFER_SIZE = 4096; function allocateFixedBuffer() { - keyBytes = typeof Buffer != 'undefined' ? Buffer.allocUnsafeSlow(KEY_BUFFER_SIZE) : new Uint8Array(KEY_BUFFER_SIZE); + keyBytes = + typeof Buffer != 'undefined' + ? Buffer.allocUnsafeSlow(KEY_BUFFER_SIZE) + : new Uint8Array(KEY_BUFFER_SIZE); const keyBuffer = keyBytes.buffer; - keyBytesView = keyBytes.dataView || (keyBytes.dataView = new DataView(keyBytes.buffer, 0, KEY_BUFFER_SIZE)); // max key size is actually 4026 + keyBytesView = + keyBytes.dataView || + (keyBytes.dataView = new DataView(keyBytes.buffer, 0, KEY_BUFFER_SIZE)); // max key size is actually 4026 keyBytes.uint32 = new Uint32Array(keyBuffer, 0, KEY_BUFFER_SIZE >> 2); keyBytes.float64 = new Float64Array(keyBuffer, 0, KEY_BUFFER_SIZE >> 3); - keyBytes.uint32.address = keyBytes.address = keyBuffer.address = getAddress(keyBuffer); + keyBytes.uint32.address = + keyBytes.address = + keyBuffer.address = + getAddress(keyBuffer); } function exists(path) { - if (fs.existsSync) - return fs.existsSync(path); + if (fs.existsSync) return fs.existsSync(path); try { return fs.statSync(path); } catch (error) { - return false + return false; } } @@ -444,8 +607,7 @@ function assignConstrainedProperties(allowedProperties, target) { for (let i = 2; i < arguments.length; i++) { let source = arguments[i]; for (let key in source) { - if (allowedProperties.includes(key)) - target[key] = source[key]; + if (allowedProperties.includes(key)) target[key] = source[key]; } } return target;