@configurator/ravendb
Version:
RavenDB client for Node.js
371 lines • 18.8 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.SessionTimeSeriesBase = void 0;
const InMemoryDocumentSessionOperations_1 = require("./InMemoryDocumentSessionOperations");
const Exceptions_1 = require("../../Exceptions");
const TypeUtil_1 = require("../../Utility/TypeUtil");
const StringUtil_1 = require("../../Utility/StringUtil");
const TimeSeriesOperation_1 = require("../Operations/TimeSeries/TimeSeriesOperation");
const IdTypeAndName_1 = require("../IdTypeAndName");
const TimeSeriesBatchCommandData_1 = require("../Commands/Batches/TimeSeriesBatchCommandData");
const DatesComparator_1 = require("../../Primitives/DatesComparator");
const GetTimeSeriesOperation_1 = require("../Operations/TimeSeries/GetTimeSeriesOperation");
const CaseInsensitiveKeysMap_1 = require("../../Primitives/CaseInsensitiveKeysMap");
const GetMultipleTimeSeriesOperation_1 = require("../Operations/TimeSeries/GetMultipleTimeSeriesOperation");
const Constants_1 = require("../../Constants");
const IncrementalTimeSeriesBatchCommandData_1 = require("../Commands/Batches/IncrementalTimeSeriesBatchCommandData");
class SessionTimeSeriesBase {
constructor(session, documentIdOrEntity, name) {
if (TypeUtil_1.TypeUtil.isString(documentIdOrEntity)) {
const documentId = documentIdOrEntity;
if (!documentId) {
(0, Exceptions_1.throwError)("InvalidArgumentException", "DocumentId cannot be null");
}
if (!name) {
(0, Exceptions_1.throwError)("InvalidArgumentException", "Name cannot be null");
}
this.docId = documentId;
this.name = name;
this.session = session;
}
else {
const entity = documentIdOrEntity;
if (!entity) {
(0, Exceptions_1.throwError)("InvalidArgumentException", "Entity cannot be null");
}
const documentInfo = session.documentsByEntity.get(entity);
if (!documentInfo) {
this._throwEntityNotInSession();
return;
}
if (StringUtil_1.StringUtil.isNullOrWhitespace(name)) {
(0, Exceptions_1.throwError)("InvalidArgumentException", "Name cannot be null or whitespace");
}
this.docId = documentInfo.id;
this.name = name;
this.session = session;
}
}
_appendInternal(timestamp, valueOrValues, tag) {
const values = TypeUtil_1.TypeUtil.isArray(valueOrValues) ? valueOrValues : [valueOrValues];
const documentInfo = this.session.documentsById.getValue(this.docId);
if (documentInfo && this.session.deletedEntities.contains(documentInfo.entity)) {
SessionTimeSeriesBase._throwDocumentAlreadyDeletedInSession(this.docId, this.name);
}
const op = new TimeSeriesOperation_1.AppendOperation(timestamp, values, tag);
const command = this.session.deferredCommandsMap.get(IdTypeAndName_1.IdTypeAndName.keyFor(this.docId, "TimeSeries", this.name));
if (command) {
const tsCmd = command;
tsCmd.timeSeries.append(op);
}
else {
const appends = [];
appends.push(op);
this.session.defer(new TimeSeriesBatchCommandData_1.TimeSeriesBatchCommandData(this.docId, this.name, appends, null));
}
}
delete(from, to) {
const documentInfo = this.session.documentsById.getValue(this.docId);
if (documentInfo && this.session.deletedEntities.contains(documentInfo.entity)) {
SessionTimeSeriesBase._throwDocumentAlreadyDeletedInSession(this.docId, this.name);
}
const op = new TimeSeriesOperation_1.DeleteOperation(from, to);
const command = this.session.deferredCommandsMap.get(IdTypeAndName_1.IdTypeAndName.keyFor(this.docId, "TimeSeries", this.name));
if (command) {
const tsCmd = command;
tsCmd.timeSeries.delete(op);
}
else {
const deletes = [];
deletes.push(op);
this.session.defer(new TimeSeriesBatchCommandData_1.TimeSeriesBatchCommandData(this.docId, this.name, null, deletes));
}
this._removeFromCacheIfNeeded(from, to);
}
deleteAt(at) {
this.delete(at, at);
}
_removeFromCacheIfNeeded(from, to) {
const cache = this.session.timeSeriesByDocId.get(this.docId);
if (!cache) {
return;
}
if (!from && !to) {
cache.delete(this.name);
return;
}
const ranges = cache.get(this.name);
if (ranges && ranges.length) {
const newRanges = ranges.filter(range => DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(range.from), (0, DatesComparator_1.leftDate)(from)) > 0
|| DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(range.to), (0, DatesComparator_1.rightDate)(to)) < 0);
cache.set(this.name, newRanges);
}
}
_incrementInternal(timestamp, values) {
const documentInfo = this.session.documentsById.getValue(this.docId);
if (documentInfo && this.session.deletedEntities.contains(documentInfo.entity)) {
SessionTimeSeriesBase._throwDocumentAlreadyDeletedInSession(this.docId, this.name);
}
const op = new TimeSeriesOperation_1.IncrementOperation();
op.timestamp = timestamp;
op.values = values;
const command = this.session.deferredCommandsMap.get(IdTypeAndName_1.IdTypeAndName.keyFor(this.docId, "TimeSeriesWithIncrements", this.name));
if (command) {
const tsCmd = command;
tsCmd.timeSeries.increment(op);
}
else {
const list = [];
list.push(op);
this.session.defer(new IncrementalTimeSeriesBatchCommandData_1.IncrementalTimeSeriesBatchCommandData(this.docId, this.name, list));
}
}
static _throwDocumentAlreadyDeletedInSession(documentId, timeSeries) {
(0, Exceptions_1.throwError)("InvalidOperationException", "Can't modify timeseries " + timeSeries
+ " of document " + documentId + ", the document was already deleted in this session");
}
_throwEntityNotInSession() {
(0, Exceptions_1.throwError)("InvalidArgumentException", "Entity is not associated with the session, cannot perform timeseries operations to it. "
+ "Use documentId instead or track the entity in the session.");
}
async getTimeSeriesAndIncludes(from, to, includes, start, pageSize) {
if (pageSize === 0) {
return [];
}
const document = this.session.documentsById.getValue(this.docId);
if (document) {
const metadataTimeSeries = document.metadata[Constants_1.CONSTANTS.Documents.Metadata.TIME_SERIES];
if (metadataTimeSeries && TypeUtil_1.TypeUtil.isArray(metadataTimeSeries)) {
if (!metadataTimeSeries.find(x => StringUtil_1.StringUtil.equalsIgnoreCase(x, this.name))) {
return [];
}
}
}
this.session.incrementRequestCount();
const rangeResult = await this.session.operations.send(new GetTimeSeriesOperation_1.GetTimeSeriesOperation(this.docId, this.name, from, to, start, pageSize, includes), this.session.sessionInfo);
if (!rangeResult) {
return null;
}
if (!this.session.noTracking) {
this._handleIncludes(rangeResult);
let cache = this.session.timeSeriesByDocId.get(this.docId);
if (!cache) {
cache = CaseInsensitiveKeysMap_1.CaseInsensitiveKeysMap.create();
this.session.timeSeriesByDocId.set(this.docId, cache);
}
const ranges = cache.get(this.name);
if (ranges && ranges.length > 0) {
const index = DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[0].from), (0, DatesComparator_1.rightDate)(to)) > 0 ? 0 : ranges.length;
ranges.splice(index, 0, rangeResult);
}
else {
const item = [];
item.push(rangeResult);
cache.set(this.name, item);
}
}
return rangeResult.entries;
}
_handleIncludes(rangeResult) {
if (!rangeResult.includes) {
return;
}
this.session.registerIncludes(rangeResult.includes);
rangeResult.includes = null;
}
static _skipAndTrimRangeIfNeeded(from, to, fromRange, toRange, values, skip, trim) {
if (fromRange && DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(fromRange.to), (0, DatesComparator_1.leftDate)(from)) >= 0) {
if (toRange && DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(toRange.from), (0, DatesComparator_1.rightDate)(to)) <= 0) {
return values.slice(skip, values.length - trim);
}
return values.slice(skip);
}
if (toRange && DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(toRange.from), (0, DatesComparator_1.rightDate)(to)) <= 0) {
return values.slice(0, values.length - trim);
}
return values;
}
async _serveFromCache(from, to, start, pageSize, includes) {
const cache = this.session.timeSeriesByDocId.get(this.docId);
const ranges = cache.get(this.name);
let toRangeIndex;
let fromRangeIndex = -1;
let rangesToGetFromServer;
for (toRangeIndex = 0; toRangeIndex < ranges.length; toRangeIndex++) {
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[toRangeIndex].from), (0, DatesComparator_1.leftDate)(from)) <= 0) {
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(ranges[toRangeIndex].to), (0, DatesComparator_1.rightDate)(to)) >= 0
|| (ranges[toRangeIndex].entries.length - start >= pageSize)) {
return SessionTimeSeriesBase._chopRelevantRange(ranges[toRangeIndex], from, to, start, pageSize);
}
fromRangeIndex = toRangeIndex;
continue;
}
if (!rangesToGetFromServer) {
rangesToGetFromServer = [];
}
const fromToUse = toRangeIndex === 0 || DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(ranges[toRangeIndex - 1].to), (0, DatesComparator_1.leftDate)(from)) < 0
? from
: ranges[toRangeIndex - 1].to;
const toToUse = DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[toRangeIndex].from), (0, DatesComparator_1.rightDate)(to)) <= 0
? ranges[toRangeIndex].from
: to;
rangesToGetFromServer.push({
name: this.name,
from: fromToUse,
to: toToUse
});
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(ranges[toRangeIndex].to), (0, DatesComparator_1.rightDate)(to)) >= 0) {
break;
}
}
if (toRangeIndex === ranges.length) {
if (!rangesToGetFromServer) {
rangesToGetFromServer = [];
}
rangesToGetFromServer.push({
name: this.name,
from: ranges[ranges.length - 1].to,
to
});
}
this.session.incrementRequestCount();
const details = await this.session.operations.send(new GetMultipleTimeSeriesOperation_1.GetMultipleTimeSeriesOperation(this.docId, rangesToGetFromServer, start, pageSize, includes), this.session.sessionInfo);
if (includes) {
this._registerIncludes(details);
}
let resultToUser;
const mergedValues = SessionTimeSeriesBase._mergeRangesWithResults(from, to, ranges, fromRangeIndex, toRangeIndex, details.values.get(this.name), r => resultToUser = r);
if (!this.session.noTracking) {
const fromDates = details.values.get(this.name)
.map(x => (0, DatesComparator_1.leftDate)(x.from));
if (fromDates.length) {
from = fromDates[0].date;
fromDates.forEach(d => {
if (DatesComparator_1.DatesComparator.compare(d, (0, DatesComparator_1.leftDate)(from)) < 0) {
from = d.date;
}
});
}
else {
from = null;
}
const toDates = details.values.get(this.name)
.map(x => (0, DatesComparator_1.rightDate)(x.to));
if (toDates.length) {
to = toDates[0].date;
toDates.forEach(d => {
if (DatesComparator_1.DatesComparator.compare(d, (0, DatesComparator_1.rightDate)(to)) > 0) {
to = d.date;
}
});
}
else {
to = null;
}
InMemoryDocumentSessionOperations_1.InMemoryDocumentSessionOperations.addToCache(this.name, from, to, fromRangeIndex, toRangeIndex, ranges, cache, mergedValues);
}
return resultToUser;
}
_registerIncludes(details) {
for (const rangeResult of details.values.get(this.name)) {
this._handleIncludes(rangeResult);
}
}
static _mergeRangesWithResults(from, to, ranges, fromRangeIndex, toRangeIndex, resultFromServer, resultToUserSetter) {
let skip = 0;
let trim = 0;
let currentResultIndex = 0;
const mergedValues = [];
const start = fromRangeIndex !== -1 ? fromRangeIndex : 0;
const end = toRangeIndex === ranges.length ? ranges.length - 1 : toRangeIndex;
for (let i = start; i <= end; i++) {
if (i === fromRangeIndex) {
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[i].from), (0, DatesComparator_1.leftDate)(from)) <= 0 &&
DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(from), (0, DatesComparator_1.rightDate)(ranges[i].to)) <= 0) {
if (ranges[i].entries) {
for (const v of ranges[i].entries) {
mergedValues.push(v);
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.definedDate)(v.timestamp), (0, DatesComparator_1.leftDate)(from)) < 0) {
skip++;
}
}
}
}
continue;
}
if (currentResultIndex < resultFromServer.length
&& DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(resultFromServer[currentResultIndex].from), (0, DatesComparator_1.leftDate)(ranges[i].from)) < 0) {
const toAdd = resultFromServer[currentResultIndex++]
.entries
.slice(mergedValues.length === 0 ? 0 : 1);
mergedValues.push(...toAdd);
}
if (i === toRangeIndex) {
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[i].from), (0, DatesComparator_1.rightDate)(to)) <= 0) {
for (let index = mergedValues.length === 0 ? 0 : 1; index < ranges[i].entries.length; index++) {
mergedValues.push(ranges[i].entries[index]);
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.definedDate)(ranges[i].entries[index].timestamp), (0, DatesComparator_1.rightDate)(to)) > 0) {
trim++;
}
}
}
continue;
}
let shouldSkip = false;
if (mergedValues.length > 0) {
shouldSkip = ranges[i].entries[0].timestamp.getTime() === mergedValues[mergedValues.length - 1].timestamp.getTime();
}
const toAdd = ranges[i].entries.slice(!shouldSkip ? 0 : 1);
mergedValues.push(...toAdd);
}
if (currentResultIndex < resultFromServer.length) {
const toAdd = resultFromServer[currentResultIndex++]
.entries
.slice(mergedValues.length === 0 ? 0 : 1);
mergedValues.push(...toAdd);
}
resultToUserSetter(SessionTimeSeriesBase._skipAndTrimRangeIfNeeded(from, to, fromRangeIndex === -1 ? null : ranges[fromRangeIndex], toRangeIndex === ranges.length ? null : ranges[toRangeIndex], mergedValues, skip, trim));
return mergedValues;
}
static _chopRelevantRange(range, from, to, start, pageSize) {
if (!range.entries) {
return [];
}
const result = [];
for (const value of range.entries) {
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.definedDate)(value.timestamp), (0, DatesComparator_1.rightDate)(to)) > 0) {
break;
}
if (DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.definedDate)(value.timestamp), (0, DatesComparator_1.leftDate)(from)) < 0) {
continue;
}
if (start-- > 0) {
continue;
}
if (pageSize-- <= 0) {
break;
}
result.push(value);
}
return result;
}
async _getFromCache(from, to, includes, start, pageSize) {
const resultToUser = await this._serveFromCache(from, to, start, pageSize, includes);
return resultToUser;
}
_notInCache(from, to) {
const cache = this.session.timeSeriesByDocId.get(this.docId);
if (!cache) {
return true;
}
const ranges = cache.get(this.name);
if (!ranges) {
return true;
}
return ranges.length === 0
|| DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.leftDate)(ranges[0].from), (0, DatesComparator_1.rightDate)(to)) > 0
|| DatesComparator_1.DatesComparator.compare((0, DatesComparator_1.rightDate)(ranges[ranges.length - 1].to), (0, DatesComparator_1.leftDate)(from)) < 0;
}
}
exports.SessionTimeSeriesBase = SessionTimeSeriesBase;
//# sourceMappingURL=SessionTimeSeriesBase.js.map