Fix recursive table evaluation caching
Some checks failed
Deploy Sokko G / deploy (push) Failing after 2s
Some checks failed
Deploy Sokko G / deploy (push) Failing after 2s
This commit is contained in:
parent
34524d2961
commit
7521d50626
3 changed files with 66 additions and 7 deletions
53
tests/table-evaluation.test.mjs
Normal file
53
tests/table-evaluation.test.mjs
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
// Rôle : vérifie le coût des références répétées et les erreurs du tableau.
|
||||
import { test } from "node:test";
|
||||
import assert from "node:assert/strict";
|
||||
import { evaluateTable, evaluateTableCell } from "../website/src/features/toolboxes/modules/tableFormulaEngine.js";
|
||||
|
||||
for (const reverse of [false, true]) {
|
||||
test(`table reuses repeated references with ${reverse ? "forward" : "backward"} dependencies`, () => {
|
||||
const count = 50;
|
||||
const raw = { [reverse ? "A50" : "A1"]: "1" };
|
||||
for (let i = 1; i < count; i++) {
|
||||
const row = reverse ? count - i : i + 1;
|
||||
const dependency = reverse ? row + 1 : row - 1;
|
||||
raw[`A${row}`] = `=A${dependency}+A${dependency}`;
|
||||
}
|
||||
let reads = 0;
|
||||
const cells = new Proxy(raw, {
|
||||
get(target, address) {
|
||||
// Stop an exponential regression before it can hang the test runner.
|
||||
if (++reads > count * 4) throw new Error("Read budget exceeded");
|
||||
return target[address];
|
||||
}
|
||||
});
|
||||
const dimensions = { rows: count, columns: 1 };
|
||||
const last = reverse ? "A1" : "A50";
|
||||
assert.equal(evaluateTableCell(last, cells, dimensions).value, 2 ** 49);
|
||||
assert.ok(reads <= count * 4);
|
||||
reads = 0;
|
||||
assert.equal(evaluateTable(cells, dimensions)[last].value, 2 ** 49);
|
||||
assert.ok(reads <= count * 4);
|
||||
raw[reverse ? "A50" : "A1"] = "2";
|
||||
reads = 0;
|
||||
assert.equal(evaluateTable(cells, dimensions)[last].value, 2 ** 50);
|
||||
});
|
||||
}
|
||||
|
||||
test("shared evaluation preserves cycle, division and invalid reference errors", () => {
|
||||
const cells = {
|
||||
A1: "=B1", B1: "=A1", C1: "=A1+1",
|
||||
A2: "=1/0", B2: "=A2", C2: "=Z99",
|
||||
A3: "text", B3: "=A3", C3: "=7+5"
|
||||
};
|
||||
const dimensions = { rows: 3, columns: 3 };
|
||||
const result = evaluateTable(cells, dimensions);
|
||||
assert.deepEqual(Object.fromEntries(Object.entries(result).map(([key, value]) => [key, value.error])), {
|
||||
A1: "cycle", B1: "cycle", C1: "cycle",
|
||||
A2: "division", B2: "reference", C2: "reference",
|
||||
A3: "", B3: "reference", C3: ""
|
||||
});
|
||||
for (const address of Object.keys(cells)) {
|
||||
assert.deepEqual(result[address], evaluateTableCell(address, cells, dimensions));
|
||||
}
|
||||
assert.equal(result.C3.value, 12);
|
||||
});
|
||||
Loading…
Add table
Add a link
Reference in a new issue