Skip to content

Commit 25005e2

Browse files
tree(test): simplify enrichment testing (microsoft#26418)
## Description Small refactor of the enrichment testing code. Improves the readability of the tests by factoring out the mocking into helper function. ## Breaking Changes None
1 parent d9742af commit 25005e2

File tree

1 file changed

+58
-72
lines changed

1 file changed

+58
-72
lines changed

packages/dds/tree/src/test/shared-tree/sharedTreeChangeFamily.spec.ts

Lines changed: 58 additions & 72 deletions
Original file line numberDiff line numberDiff line change
@@ -273,10 +273,13 @@ describe("SharedTreeChangeFamily", () => {
273273
// The tests below heavily mock the inputs to updateRefreshers.
274274
// This is done to simplify the tests, but it also has the effect of reducing their dependency on the
275275
// ModularChangeset format and on the behavior of the helper functions that operate on it.
276-
// ModularChangeset instances that are used as input are mocked to represent the list of relevant node IDs that
277-
// they need refreshers for.
278-
// ModularChangeset instances that are used as output are mocked to represent the list refreshers that are
279-
// included in them. The refreshers themselves are mocked using unique strings.
276+
interface MockChange {
277+
/** The IDs of the nodes that are relevant to this change. This is the test input. */
278+
readonly relevant?: DeltaDetachedNodeId[];
279+
/** The refreshers associated with this change. This is the test output. */
280+
readonly refreshers?: string[];
281+
}
282+
280283
const idInForest1: DeltaDetachedNodeId = { minor: 1 };
281284
const idInForest2: DeltaDetachedNodeId = { minor: 2 };
282285
const idNotInForest: DeltaDetachedNodeId = { minor: 3 };
@@ -293,25 +296,31 @@ describe("SharedTreeChangeFamily", () => {
293296
removedRoots: Iterable<DeltaDetachedNodeId>,
294297
requireRefreshers: boolean,
295298
): ModularChangeset {
296-
const output: TreeChunk[] = [];
297-
const relevantToChange = new Set<string>(change as unknown as string[]);
299+
const mockChange = change as unknown as MockChange;
300+
const relevantToChange = new Set<DeltaDetachedNodeId>(mockChange.relevant ?? []);
301+
const refreshers: string[] = [];
298302
for (const id of removedRoots) {
299303
// Check that the removed root is indeed relevant to the change
300-
assert.equal(relevantToChange.has(id as unknown as string), true);
304+
assert.equal(relevantToChange.has(id), true);
301305
const tree = getDetachedNode(id);
302306
if (tree === undefined) {
303307
if (requireRefreshers) {
304308
throw new Error("Missing tree");
305309
}
306310
} else {
307-
output.push(tree);
311+
refreshers.push(tree as unknown as string);
308312
}
309313
}
310-
return output as unknown as ModularChangeset;
314+
const updated: MockChange = {
315+
...mockChange,
316+
refreshers,
317+
};
318+
return updated as unknown as ModularChangeset;
311319
}
312-
function testUpdateRefreshers(input: SharedTreeChange): SharedTreeChange {
320+
function testUpdateRefreshers(mocks: readonly MockChange[]): string[][] {
321+
const input: SharedTreeChange = sharedTreeChangeFromMocks(mocks);
313322
deepFreeze(input);
314-
return updateRefreshers(
323+
const updated = updateRefreshers(
315324
input,
316325
// Mock for getDetachedNode
317326
(id): TreeChunk | undefined => {
@@ -329,81 +338,58 @@ describe("SharedTreeChangeFamily", () => {
329338
},
330339
// Mock for relevantRemovedRootsFromDataChange
331340
(change: ModularChangeset): DeltaDetachedNodeId[] =>
332-
change as unknown as DeltaDetachedNodeId[],
341+
(change as unknown as MockChange).relevant ?? [],
333342
updateDataChangeRefreshers,
334343
);
344+
return refreshersFromSharedTreeChange(updated);
335345
}
346+
function sharedTreeChangeFromMocks(mocks: readonly MockChange[]): SharedTreeChange {
347+
const changes: SharedTreeInnerChange[] = [];
348+
for (const mock of mocks) {
349+
changes.push({
350+
type: "data",
351+
innerChange: mock as unknown as ModularChangeset,
352+
});
353+
changes.push(schemaChange);
354+
}
355+
return { changes };
356+
}
357+
function refreshersFromSharedTreeChange(change: SharedTreeChange): string[][] {
358+
const result: string[][] = [];
359+
for (const innerChange of change.changes) {
360+
if (innerChange.type === "data") {
361+
const mockChange = innerChange.innerChange as unknown as MockChange;
362+
result.push(mockChange.refreshers ?? []);
363+
}
364+
}
365+
return result;
366+
}
367+
336368
it("updates all data changes", () => {
337-
const input: SharedTreeChange = {
338-
changes: [
339-
{ innerChange: [idInForest1] as unknown as ModularChangeset, type: "data" },
340-
schemaChange,
341-
{ innerChange: [idInForest2] as unknown as ModularChangeset, type: "data" },
342-
],
343-
};
369+
const input: MockChange[] = [{ relevant: [idInForest1] }, { relevant: [idInForest2] }];
344370
const updated = testUpdateRefreshers(input);
345-
assert.deepEqual(updated, {
346-
changes: [
347-
{ innerChange: [refresher1], type: "data" },
348-
schemaChange,
349-
{ innerChange: [refresher2], type: "data" },
350-
],
351-
});
371+
assert.deepEqual(updated, [[refresher1], [refresher2]]);
352372
});
353373
it("excludes refreshers from later changes if they are included in earlier changes", () => {
354-
const input: SharedTreeChange = {
355-
changes: [
356-
{ innerChange: [idInForest1] as unknown as ModularChangeset, type: "data" },
357-
schemaChange,
358-
{
359-
innerChange: [idInForest1, idInForest2] as unknown as ModularChangeset,
360-
type: "data",
361-
},
362-
schemaChange,
363-
{
364-
innerChange: [idInForest1, idInForest2] as unknown as ModularChangeset,
365-
type: "data",
366-
},
367-
],
368-
};
374+
const input: MockChange[] = [
375+
{ relevant: [idInForest1] },
376+
{ relevant: [idInForest1, idInForest2] },
377+
{ relevant: [idInForest1, idInForest2] },
378+
];
369379
const updated = testUpdateRefreshers(input);
370-
assert.deepEqual(updated, {
371-
changes: [
372-
{ innerChange: [refresher1], type: "data" },
373-
schemaChange,
374-
{ innerChange: [refresher2], type: "data" },
375-
schemaChange,
376-
{ innerChange: [], type: "data" },
377-
],
378-
});
380+
assert.deepEqual(updated, [[refresher1], [refresher2], []]);
379381
});
380382
it("throws for missing refreshers in first data change", () => {
381-
const input: SharedTreeChange = {
382-
changes: [
383-
{ innerChange: [idNotInForest] as unknown as ModularChangeset, type: "data" },
384-
],
385-
};
383+
const input: MockChange[] = [{ relevant: [idNotInForest] }];
386384
assert.throws(() => testUpdateRefreshers(input));
387385
});
388386
it("tolerates missing refreshers in later data changes", () => {
389-
const input: SharedTreeChange = {
390-
changes: [
391-
{ innerChange: [idInForest1] as unknown as ModularChangeset, type: "data" },
392-
schemaChange,
393-
{
394-
innerChange: [idNotInForest, idInForest2] as unknown as ModularChangeset,
395-
type: "data",
396-
},
397-
],
398-
};
387+
const input: MockChange[] = [
388+
{ relevant: [idInForest1] },
389+
{ relevant: [idNotInForest, idInForest2] },
390+
];
399391
const updated = testUpdateRefreshers(input);
400-
assert.deepEqual(updated, {
401-
changes: [
402-
{ innerChange: [refresher1], type: "data" },
403-
schemaChange,
404-
{ innerChange: [refresher2], type: "data" },
405-
],
406-
});
392+
assert.deepEqual(updated, [[refresher1], [refresher2]]);
407393
});
408394
});
409395

0 commit comments

Comments
 (0)