Fast document oriented javascript in-memory database
npx @tessl/cli install tessl/npm-lokijs@1.5.0LokiJS is a fast, document-oriented NoSQL in-memory database written entirely in JavaScript. It provides high-performance data storage and retrieval with unique and binary indexing capabilities, achieving up to 1.1M operations per second. The library supports dynamic views for efficient data subset access, built-in persistence adapters, a changes API for tracking modifications, and join operations for complex queries.
npm install lokijsconst loki = require('lokijs');For ES6 modules:
import loki from 'lokijs';Browser usage:
<script src="lokijs.js"></script>
<!-- loki is available as a global variable -->const loki = require('lokijs');
// Create database
const db = new loki('example.db');
// Add collection
const users = db.addCollection('users');
// Insert documents
users.insert({ name: 'Alice', age: 25, active: true });
users.insert({ name: 'Bob', age: 30, active: false });
users.insert({ name: 'Charlie', age: 35, active: true });
// Query documents
const activeUsers = users.find({ active: true });
const user = users.findOne({ name: 'Alice' });
// Chain operations
const result = users.chain()
.find({ active: true })
.where(obj => obj.age > 25)
.simplesort('name')
.data();
// Save database (with adapter)
db.saveDatabase();LokiJS is built around several key components:
Core database operations including creation, persistence, serialization, and collection management.
class Loki {
constructor(filename?: string, options?: DatabaseOptions);
addCollection(name: string, options?: CollectionOptions): Collection;
getCollection(collectionName: string): Collection | null;
removeCollection(collectionName: string): void;
loadDatabase(options?: any, callback?: Function): void;
saveDatabase(callback?: Function): void;
serialize(options?: SerializeOptions): string;
}Document storage and retrieval with powerful querying, indexing, and aggregation capabilities.
class Collection {
constructor(name: string, options?: CollectionOptions);
insert(doc: object | object[]): object | object[];
update(doc: object): object;
remove(doc: object): object;
find(query?: object): object[];
findOne(query?: object): object | null;
chain(transform?: string, parameters?: object): Resultset;
where(fun: Function): object[];
count(query?: object): number;
}Chainable query interface with filtering, sorting, transformations, and aggregation operations.
class Resultset {
constructor(collection: Collection, options?: object);
find(query: object, firstOnly?: boolean): Resultset;
where(fun: Function): Resultset;
sort(comparefun: Function): Resultset;
simplesort(propname: string, options?: object): Resultset;
limit(qty: number): Resultset;
offset(pos: number): Resultset;
data(options?: object): object[];
}Live, automatically updated views of collection data with persistent filtering and sorting.
class DynamicView {
constructor(collection: Collection, name: string, options?: object);
applyFind(query: object): DynamicView;
applyWhere(fun: Function): DynamicView;
applySort(comparefun: Function): DynamicView;
applySimpleSort(propname: string, options?: object): DynamicView;
data(options?: object): object[];
count(): number;
rematerialize(): DynamicView;
}Storage backends for different environments including file system, localStorage, IndexedDB, and custom adapters.
interface PersistenceAdapter {
loadDatabase(dbname: string, callback: Function): void;
saveDatabase(dbname: string, dbref: object, callback: Function): void;
}
// Built-in adapters
class LokiFsAdapter implements PersistenceAdapter;
class LokiLocalStorageAdapter implements PersistenceAdapter;
class LokiMemoryAdapter implements PersistenceAdapter;
class LokiPartitioningAdapter implements PersistenceAdapter;Simple key-value storage with binary search capabilities for efficient lookups.
class KeyValueStore {
constructor();
/** Set a key-value pair */
set(key: any, value: any): void;
/** Get values for a key */
get(key: any): any[];
/** Set custom sort function */
setSort(fun: Function): void;
/** Remove a key-value pair */
remove(key: any, value: any): void;
/** Clear all key-value pairs */
clear(): void;
}Helper functions for object manipulation, comparison operations, and query processing.
// Object utilities
loki.deepFreeze(obj: object): void;
loki.freeze(obj: object): void;
loki.unFreeze(obj: object): object;
// Comparison helpers
loki.aeq(prop1: any, prop2: any): boolean;
loki.lt(prop1: any, prop2: any, equal?: boolean): boolean;
loki.gt(prop1: any, prop2: any, equal?: boolean): boolean;
// Query operations (complete set)
loki.LokiOps: {
// Comparison operators
$eq: Function, $aeq: Function, $ne: Function, $dteq: Function,
$gt: Function, $gte: Function, $lt: Function, $lte: Function,
$jgt: Function, $jgte: Function, $jlt: Function, $jlte: Function,
// Range operators
$between: Function, $jbetween: Function,
// Array/Set operators
$in: Function, $nin: Function, $inSet: Function,
$contains: Function, $containsAny: Function, $containsNone: Function,
$containsString: Function,
// Object operators
$keyin: Function, $nkeyin: Function, $definedin: Function, $undefinedin: Function,
$elemMatch: Function,
// Pattern matching
$regex: Function, $type: Function, $where: Function
};
// Comparator functions
loki.Comparators: {
aeq: Function,
lt: Function,
gt: Function
};
// Constructors available on loki
loki.Collection: typeof Collection;
loki.DynamicView: typeof DynamicView;
loki.Resultset: typeof Resultset;
loki.KeyValueStore: typeof KeyValueStore;
// Persistence adapters
loki.LokiMemoryAdapter: typeof LokiMemoryAdapter;
loki.LokiPartitioningAdapter: typeof LokiPartitioningAdapter;
loki.LokiLocalStorageAdapter: typeof LokiLocalStorageAdapter;
loki.LokiFsAdapter: typeof LokiFsAdapter;
loki.persistenceAdapters: {
fs: typeof LokiFsAdapter;
localStorage: typeof LokiLocalStorageAdapter;
};
// Event system (inherited by Loki, Collection, DynamicView)
interface EventEmitter {
on(eventName: string, listener: Function): void;
emit(eventName: string, ...args: any[]): void;
removeListener(eventName: string, listener: Function): void;
}interface DatabaseOptions {
autosave?: boolean;
autosaveInterval?: number;
adapter?: PersistenceAdapter;
serializationMethod?: string;
destructureDelimiter?: string;
verbose?: boolean;
throttledSaves?: boolean;
env?: string;
persistenceMethod?: string;
}
interface CollectionOptions {
unique?: string[];
exact?: string[];
indices?: string[];
adaptiveBinaryIndices?: boolean;
asyncListeners?: boolean;
disableMeta?: boolean;
disableChangesApi?: boolean;
disableDeltaChangesApi?: boolean;
autoupdate?: boolean;
clone?: boolean;
cloneMethod?: string;
transactional?: boolean;
ttl?: number;
ttlInterval?: number;
serializableIndices?: boolean;
}
interface SerializeOptions {
serializationMethod?: string;
destructureDelimiter?: string;
}