@tanstack/db-ivm
Version:
Incremental View Maintenance for TanStack DB based on Differential Dataflow
100 lines (99 loc) • 3.88 kB
JavaScript
;
var __typeError = (msg) => {
throw TypeError(msg);
};
var __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg);
var __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj));
var __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value);
var __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), setter ? setter.call(obj, value) : member.set(obj, value), value);
var _index, _indexOut, _f;
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
const graph = require("../graph.cjs");
const d2 = require("../d2.cjs");
const multiset = require("../multiset.cjs");
const indexes = require("../indexes.cjs");
class ReduceOperator extends graph.UnaryOperator {
constructor(id, inputA, output, f) {
super(id, inputA, output);
__privateAdd(this, _index, new indexes.Index());
__privateAdd(this, _indexOut, new indexes.Index());
__privateAdd(this, _f);
__privateSet(this, _f, f);
}
run() {
const keysTodo = /* @__PURE__ */ new Set();
for (const message of this.inputMessages()) {
for (const [item, multiplicity] of message.getInner()) {
const [key, value] = item;
__privateGet(this, _index).addValue(key, [value, multiplicity]);
keysTodo.add(key);
}
}
const result = [];
for (const key of keysTodo) {
const curr = __privateGet(this, _index).get(key);
const currOut = __privateGet(this, _indexOut).get(key);
const out = __privateGet(this, _f).call(this, curr);
const newOutputMap = /* @__PURE__ */ new Map();
const oldOutputMap = /* @__PURE__ */ new Map();
for (const [value, multiplicity] of out) {
const existing = newOutputMap.get(value) ?? 0;
newOutputMap.set(value, existing + multiplicity);
}
for (const [value, multiplicity] of currOut) {
const existing = oldOutputMap.get(value) ?? 0;
oldOutputMap.set(value, existing + multiplicity);
}
for (const [value, multiplicity] of oldOutputMap) {
if (!newOutputMap.has(value)) {
result.push([[key, value], -multiplicity]);
__privateGet(this, _indexOut).addValue(key, [value, -multiplicity]);
}
}
for (const [value, multiplicity] of newOutputMap) {
if (!oldOutputMap.has(value)) {
if (multiplicity !== 0) {
result.push([[key, value], multiplicity]);
__privateGet(this, _indexOut).addValue(key, [value, multiplicity]);
}
}
}
for (const [value, newMultiplicity] of newOutputMap) {
const oldMultiplicity = oldOutputMap.get(value);
if (oldMultiplicity !== void 0) {
const delta = newMultiplicity - oldMultiplicity;
if (delta !== 0) {
result.push([[key, value], delta]);
__privateGet(this, _indexOut).addValue(key, [value, delta]);
}
}
}
}
if (result.length > 0) {
this.output.sendData(new multiset.MultiSet(result));
}
}
}
_index = new WeakMap();
_indexOut = new WeakMap();
_f = new WeakMap();
function reduce(f) {
return (stream) => {
const output = new d2.StreamBuilder(
stream.graph,
new graph.DifferenceStreamWriter()
);
const operator = new ReduceOperator(
stream.graph.getNextOperatorId(),
stream.connectReader(),
output.writer,
f
);
stream.graph.addOperator(operator);
stream.graph.addStream(output.connectReader());
return output;
};
}
exports.ReduceOperator = ReduceOperator;
exports.reduce = reduce;
//# sourceMappingURL=reduce.cjs.map