@solid/community-server
Version:
Community Solid Server: an open and modular implementation of the Solid specifications
75 lines • 3.04 kB
JavaScript
;
Object.defineProperty(exports, "__esModule", { value: true });
exports.PathBasedReader = void 0;
const global_logger_factory_1 = require("global-logger-factory");
const IterableUtil_1 = require("../util/IterableUtil");
const IdentifierMap_1 = require("../util/map/IdentifierMap");
const MapUtil_1 = require("../util/map/MapUtil");
const PathUtil_1 = require("../util/PathUtil");
const PermissionReader_1 = require("./PermissionReader");
/**
* Redirects requests to specific PermissionReaders based on their identifier.
* The keys are regular expression strings.
* The regular expressions should all start with a slash
* and will be evaluated relative to the base URL.
*
* Will error if no match is found.
*/
class PathBasedReader extends PermissionReader_1.PermissionReader {
logger = (0, global_logger_factory_1.getLoggerFor)(this);
baseUrl;
paths;
defaultReader;
constructor(baseUrl, paths, defaultReader) {
super();
this.baseUrl = (0, PathUtil_1.ensureTrailingSlash)(baseUrl);
const entries = Object.entries(paths)
.map(([key, val]) => [new RegExp(key, 'u'), val]);
this.paths = new Map(entries);
this.defaultReader = defaultReader;
}
async canHandle(input) {
for (const [reader, readerModes] of this.matchReaders(input.requestedModes)) {
await reader.canHandle({ credentials: input.credentials, requestedModes: readerModes });
}
}
async handle(input) {
const results = [];
for (const [reader, readerModes] of this.matchReaders(input.requestedModes)) {
results.push(await reader.handle({ credentials: input.credentials, requestedModes: readerModes }));
}
return new IdentifierMap_1.IdentifierMap((0, IterableUtil_1.concat)(results));
}
/**
* Returns for each reader the matching part of the access map.
*/
matchReaders(accessMap) {
const result = new Map();
for (const [identifier, modes] of accessMap.entrySets()) {
const reader = this.findReader(identifier.path);
if (reader) {
const matches = (0, MapUtil_1.getDefault)(result, reader, () => new IdentifierMap_1.IdentifierSetMultiMap());
matches.set(identifier, modes);
}
}
return result;
}
/**
* Find the PermissionReader corresponding to the given path.
*/
findReader(path) {
if (path.startsWith(this.baseUrl)) {
// We want to keep the leading slash
const relative = path.slice((0, PathUtil_1.trimTrailingSlashes)(this.baseUrl).length);
for (const [regex, reader] of this.paths) {
if (regex.test(relative)) {
this.logger.debug(`Permission reader found for ${path}`);
return reader;
}
}
}
return this.defaultReader;
}
}
exports.PathBasedReader = PathBasedReader;
//# sourceMappingURL=PathBasedReader.js.map