@solid/community-server
Version:
Community Solid Server: an open and modular implementation of the Solid specifications
83 lines • 2.58 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.JsonFileStorage = void 0;
const fs_extra_1 = require("fs-extra");
const SystemError_1 = require("../../util/errors/SystemError");
/**
* Uses a JSON file to store key/value pairs.
*/
class JsonFileStorage {
filePath;
locker;
lockIdentifier;
constructor(filePath, locker) {
this.filePath = filePath;
this.locker = locker;
// Using file path as identifier for the lock as it should be unique for this file
this.lockIdentifier = { path: filePath };
}
async get(key) {
const json = await this.getJsonSafely();
return json[key];
}
async has(key) {
const json = await this.getJsonSafely();
return typeof json[key] !== 'undefined';
}
async set(key, value) {
return this.updateJsonSafely((json) => {
json[key] = value;
return this;
});
}
async delete(key) {
return this.updateJsonSafely((json) => {
if (typeof json[key] !== 'undefined') {
delete json[key];
return true;
}
return false;
});
}
async *entries() {
const json = await this.getJsonSafely();
yield* Object.entries(json);
}
/**
* Acquires the data in the JSON file while using a read lock.
*/
async getJsonSafely() {
return this.locker.withReadLock(this.lockIdentifier, this.getJson.bind(this));
}
/**
* Updates the data in the JSON file while using a write lock.
*
* @param updateFn - A function that updates the JSON object.
*
* @returns The return value of `updateFn`.
*/
async updateJsonSafely(updateFn) {
return this.locker.withWriteLock(this.lockIdentifier, async () => {
const json = await this.getJson();
const result = updateFn(json);
await (0, fs_extra_1.writeJson)(this.filePath, json, { encoding: 'utf8', spaces: 2 });
return result;
});
}
/**
* Reads and parses the data from the JSON file (without locking).
*/
async getJson() {
try {
return await (0, fs_extra_1.readJson)(this.filePath, 'utf8');
}
catch (error) {
if ((0, SystemError_1.isSystemError)(error) && error.code === 'ENOENT') {
return {};
}
throw error;
}
}
}
exports.JsonFileStorage = JsonFileStorage;
//# sourceMappingURL=JsonFileStorage.js.map