@fluidframework/sequence 2.0.0-rc.2.0.2 → 2.0.0-rc.3.0.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +23 -0
- package/README.md +1 -1
- package/api-report/sequence.api.md +32 -32
- package/beta.d.ts +11 -0
- package/dist/{localValues.d.ts → IntervalCollectionValues.d.ts} +13 -12
- package/dist/IntervalCollectionValues.d.ts.map +1 -0
- package/dist/{localValues.js → IntervalCollectionValues.js} +6 -6
- package/dist/IntervalCollectionValues.js.map +1 -0
- package/dist/beta.d.ts +12 -0
- package/dist/index.d.ts +2 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +10 -10
- package/dist/index.js.map +1 -1
- package/dist/intervalCollection.d.ts +10 -10
- package/dist/intervalCollection.d.ts.map +1 -1
- package/dist/intervalCollection.js +103 -99
- package/dist/intervalCollection.js.map +1 -1
- package/dist/{defaultMap.d.ts → intervalCollectionMap.d.ts} +11 -44
- package/dist/intervalCollectionMap.d.ts.map +1 -0
- package/dist/{defaultMap.js → intervalCollectionMap.js} +15 -70
- package/dist/intervalCollectionMap.js.map +1 -0
- package/dist/{defaultMapInterfaces.d.ts → intervalCollectionMapInterfaces.d.ts} +17 -16
- package/dist/intervalCollectionMapInterfaces.d.ts.map +1 -0
- package/dist/{defaultMapInterfaces.js → intervalCollectionMapInterfaces.js} +1 -1
- package/dist/intervalCollectionMapInterfaces.js.map +1 -0
- package/dist/intervalIndex/endpointInRangeIndex.d.ts +1 -1
- package/dist/intervalIndex/endpointInRangeIndex.d.ts.map +1 -1
- package/dist/intervalIndex/endpointInRangeIndex.js +3 -3
- package/dist/intervalIndex/endpointInRangeIndex.js.map +1 -1
- package/dist/intervalIndex/endpointIndex.d.ts +1 -1
- package/dist/intervalIndex/endpointIndex.d.ts.map +1 -1
- package/dist/intervalIndex/endpointIndex.js +3 -3
- package/dist/intervalIndex/endpointIndex.js.map +1 -1
- package/dist/intervalIndex/idIntervalIndex.d.ts.map +1 -1
- package/dist/intervalIndex/idIntervalIndex.js +3 -3
- package/dist/intervalIndex/idIntervalIndex.js.map +1 -1
- package/dist/intervalIndex/overlappingIntervalsIndex.d.ts +3 -3
- package/dist/intervalIndex/overlappingIntervalsIndex.d.ts.map +1 -1
- package/dist/intervalIndex/overlappingIntervalsIndex.js +2 -3
- package/dist/intervalIndex/overlappingIntervalsIndex.js.map +1 -1
- package/dist/intervalIndex/overlappingSequenceIntervalsIndex.d.ts.map +1 -1
- package/dist/intervalIndex/overlappingSequenceIntervalsIndex.js +6 -6
- package/dist/intervalIndex/overlappingSequenceIntervalsIndex.js.map +1 -1
- package/dist/intervalIndex/sequenceIntervalIndexes.d.ts +1 -1
- package/dist/intervalIndex/sequenceIntervalIndexes.d.ts.map +1 -1
- package/dist/intervalIndex/sequenceIntervalIndexes.js.map +1 -1
- package/dist/intervalIndex/startpointInRangeIndex.d.ts +1 -1
- package/dist/intervalIndex/startpointInRangeIndex.d.ts.map +1 -1
- package/dist/intervalIndex/startpointInRangeIndex.js +3 -3
- package/dist/intervalIndex/startpointInRangeIndex.js.map +1 -1
- package/dist/intervalTree.d.ts +1 -1
- package/dist/intervalTree.d.ts.map +1 -1
- package/dist/intervalTree.js +2 -2
- package/dist/intervalTree.js.map +1 -1
- package/dist/intervals/interval.d.ts +1 -1
- package/dist/intervals/interval.d.ts.map +1 -1
- package/dist/intervals/interval.js +10 -10
- package/dist/intervals/interval.js.map +1 -1
- package/dist/intervals/intervalUtils.d.ts +1 -1
- package/dist/intervals/intervalUtils.d.ts.map +1 -1
- package/dist/intervals/intervalUtils.js +5 -5
- package/dist/intervals/intervalUtils.js.map +1 -1
- package/dist/intervals/sequenceInterval.d.ts +1 -1
- package/dist/intervals/sequenceInterval.d.ts.map +1 -1
- package/dist/intervals/sequenceInterval.js +34 -34
- package/dist/intervals/sequenceInterval.js.map +1 -1
- package/dist/legacy.d.ts +61 -0
- package/dist/packageVersion.d.ts +1 -1
- package/dist/packageVersion.js +1 -1
- package/dist/packageVersion.js.map +1 -1
- package/dist/public.d.ts +12 -0
- package/dist/revertibles.d.ts +2 -2
- package/dist/revertibles.d.ts.map +1 -1
- package/dist/revertibles.js +34 -34
- package/dist/revertibles.js.map +1 -1
- package/dist/sequence.d.ts +7 -6
- package/dist/sequence.d.ts.map +1 -1
- package/dist/sequence.js +34 -34
- package/dist/sequence.js.map +1 -1
- package/dist/sequenceDeltaEvent.d.ts +1 -1
- package/dist/sequenceDeltaEvent.d.ts.map +1 -1
- package/dist/sequenceDeltaEvent.js +4 -4
- package/dist/sequenceDeltaEvent.js.map +1 -1
- package/dist/sequenceFactory.d.ts +1 -1
- package/dist/sequenceFactory.d.ts.map +1 -1
- package/dist/sequenceFactory.js +3 -3
- package/dist/sequenceFactory.js.map +1 -1
- package/dist/sharedIntervalCollection.d.ts +4 -3
- package/dist/sharedIntervalCollection.d.ts.map +1 -1
- package/dist/sharedIntervalCollection.js +5 -5
- package/dist/sharedIntervalCollection.js.map +1 -1
- package/dist/sharedSequence.d.ts +3 -2
- package/dist/sharedSequence.d.ts.map +1 -1
- package/dist/sharedSequence.js +4 -4
- package/dist/sharedSequence.js.map +1 -1
- package/dist/sharedString.d.ts +2 -2
- package/dist/sharedString.d.ts.map +1 -1
- package/dist/sharedString.js +9 -9
- package/dist/sharedString.js.map +1 -1
- package/internal.d.ts +11 -0
- package/legacy.d.ts +11 -0
- package/lib/{localValues.d.ts → IntervalCollectionValues.d.ts} +13 -12
- package/lib/IntervalCollectionValues.d.ts.map +1 -0
- package/lib/{localValues.js → IntervalCollectionValues.js} +3 -3
- package/lib/IntervalCollectionValues.js.map +1 -0
- package/lib/beta.d.ts +12 -0
- package/lib/index.d.ts +2 -2
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -1
- package/lib/index.js.map +1 -1
- package/lib/intervalCollection.d.ts +10 -10
- package/lib/intervalCollection.d.ts.map +1 -1
- package/lib/intervalCollection.js +8 -4
- package/lib/intervalCollection.js.map +1 -1
- package/lib/{defaultMap.d.ts → intervalCollectionMap.d.ts} +11 -44
- package/lib/intervalCollectionMap.d.ts.map +1 -0
- package/lib/{defaultMap.js → intervalCollectionMap.js} +8 -63
- package/lib/intervalCollectionMap.js.map +1 -0
- package/lib/{defaultMapInterfaces.d.ts → intervalCollectionMapInterfaces.d.ts} +17 -16
- package/lib/intervalCollectionMapInterfaces.d.ts.map +1 -0
- package/lib/{defaultMapInterfaces.js → intervalCollectionMapInterfaces.js} +1 -1
- package/lib/intervalCollectionMapInterfaces.js.map +1 -0
- package/lib/intervalIndex/endpointInRangeIndex.d.ts +1 -1
- package/lib/intervalIndex/endpointInRangeIndex.d.ts.map +1 -1
- package/lib/intervalIndex/endpointInRangeIndex.js +1 -1
- package/lib/intervalIndex/endpointInRangeIndex.js.map +1 -1
- package/lib/intervalIndex/endpointIndex.d.ts +1 -1
- package/lib/intervalIndex/endpointIndex.d.ts.map +1 -1
- package/lib/intervalIndex/endpointIndex.js +1 -1
- package/lib/intervalIndex/endpointIndex.js.map +1 -1
- package/lib/intervalIndex/idIntervalIndex.d.ts.map +1 -1
- package/lib/intervalIndex/idIntervalIndex.js +1 -1
- package/lib/intervalIndex/idIntervalIndex.js.map +1 -1
- package/lib/intervalIndex/overlappingIntervalsIndex.d.ts +3 -3
- package/lib/intervalIndex/overlappingIntervalsIndex.d.ts.map +1 -1
- package/lib/intervalIndex/overlappingIntervalsIndex.js +2 -3
- package/lib/intervalIndex/overlappingIntervalsIndex.js.map +1 -1
- package/lib/intervalIndex/overlappingSequenceIntervalsIndex.d.ts.map +1 -1
- package/lib/intervalIndex/overlappingSequenceIntervalsIndex.js +2 -2
- package/lib/intervalIndex/overlappingSequenceIntervalsIndex.js.map +1 -1
- package/lib/intervalIndex/sequenceIntervalIndexes.d.ts +1 -1
- package/lib/intervalIndex/sequenceIntervalIndexes.d.ts.map +1 -1
- package/lib/intervalIndex/sequenceIntervalIndexes.js.map +1 -1
- package/lib/intervalIndex/startpointInRangeIndex.d.ts +1 -1
- package/lib/intervalIndex/startpointInRangeIndex.d.ts.map +1 -1
- package/lib/intervalIndex/startpointInRangeIndex.js +1 -1
- package/lib/intervalIndex/startpointInRangeIndex.js.map +1 -1
- package/lib/intervalTree.d.ts +1 -1
- package/lib/intervalTree.d.ts.map +1 -1
- package/lib/intervalTree.js +1 -1
- package/lib/intervalTree.js.map +1 -1
- package/lib/intervals/interval.d.ts +1 -1
- package/lib/intervals/interval.d.ts.map +1 -1
- package/lib/intervals/interval.js +3 -3
- package/lib/intervals/interval.js.map +1 -1
- package/lib/intervals/intervalUtils.d.ts +1 -1
- package/lib/intervals/intervalUtils.d.ts.map +1 -1
- package/lib/intervals/intervalUtils.js +1 -1
- package/lib/intervals/intervalUtils.js.map +1 -1
- package/lib/intervals/sequenceInterval.d.ts +1 -1
- package/lib/intervals/sequenceInterval.d.ts.map +1 -1
- package/lib/intervals/sequenceInterval.js +3 -3
- package/lib/intervals/sequenceInterval.js.map +1 -1
- package/lib/legacy.d.ts +61 -0
- package/lib/packageVersion.d.ts +1 -1
- package/lib/packageVersion.js +1 -1
- package/lib/packageVersion.js.map +1 -1
- package/lib/public.d.ts +12 -0
- package/lib/revertibles.d.ts +2 -2
- package/lib/revertibles.d.ts.map +1 -1
- package/lib/revertibles.js +3 -4
- package/lib/revertibles.js.map +1 -1
- package/lib/sequence.d.ts +7 -6
- package/lib/sequence.d.ts.map +1 -1
- package/lib/sequence.js +11 -12
- package/lib/sequence.js.map +1 -1
- package/lib/sequenceDeltaEvent.d.ts +1 -1
- package/lib/sequenceDeltaEvent.d.ts.map +1 -1
- package/lib/sequenceDeltaEvent.js +3 -4
- package/lib/sequenceDeltaEvent.js.map +1 -1
- package/lib/sequenceFactory.d.ts +1 -1
- package/lib/sequenceFactory.d.ts.map +1 -1
- package/lib/sequenceFactory.js +1 -1
- package/lib/sequenceFactory.js.map +1 -1
- package/lib/sharedIntervalCollection.d.ts +4 -3
- package/lib/sharedIntervalCollection.d.ts.map +1 -1
- package/lib/sharedIntervalCollection.js +4 -4
- package/lib/sharedIntervalCollection.js.map +1 -1
- package/lib/sharedSequence.d.ts +3 -2
- package/lib/sharedSequence.d.ts.map +1 -1
- package/lib/sharedSequence.js +2 -2
- package/lib/sharedSequence.js.map +1 -1
- package/lib/sharedString.d.ts +2 -2
- package/lib/sharedString.d.ts.map +1 -1
- package/lib/sharedString.js +1 -1
- package/lib/sharedString.js.map +1 -1
- package/package.json +41 -58
- package/src/{localValues.ts → IntervalCollectionValues.ts} +26 -18
- package/src/index.ts +2 -2
- package/src/intervalCollection.ts +46 -47
- package/src/{defaultMap.ts → intervalCollectionMap.ts} +42 -105
- package/src/{defaultMapInterfaces.ts → intervalCollectionMapInterfaces.ts} +26 -16
- package/src/intervalIndex/endpointInRangeIndex.ts +4 -1
- package/src/intervalIndex/endpointIndex.ts +4 -1
- package/src/intervalIndex/idIntervalIndex.ts +4 -2
- package/src/intervalIndex/overlappingIntervalsIndex.ts +8 -5
- package/src/intervalIndex/overlappingSequenceIntervalsIndex.ts +6 -3
- package/src/intervalIndex/sequenceIntervalIndexes.ts +3 -1
- package/src/intervalIndex/startpointInRangeIndex.ts +4 -1
- package/src/intervalTree.ts +4 -3
- package/src/intervals/interval.ts +6 -3
- package/src/intervals/intervalUtils.ts +4 -2
- package/src/intervals/sequenceInterval.ts +5 -3
- package/src/packageVersion.ts +1 -1
- package/src/revertibles.ts +10 -10
- package/src/sequence.ts +24 -31
- package/src/sequenceDeltaEvent.ts +3 -4
- package/src/sequenceFactory.ts +4 -3
- package/src/sharedIntervalCollection.ts +12 -18
- package/src/sharedSequence.ts +9 -6
- package/src/sharedString.ts +4 -3
- package/api-extractor-cjs.json +0 -8
- package/dist/defaultMap.d.ts.map +0 -1
- package/dist/defaultMap.js.map +0 -1
- package/dist/defaultMapInterfaces.d.ts.map +0 -1
- package/dist/defaultMapInterfaces.js.map +0 -1
- package/dist/localValues.d.ts.map +0 -1
- package/dist/localValues.js.map +0 -1
- package/dist/sequence-alpha.d.ts +0 -1432
- package/dist/sequence-beta.d.ts +0 -246
- package/dist/sequence-public.d.ts +0 -246
- package/dist/sequence-untrimmed.d.ts +0 -1820
- package/lib/defaultMap.d.ts.map +0 -1
- package/lib/defaultMap.js.map +0 -1
- package/lib/defaultMapInterfaces.d.ts.map +0 -1
- package/lib/defaultMapInterfaces.js.map +0 -1
- package/lib/localValues.d.ts.map +0 -1
- package/lib/localValues.js.map +0 -1
- package/lib/sequence-alpha.d.ts +0 -1432
- package/lib/sequence-beta.d.ts +0 -246
- package/lib/sequence-public.d.ts +0 -246
- package/lib/sequence-untrimmed.d.ts +0 -1820
- package/lib/test/collections.intervalTree.js +0 -73
- package/lib/test/collections.intervalTree.js.map +0 -1
- package/lib/test/createSnapshotFiles.js +0 -15
- package/lib/test/createSnapshotFiles.js.map +0 -1
- package/lib/test/dirname.cjs +0 -16
- package/lib/test/dirname.cjs.map +0 -1
- package/lib/test/endpointInRangeIndex.spec.js +0 -182
- package/lib/test/endpointInRangeIndex.spec.js.map +0 -1
- package/lib/test/fuzz/fuzzUtils.js +0 -250
- package/lib/test/fuzz/fuzzUtils.js.map +0 -1
- package/lib/test/fuzz/intervalCollection.fuzz.spec.js +0 -200
- package/lib/test/fuzz/intervalCollection.fuzz.spec.js.map +0 -1
- package/lib/test/fuzz/intervalRevertibles.fuzz.spec.js +0 -129
- package/lib/test/fuzz/intervalRevertibles.fuzz.spec.js.map +0 -1
- package/lib/test/fuzz/sharedString.fuzz.spec.js +0 -91
- package/lib/test/fuzz/sharedString.fuzz.spec.js.map +0 -1
- package/lib/test/generateSharedStrings.js +0 -138
- package/lib/test/generateSharedStrings.js.map +0 -1
- package/lib/test/intervalCollection.detached.spec.js +0 -126
- package/lib/test/intervalCollection.detached.spec.js.map +0 -1
- package/lib/test/intervalCollection.events.spec.js +0 -491
- package/lib/test/intervalCollection.events.spec.js.map +0 -1
- package/lib/test/intervalCollection.perf.spec.js +0 -88
- package/lib/test/intervalCollection.perf.spec.js.map +0 -1
- package/lib/test/intervalCollection.snapshot.spec.js +0 -171
- package/lib/test/intervalCollection.snapshot.spec.js.map +0 -1
- package/lib/test/intervalCollection.spec.js +0 -1660
- package/lib/test/intervalCollection.spec.js.map +0 -1
- package/lib/test/intervalIndexTestUtils.js +0 -49
- package/lib/test/intervalIndexTestUtils.js.map +0 -1
- package/lib/test/intervalRebasing.spec.js +0 -589
- package/lib/test/intervalRebasing.spec.js.map +0 -1
- package/lib/test/intervalStashedOps.spec.js +0 -142
- package/lib/test/intervalStashedOps.spec.js.map +0 -1
- package/lib/test/intervalTestUtils.js +0 -81
- package/lib/test/intervalTestUtils.js.map +0 -1
- package/lib/test/marshalling.spec.js +0 -55
- package/lib/test/marshalling.spec.js.map +0 -1
- package/lib/test/memory/sharedSequence.spec.js +0 -82
- package/lib/test/memory/sharedSequence.spec.js.map +0 -1
- package/lib/test/memory/sharedString.spec.js +0 -134
- package/lib/test/memory/sharedString.spec.js.map +0 -1
- package/lib/test/overlappingSequenceIntervalsIndex.spec.js +0 -348
- package/lib/test/overlappingSequenceIntervalsIndex.spec.js.map +0 -1
- package/lib/test/partialLoad.spec.js +0 -211
- package/lib/test/partialLoad.spec.js.map +0 -1
- package/lib/test/rebasing.spec.js +0 -81
- package/lib/test/rebasing.spec.js.map +0 -1
- package/lib/test/reentrancy.spec.js +0 -174
- package/lib/test/reentrancy.spec.js.map +0 -1
- package/lib/test/revertibles.spec.js +0 -971
- package/lib/test/revertibles.spec.js.map +0 -1
- package/lib/test/sequenceDeltaEvent.spec.js +0 -2144
- package/lib/test/sequenceDeltaEvent.spec.js.map +0 -1
- package/lib/test/sharedIntervalCollection.spec.js +0 -159
- package/lib/test/sharedIntervalCollection.spec.js.map +0 -1
- package/lib/test/sharedString.spec.js +0 -532
- package/lib/test/sharedString.spec.js.map +0 -1
- package/lib/test/snapshotEmptyProps.spec.js +0 -45
- package/lib/test/snapshotEmptyProps.spec.js.map +0 -1
- package/lib/test/snapshotVersion.spec.js +0 -149
- package/lib/test/snapshotVersion.spec.js.map +0 -1
- package/lib/test/startpointInRangeIndex.spec.js +0 -182
- package/lib/test/startpointInRangeIndex.spec.js.map +0 -1
- package/lib/test/subSequence.spec.js +0 -92
- package/lib/test/subSequence.spec.js.map +0 -1
- package/lib/test/types/validateSequencePrevious.generated.js +0 -162
- package/lib/test/types/validateSequencePrevious.generated.js.map +0 -1
- package/lib/test/v1IntervalCollectionHelpers.js +0 -93
- package/lib/test/v1IntervalCollectionHelpers.js.map +0 -1
- /package/{dist → lib}/tsdoc-metadata.json +0 -0
|
@@ -1,200 +0,0 @@
|
|
|
1
|
-
/*!
|
|
2
|
-
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
-
* Licensed under the MIT License.
|
|
4
|
-
*/
|
|
5
|
-
import { strict as assert } from "assert";
|
|
6
|
-
import { createWeightedAsyncGenerator as createWeightedGenerator, takeAsync as take, } from "@fluid-private/stochastic-test-utils";
|
|
7
|
-
import { createDDSFuzzSuite } from "@fluid-private/test-dds-utils";
|
|
8
|
-
import { FlushMode } from "@fluidframework/runtime-definitions";
|
|
9
|
-
import { Side } from "../../intervalCollection.js";
|
|
10
|
-
import { defaultIntervalOperationGenerationConfig, createSharedStringGeneratorOperations, baseModel, defaultFuzzOptions, } from "./fuzzUtils.js";
|
|
11
|
-
export function makeOperationGenerator(optionsParam, alwaysLeaveChar = false) {
|
|
12
|
-
const { startPosition, addText, obliterateRange, removeRange, removeRangeLeaveChar, lengthSatisfies, hasNonzeroLength, isShorterThanMaxLength, } = createSharedStringGeneratorOperations(optionsParam);
|
|
13
|
-
const options = { ...defaultIntervalOperationGenerationConfig, ...(optionsParam ?? {}) };
|
|
14
|
-
function isNonEmpty(collection) {
|
|
15
|
-
for (const _ of collection) {
|
|
16
|
-
return true;
|
|
17
|
-
}
|
|
18
|
-
return false;
|
|
19
|
-
}
|
|
20
|
-
function inclusiveRange(state) {
|
|
21
|
-
const start = startPosition(state);
|
|
22
|
-
const end = state.random.integer(start, Math.max(start, state.client.channel.getLength() - 1));
|
|
23
|
-
return { start, end };
|
|
24
|
-
}
|
|
25
|
-
function inclusiveRangeWithUndefined(state) {
|
|
26
|
-
return state.random.bool() ? inclusiveRange(state) : { start: undefined, end: undefined };
|
|
27
|
-
}
|
|
28
|
-
function propertySet(state) {
|
|
29
|
-
const propNamesShuffled = [...options.propertyNamePool];
|
|
30
|
-
state.random.shuffle(propNamesShuffled);
|
|
31
|
-
const propsToChange = propNamesShuffled.slice(0, state.random.integer(1, propNamesShuffled.length));
|
|
32
|
-
const propSet = {};
|
|
33
|
-
for (const name of propsToChange) {
|
|
34
|
-
propSet[name] = state.random.string(5);
|
|
35
|
-
}
|
|
36
|
-
return propSet;
|
|
37
|
-
}
|
|
38
|
-
function propertySetWithUndefined(state) {
|
|
39
|
-
return state.random.bool() ? propertySet(state) : undefined;
|
|
40
|
-
}
|
|
41
|
-
function nonEmptyIntervalCollection({ client, random }) {
|
|
42
|
-
const nonEmptyLabels = Array.from(client.channel.getIntervalCollectionLabels()).filter((label) => {
|
|
43
|
-
const collection = client.channel.getIntervalCollection(label);
|
|
44
|
-
return isNonEmpty(collection);
|
|
45
|
-
});
|
|
46
|
-
return random.pick(nonEmptyLabels);
|
|
47
|
-
}
|
|
48
|
-
function interval(state) {
|
|
49
|
-
const collectionName = nonEmptyIntervalCollection(state);
|
|
50
|
-
const intervals = Array.from(state.client.channel.getIntervalCollection(collectionName));
|
|
51
|
-
const id = state.random.pick(intervals)?.getIntervalId();
|
|
52
|
-
assert(id);
|
|
53
|
-
return {
|
|
54
|
-
id,
|
|
55
|
-
collectionName,
|
|
56
|
-
};
|
|
57
|
-
}
|
|
58
|
-
async function addInterval(state) {
|
|
59
|
-
return {
|
|
60
|
-
type: "addInterval",
|
|
61
|
-
...inclusiveRange(state),
|
|
62
|
-
collectionName: state.random.pick(options.intervalCollectionNamePool),
|
|
63
|
-
id: state.random.uuid4(),
|
|
64
|
-
startSide: state.random.pick([Side.Before, Side.After]),
|
|
65
|
-
endSide: state.random.pick([Side.Before, Side.After]),
|
|
66
|
-
};
|
|
67
|
-
}
|
|
68
|
-
async function deleteInterval(state) {
|
|
69
|
-
return {
|
|
70
|
-
type: "deleteInterval",
|
|
71
|
-
...interval(state),
|
|
72
|
-
};
|
|
73
|
-
}
|
|
74
|
-
async function changeInterval(state) {
|
|
75
|
-
const { start, end } = inclusiveRangeWithUndefined(state);
|
|
76
|
-
const properties = propertySetWithUndefined(state);
|
|
77
|
-
return {
|
|
78
|
-
type: "changeInterval",
|
|
79
|
-
start,
|
|
80
|
-
end,
|
|
81
|
-
startSide: state.random.pick([Side.Before, Side.After]),
|
|
82
|
-
endSide: state.random.pick([Side.Before, Side.After]),
|
|
83
|
-
properties,
|
|
84
|
-
...interval(state),
|
|
85
|
-
};
|
|
86
|
-
}
|
|
87
|
-
const hasAnInterval = ({ client }) => Array.from(client.channel.getIntervalCollectionLabels()).some((label) => {
|
|
88
|
-
const collection = client.channel.getIntervalCollection(label);
|
|
89
|
-
return isNonEmpty(collection);
|
|
90
|
-
});
|
|
91
|
-
const hasNotTooManyIntervals = ({ client }) => {
|
|
92
|
-
let intervalCount = 0;
|
|
93
|
-
for (const label of client.channel.getIntervalCollectionLabels()) {
|
|
94
|
-
for (const _ of client.channel.getIntervalCollection(label)) {
|
|
95
|
-
intervalCount++;
|
|
96
|
-
if (intervalCount >= options.maxIntervals) {
|
|
97
|
-
return false;
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
}
|
|
101
|
-
return true;
|
|
102
|
-
};
|
|
103
|
-
const all = (...clauses) => (t) => clauses.reduce((prev, cond) => prev && cond(t), true);
|
|
104
|
-
const usableWeights = optionsParam?.weights ?? defaultIntervalOperationGenerationConfig.weights;
|
|
105
|
-
return createWeightedGenerator([
|
|
106
|
-
[addText, usableWeights.addText, isShorterThanMaxLength],
|
|
107
|
-
[
|
|
108
|
-
alwaysLeaveChar ? removeRangeLeaveChar : removeRange,
|
|
109
|
-
usableWeights.removeRange,
|
|
110
|
-
alwaysLeaveChar
|
|
111
|
-
? lengthSatisfies((length) => {
|
|
112
|
-
return length > 1;
|
|
113
|
-
})
|
|
114
|
-
: hasNonzeroLength,
|
|
115
|
-
],
|
|
116
|
-
[obliterateRange, usableWeights.obliterateRange, hasNonzeroLength],
|
|
117
|
-
[addInterval, usableWeights.addInterval, all(hasNotTooManyIntervals, hasNonzeroLength)],
|
|
118
|
-
[deleteInterval, usableWeights.deleteInterval, hasAnInterval],
|
|
119
|
-
[changeInterval, usableWeights.changeInterval, all(hasAnInterval, hasNonzeroLength)],
|
|
120
|
-
]);
|
|
121
|
-
}
|
|
122
|
-
const baseIntervalModel = {
|
|
123
|
-
...baseModel,
|
|
124
|
-
generatorFactory: () => take(100, makeOperationGenerator(defaultIntervalOperationGenerationConfig)),
|
|
125
|
-
};
|
|
126
|
-
describe("IntervalCollection fuzz testing", () => {
|
|
127
|
-
const model = {
|
|
128
|
-
...baseIntervalModel,
|
|
129
|
-
workloadName: "default interval collection",
|
|
130
|
-
};
|
|
131
|
-
createDDSFuzzSuite(model, {
|
|
132
|
-
...defaultFuzzOptions,
|
|
133
|
-
skip: [68],
|
|
134
|
-
// Note: there are some known eventual consistency issues which the tests don't currently reproduce.
|
|
135
|
-
// Search this package for AB#6552 (or look at that work item) for a skipped test and further details.
|
|
136
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
137
|
-
// replay: 0,
|
|
138
|
-
});
|
|
139
|
-
});
|
|
140
|
-
describe("IntervalCollection with stashing", () => {
|
|
141
|
-
const model = {
|
|
142
|
-
...baseIntervalModel,
|
|
143
|
-
workloadName: "default interval collection with stashing",
|
|
144
|
-
};
|
|
145
|
-
createDDSFuzzSuite(model, {
|
|
146
|
-
...defaultFuzzOptions,
|
|
147
|
-
clientJoinOptions: {
|
|
148
|
-
clientAddProbability: 0.1,
|
|
149
|
-
maxNumberOfClients: Number.MAX_SAFE_INTEGER,
|
|
150
|
-
stashableClientProbability: 0.2,
|
|
151
|
-
},
|
|
152
|
-
// AB#7220
|
|
153
|
-
skip: [68],
|
|
154
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
155
|
-
// replay: 0,
|
|
156
|
-
});
|
|
157
|
-
});
|
|
158
|
-
describe("IntervalCollection no reconnect fuzz testing", () => {
|
|
159
|
-
const noReconnectModel = {
|
|
160
|
-
...baseIntervalModel,
|
|
161
|
-
workloadName: "interval collection without reconnects",
|
|
162
|
-
};
|
|
163
|
-
const options = {
|
|
164
|
-
...defaultFuzzOptions,
|
|
165
|
-
skip: [68],
|
|
166
|
-
reconnectProbability: 0.0,
|
|
167
|
-
clientJoinOptions: {
|
|
168
|
-
maxNumberOfClients: 3,
|
|
169
|
-
clientAddProbability: 0.0,
|
|
170
|
-
},
|
|
171
|
-
};
|
|
172
|
-
createDDSFuzzSuite(noReconnectModel, {
|
|
173
|
-
...options,
|
|
174
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
175
|
-
// replay: 0,
|
|
176
|
-
});
|
|
177
|
-
});
|
|
178
|
-
describe("IntervalCollection fuzz testing with rebased batches", () => {
|
|
179
|
-
const noReconnectWithRebaseModel = {
|
|
180
|
-
...baseIntervalModel,
|
|
181
|
-
workloadName: "interval collection with rebasing",
|
|
182
|
-
};
|
|
183
|
-
createDDSFuzzSuite(noReconnectWithRebaseModel, {
|
|
184
|
-
...defaultFuzzOptions,
|
|
185
|
-
// todo AB#5603
|
|
186
|
-
skip: [97],
|
|
187
|
-
reconnectProbability: 0.0,
|
|
188
|
-
clientJoinOptions: {
|
|
189
|
-
maxNumberOfClients: 3,
|
|
190
|
-
clientAddProbability: 0.0,
|
|
191
|
-
},
|
|
192
|
-
rebaseProbability: 0.2,
|
|
193
|
-
containerRuntimeOptions: {
|
|
194
|
-
flushMode: FlushMode.TurnBased,
|
|
195
|
-
enableGroupedBatching: true,
|
|
196
|
-
},
|
|
197
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
198
|
-
});
|
|
199
|
-
});
|
|
200
|
-
//# sourceMappingURL=intervalCollection.fuzz.spec.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"intervalCollection.fuzz.spec.js","sourceRoot":"","sources":["../../../src/test/fuzz/intervalCollection.fuzz.spec.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { strict as assert } from \"assert\";\nimport {\n\tAcceptanceCondition,\n\tcreateWeightedAsyncGenerator as createWeightedGenerator,\n\tAsyncGenerator as Generator,\n\ttakeAsync as take,\n} from \"@fluid-private/stochastic-test-utils\";\nimport { createDDSFuzzSuite } from \"@fluid-private/test-dds-utils\";\nimport { PropertySet } from \"@fluidframework/merge-tree\";\nimport { FlushMode } from \"@fluidframework/runtime-definitions\";\nimport { IIntervalCollection, Side } from \"../../intervalCollection.js\";\nimport { SequenceInterval } from \"../../intervals/index.js\";\nimport {\n\tOperation,\n\tRangeSpec,\n\tAddInterval,\n\tDeleteInterval,\n\tChangeInterval,\n\tFuzzTestState,\n\tIntervalOperationGenerationConfig,\n\tdefaultIntervalOperationGenerationConfig,\n\tcreateSharedStringGeneratorOperations,\n\tbaseModel,\n\tdefaultFuzzOptions,\n} from \"./fuzzUtils.js\";\n\ntype ClientOpState = FuzzTestState;\nexport function makeOperationGenerator(\n\toptionsParam?: IntervalOperationGenerationConfig,\n\talwaysLeaveChar: boolean = false,\n): Generator<Operation, ClientOpState> {\n\tconst {\n\t\tstartPosition,\n\t\taddText,\n\t\tobliterateRange,\n\t\tremoveRange,\n\t\tremoveRangeLeaveChar,\n\t\tlengthSatisfies,\n\t\thasNonzeroLength,\n\t\tisShorterThanMaxLength,\n\t} = createSharedStringGeneratorOperations(optionsParam);\n\n\tconst options = { ...defaultIntervalOperationGenerationConfig, ...(optionsParam ?? {}) };\n\n\tfunction isNonEmpty(collection: IIntervalCollection<SequenceInterval>): boolean {\n\t\tfor (const _ of collection) {\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t}\n\n\tfunction inclusiveRange(state: ClientOpState): RangeSpec {\n\t\tconst start = startPosition(state);\n\t\tconst end = state.random.integer(\n\t\t\tstart,\n\t\t\tMath.max(start, state.client.channel.getLength() - 1),\n\t\t);\n\t\treturn { start, end };\n\t}\n\n\tfunction inclusiveRangeWithUndefined(\n\t\tstate: ClientOpState,\n\t): RangeSpec | { start: undefined; end: undefined } {\n\t\treturn state.random.bool() ? inclusiveRange(state) : { start: undefined, end: undefined };\n\t}\n\n\tfunction propertySet(state: ClientOpState): PropertySet {\n\t\tconst propNamesShuffled = [...options.propertyNamePool];\n\t\tstate.random.shuffle(propNamesShuffled);\n\t\tconst propsToChange = propNamesShuffled.slice(\n\t\t\t0,\n\t\t\tstate.random.integer(1, propNamesShuffled.length),\n\t\t);\n\t\tconst propSet: PropertySet = {};\n\t\tfor (const name of propsToChange) {\n\t\t\tpropSet[name] = state.random.string(5);\n\t\t}\n\t\treturn propSet;\n\t}\n\n\tfunction propertySetWithUndefined(state: ClientOpState): PropertySet | undefined {\n\t\treturn state.random.bool() ? propertySet(state) : undefined;\n\t}\n\n\tfunction nonEmptyIntervalCollection({ client, random }: ClientOpState): string {\n\t\tconst nonEmptyLabels = Array.from(client.channel.getIntervalCollectionLabels()).filter(\n\t\t\t(label) => {\n\t\t\t\tconst collection = client.channel.getIntervalCollection(label);\n\t\t\t\treturn isNonEmpty(collection);\n\t\t\t},\n\t\t);\n\t\treturn random.pick(nonEmptyLabels);\n\t}\n\n\tfunction interval(state: ClientOpState): { collectionName: string; id: string } {\n\t\tconst collectionName = nonEmptyIntervalCollection(state);\n\t\tconst intervals = Array.from(state.client.channel.getIntervalCollection(collectionName));\n\t\tconst id = state.random.pick(intervals)?.getIntervalId();\n\t\tassert(id);\n\n\t\treturn {\n\t\t\tid,\n\t\t\tcollectionName,\n\t\t};\n\t}\n\n\tasync function addInterval(state: ClientOpState): Promise<AddInterval> {\n\t\treturn {\n\t\t\ttype: \"addInterval\",\n\t\t\t...inclusiveRange(state),\n\t\t\tcollectionName: state.random.pick(options.intervalCollectionNamePool),\n\t\t\tid: state.random.uuid4(),\n\t\t\tstartSide: state.random.pick([Side.Before, Side.After]),\n\t\t\tendSide: state.random.pick([Side.Before, Side.After]),\n\t\t};\n\t}\n\n\tasync function deleteInterval(state: ClientOpState): Promise<DeleteInterval> {\n\t\treturn {\n\t\t\ttype: \"deleteInterval\",\n\t\t\t...interval(state),\n\t\t};\n\t}\n\n\tasync function changeInterval(state: ClientOpState): Promise<ChangeInterval> {\n\t\tconst { start, end } = inclusiveRangeWithUndefined(state);\n\t\tconst properties = propertySetWithUndefined(state);\n\t\treturn {\n\t\t\ttype: \"changeInterval\",\n\t\t\tstart,\n\t\t\tend,\n\t\t\tstartSide: state.random.pick([Side.Before, Side.After]),\n\t\t\tendSide: state.random.pick([Side.Before, Side.After]),\n\t\t\tproperties,\n\t\t\t...interval(state),\n\t\t};\n\t}\n\n\tconst hasAnInterval = ({ client }: ClientOpState): boolean =>\n\t\tArray.from(client.channel.getIntervalCollectionLabels()).some((label) => {\n\t\t\tconst collection = client.channel.getIntervalCollection(label);\n\t\t\treturn isNonEmpty(collection);\n\t\t});\n\n\tconst hasNotTooManyIntervals: AcceptanceCondition<ClientOpState> = ({ client }) => {\n\t\tlet intervalCount = 0;\n\t\tfor (const label of client.channel.getIntervalCollectionLabels()) {\n\t\t\tfor (const _ of client.channel.getIntervalCollection(label)) {\n\t\t\t\tintervalCount++;\n\t\t\t\tif (intervalCount >= options.maxIntervals) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t};\n\n\tconst all =\n\t\t<T>(...clauses: AcceptanceCondition<T>[]): AcceptanceCondition<T> =>\n\t\t(t: T) =>\n\t\t\tclauses.reduce<boolean>((prev, cond) => prev && cond(t), true);\n\tconst usableWeights = optionsParam?.weights ?? defaultIntervalOperationGenerationConfig.weights;\n\treturn createWeightedGenerator<Operation, ClientOpState>([\n\t\t[addText, usableWeights.addText, isShorterThanMaxLength],\n\t\t[\n\t\t\talwaysLeaveChar ? removeRangeLeaveChar : removeRange,\n\t\t\tusableWeights.removeRange,\n\t\t\talwaysLeaveChar\n\t\t\t\t? lengthSatisfies((length) => {\n\t\t\t\t\t\treturn length > 1;\n\t\t\t\t })\n\t\t\t\t: hasNonzeroLength,\n\t\t],\n\t\t[obliterateRange, usableWeights.obliterateRange, hasNonzeroLength],\n\t\t[addInterval, usableWeights.addInterval, all(hasNotTooManyIntervals, hasNonzeroLength)],\n\t\t[deleteInterval, usableWeights.deleteInterval, hasAnInterval],\n\t\t[changeInterval, usableWeights.changeInterval, all(hasAnInterval, hasNonzeroLength)],\n\t]);\n}\n\nconst baseIntervalModel = {\n\t...baseModel,\n\tgeneratorFactory: () =>\n\t\ttake(100, makeOperationGenerator(defaultIntervalOperationGenerationConfig)),\n};\n\ndescribe(\"IntervalCollection fuzz testing\", () => {\n\tconst model = {\n\t\t...baseIntervalModel,\n\t\tworkloadName: \"default interval collection\",\n\t};\n\n\tcreateDDSFuzzSuite(model, {\n\t\t...defaultFuzzOptions,\n\t\tskip: [68],\n\t\t// Note: there are some known eventual consistency issues which the tests don't currently reproduce.\n\t\t// Search this package for AB#6552 (or look at that work item) for a skipped test and further details.\n\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t// replay: 0,\n\t});\n});\n\ndescribe(\"IntervalCollection with stashing\", () => {\n\tconst model = {\n\t\t...baseIntervalModel,\n\t\tworkloadName: \"default interval collection with stashing\",\n\t};\n\n\tcreateDDSFuzzSuite(model, {\n\t\t...defaultFuzzOptions,\n\t\tclientJoinOptions: {\n\t\t\tclientAddProbability: 0.1,\n\t\t\tmaxNumberOfClients: Number.MAX_SAFE_INTEGER,\n\t\t\tstashableClientProbability: 0.2,\n\t\t},\n\t\t// AB#7220\n\t\tskip: [68],\n\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t// replay: 0,\n\t});\n});\n\ndescribe(\"IntervalCollection no reconnect fuzz testing\", () => {\n\tconst noReconnectModel = {\n\t\t...baseIntervalModel,\n\t\tworkloadName: \"interval collection without reconnects\",\n\t};\n\n\tconst options = {\n\t\t...defaultFuzzOptions,\n\t\tskip: [68],\n\t\treconnectProbability: 0.0,\n\t\tclientJoinOptions: {\n\t\t\tmaxNumberOfClients: 3,\n\t\t\tclientAddProbability: 0.0,\n\t\t},\n\t};\n\n\tcreateDDSFuzzSuite(noReconnectModel, {\n\t\t...options,\n\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t// replay: 0,\n\t});\n});\n\ndescribe(\"IntervalCollection fuzz testing with rebased batches\", () => {\n\tconst noReconnectWithRebaseModel = {\n\t\t...baseIntervalModel,\n\t\tworkloadName: \"interval collection with rebasing\",\n\t};\n\n\tcreateDDSFuzzSuite(noReconnectWithRebaseModel, {\n\t\t...defaultFuzzOptions,\n\t\t// todo AB#5603\n\t\tskip: [97],\n\t\treconnectProbability: 0.0,\n\t\tclientJoinOptions: {\n\t\t\tmaxNumberOfClients: 3,\n\t\t\tclientAddProbability: 0.0,\n\t\t},\n\t\trebaseProbability: 0.2,\n\t\tcontainerRuntimeOptions: {\n\t\t\tflushMode: FlushMode.TurnBased,\n\t\t\tenableGroupedBatching: true,\n\t\t},\n\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t});\n});\n"]}
|
|
@@ -1,129 +0,0 @@
|
|
|
1
|
-
/*!
|
|
2
|
-
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
-
* Licensed under the MIT License.
|
|
4
|
-
*/
|
|
5
|
-
import { strict as assert } from "assert";
|
|
6
|
-
import { createWeightedAsyncGenerator as createWeightedGenerator, takeAsync as take, } from "@fluid-private/stochastic-test-utils";
|
|
7
|
-
import { createDDSFuzzSuite, } from "@fluid-private/test-dds-utils";
|
|
8
|
-
import { TypedEventEmitter } from "@fluid-internal/client-utils";
|
|
9
|
-
import { FlushMode } from "@fluidframework/runtime-definitions";
|
|
10
|
-
import { appendAddIntervalToRevertibles, appendChangeIntervalToRevertibles, appendDeleteIntervalToRevertibles, appendIntervalPropertyChangedToRevertibles, appendSharedStringDeltaToRevertibles, } from "../../revertibles.js";
|
|
11
|
-
import { isRevertibleSharedString, baseModel, defaultFuzzOptions, } from "./fuzzUtils.js";
|
|
12
|
-
import { makeOperationGenerator } from "./intervalCollection.fuzz.spec.js";
|
|
13
|
-
const emitter = new TypedEventEmitter();
|
|
14
|
-
emitter.on("clientCreate", (client) => {
|
|
15
|
-
const channel = client.channel;
|
|
16
|
-
channel.revertibles = [];
|
|
17
|
-
channel.isCurrentRevert = false;
|
|
18
|
-
channel.on("createIntervalCollection", (label) => {
|
|
19
|
-
const collection = channel.getIntervalCollection(label);
|
|
20
|
-
assert(isRevertibleSharedString(channel));
|
|
21
|
-
collection.on("addInterval", (interval, local, op) => {
|
|
22
|
-
if (local && !channel.isCurrentRevert) {
|
|
23
|
-
appendAddIntervalToRevertibles(interval, channel.revertibles);
|
|
24
|
-
}
|
|
25
|
-
});
|
|
26
|
-
collection.on("deleteInterval", (interval, local, op) => {
|
|
27
|
-
if (local && !channel.isCurrentRevert) {
|
|
28
|
-
appendDeleteIntervalToRevertibles(channel, interval, channel.revertibles);
|
|
29
|
-
}
|
|
30
|
-
});
|
|
31
|
-
collection.on("changeInterval", (interval, previousInterval, local, op, slide) => {
|
|
32
|
-
if (local && !channel.isCurrentRevert && !slide) {
|
|
33
|
-
appendChangeIntervalToRevertibles(channel, interval, previousInterval, channel.revertibles);
|
|
34
|
-
}
|
|
35
|
-
});
|
|
36
|
-
collection.on("propertyChanged", (interval, propertyDeltas, local, op) => {
|
|
37
|
-
if (local && !channel.isCurrentRevert) {
|
|
38
|
-
appendIntervalPropertyChangedToRevertibles(interval, propertyDeltas, channel.revertibles);
|
|
39
|
-
}
|
|
40
|
-
});
|
|
41
|
-
channel.on("sequenceDelta", (op) => {
|
|
42
|
-
if (op.isLocal && !channel.isCurrentRevert) {
|
|
43
|
-
appendSharedStringDeltaToRevertibles(channel, op, channel.revertibles);
|
|
44
|
-
}
|
|
45
|
-
});
|
|
46
|
-
});
|
|
47
|
-
});
|
|
48
|
-
const defaultRevertiblesFuzzOptions = {
|
|
49
|
-
...defaultFuzzOptions,
|
|
50
|
-
reconnectProbability: 0,
|
|
51
|
-
clientJoinOptions: {
|
|
52
|
-
maxNumberOfClients: 6,
|
|
53
|
-
clientAddProbability: 0,
|
|
54
|
-
},
|
|
55
|
-
};
|
|
56
|
-
const optionsWithEmitter = {
|
|
57
|
-
...defaultRevertiblesFuzzOptions,
|
|
58
|
-
emitter,
|
|
59
|
-
};
|
|
60
|
-
function operationGenerator(optionsParam) {
|
|
61
|
-
async function revertSharedStringRevertibles(state) {
|
|
62
|
-
assert(isRevertibleSharedString(state.client.channel));
|
|
63
|
-
return {
|
|
64
|
-
type: "revertSharedStringRevertibles",
|
|
65
|
-
// grab a random number of edits to revert
|
|
66
|
-
editsToRevert: state.random.integer(1, state.client.channel.revertibles.length),
|
|
67
|
-
};
|
|
68
|
-
}
|
|
69
|
-
const hasRevertibles = ({ client }) => {
|
|
70
|
-
assert(isRevertibleSharedString(client.channel));
|
|
71
|
-
return client.channel.revertibles.length > 0;
|
|
72
|
-
};
|
|
73
|
-
assert(optionsParam.weights !== undefined);
|
|
74
|
-
const baseGenerator = makeOperationGenerator(optionsParam, true);
|
|
75
|
-
return createWeightedGenerator([
|
|
76
|
-
[revertSharedStringRevertibles, optionsParam.weights.revertWeight, hasRevertibles],
|
|
77
|
-
[baseGenerator, 1],
|
|
78
|
-
]);
|
|
79
|
-
}
|
|
80
|
-
describe("IntervalCollection fuzz testing", () => {
|
|
81
|
-
const model = {
|
|
82
|
-
...baseModel,
|
|
83
|
-
workloadName: "interval collection with revertibles",
|
|
84
|
-
generatorFactory: () => take(100,
|
|
85
|
-
// Weights are explicitly defined here while bugs are being resolved. Once resolved,
|
|
86
|
-
// the weights in the defaultOptions parameter will be used.
|
|
87
|
-
operationGenerator({
|
|
88
|
-
weights: {
|
|
89
|
-
revertWeight: 2,
|
|
90
|
-
addText: 2,
|
|
91
|
-
removeRange: 1,
|
|
92
|
-
obliterateRange: 0,
|
|
93
|
-
addInterval: 2,
|
|
94
|
-
deleteInterval: 2,
|
|
95
|
-
changeInterval: 2,
|
|
96
|
-
},
|
|
97
|
-
})),
|
|
98
|
-
};
|
|
99
|
-
createDDSFuzzSuite(model, optionsWithEmitter);
|
|
100
|
-
});
|
|
101
|
-
describe("IntervalCollection fuzz testing with rebasing", () => {
|
|
102
|
-
const model = {
|
|
103
|
-
...baseModel,
|
|
104
|
-
workloadName: "interval collection with revertibles and rebasing",
|
|
105
|
-
generatorFactory: () => take(100,
|
|
106
|
-
// Weights are explicitly defined here while bugs are being resolved. Once resolved,
|
|
107
|
-
// the weights in the defaultOptions parameter will be used.
|
|
108
|
-
operationGenerator({
|
|
109
|
-
weights: {
|
|
110
|
-
revertWeight: 2,
|
|
111
|
-
addText: 2,
|
|
112
|
-
removeRange: 1,
|
|
113
|
-
obliterateRange: 0,
|
|
114
|
-
addInterval: 2,
|
|
115
|
-
deleteInterval: 2,
|
|
116
|
-
changeInterval: 2,
|
|
117
|
-
},
|
|
118
|
-
})),
|
|
119
|
-
};
|
|
120
|
-
createDDSFuzzSuite(model, {
|
|
121
|
-
...optionsWithEmitter,
|
|
122
|
-
rebaseProbability: 0.15,
|
|
123
|
-
containerRuntimeOptions: {
|
|
124
|
-
flushMode: FlushMode.TurnBased,
|
|
125
|
-
enableGroupedBatching: true,
|
|
126
|
-
},
|
|
127
|
-
});
|
|
128
|
-
});
|
|
129
|
-
//# sourceMappingURL=intervalRevertibles.fuzz.spec.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"intervalRevertibles.fuzz.spec.js","sourceRoot":"","sources":["../../../src/test/fuzz/intervalRevertibles.fuzz.spec.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { strict as assert } from \"assert\";\nimport {\n\tcreateWeightedAsyncGenerator as createWeightedGenerator,\n\tAsyncGenerator as Generator,\n\ttakeAsync as take,\n} from \"@fluid-private/stochastic-test-utils\";\nimport {\n\tcreateDDSFuzzSuite,\n\tDDSFuzzModel,\n\tDDSFuzzHarnessEvents,\n\tDDSFuzzSuiteOptions,\n} from \"@fluid-private/test-dds-utils\";\nimport { TypedEventEmitter } from \"@fluid-internal/client-utils\";\nimport { FlushMode } from \"@fluidframework/runtime-definitions\";\nimport {\n\tappendAddIntervalToRevertibles,\n\tappendChangeIntervalToRevertibles,\n\tappendDeleteIntervalToRevertibles,\n\tappendIntervalPropertyChangedToRevertibles,\n\tappendSharedStringDeltaToRevertibles,\n} from \"../../revertibles.js\";\nimport {\n\tFuzzTestState,\n\tRevertOperation,\n\tRevertibleSharedString,\n\tisRevertibleSharedString,\n\tIntervalOperationGenerationConfig,\n\tRevertSharedStringRevertibles,\n\tSharedStringFuzzFactory,\n\tbaseModel,\n\tdefaultFuzzOptions,\n} from \"./fuzzUtils.js\";\nimport { makeOperationGenerator } from \"./intervalCollection.fuzz.spec.js\";\n\nconst emitter = new TypedEventEmitter<DDSFuzzHarnessEvents>();\n\nemitter.on(\"clientCreate\", (client) => {\n\tconst channel = client.channel as RevertibleSharedString;\n\tchannel.revertibles = [];\n\tchannel.isCurrentRevert = false;\n\n\tchannel.on(\"createIntervalCollection\", (label) => {\n\t\tconst collection = channel.getIntervalCollection(label);\n\n\t\tassert(isRevertibleSharedString(channel));\n\t\tcollection.on(\"addInterval\", (interval, local, op) => {\n\t\t\tif (local && !channel.isCurrentRevert) {\n\t\t\t\tappendAddIntervalToRevertibles(interval, channel.revertibles);\n\t\t\t}\n\t\t});\n\t\tcollection.on(\"deleteInterval\", (interval, local, op) => {\n\t\t\tif (local && !channel.isCurrentRevert) {\n\t\t\t\tappendDeleteIntervalToRevertibles(channel, interval, channel.revertibles);\n\t\t\t}\n\t\t});\n\t\tcollection.on(\"changeInterval\", (interval, previousInterval, local, op, slide) => {\n\t\t\tif (local && !channel.isCurrentRevert && !slide) {\n\t\t\t\tappendChangeIntervalToRevertibles(\n\t\t\t\t\tchannel,\n\t\t\t\t\tinterval,\n\t\t\t\t\tpreviousInterval,\n\t\t\t\t\tchannel.revertibles,\n\t\t\t\t);\n\t\t\t}\n\t\t});\n\t\tcollection.on(\"propertyChanged\", (interval, propertyDeltas, local, op) => {\n\t\t\tif (local && !channel.isCurrentRevert) {\n\t\t\t\tappendIntervalPropertyChangedToRevertibles(\n\t\t\t\t\tinterval,\n\t\t\t\t\tpropertyDeltas,\n\t\t\t\t\tchannel.revertibles,\n\t\t\t\t);\n\t\t\t}\n\t\t});\n\t\tchannel.on(\"sequenceDelta\", (op) => {\n\t\t\tif (op.isLocal && !channel.isCurrentRevert) {\n\t\t\t\tappendSharedStringDeltaToRevertibles(channel, op, channel.revertibles);\n\t\t\t}\n\t\t});\n\t});\n});\n\nconst defaultRevertiblesFuzzOptions: Partial<DDSFuzzSuiteOptions> = {\n\t...defaultFuzzOptions,\n\treconnectProbability: 0,\n\tclientJoinOptions: {\n\t\tmaxNumberOfClients: 6,\n\t\tclientAddProbability: 0,\n\t},\n};\n\nconst optionsWithEmitter: Partial<DDSFuzzSuiteOptions> = {\n\t...defaultRevertiblesFuzzOptions,\n\temitter,\n};\n\ntype ClientOpState = FuzzTestState;\nfunction operationGenerator(\n\toptionsParam: IntervalOperationGenerationConfig,\n): Generator<RevertOperation, ClientOpState> {\n\tasync function revertSharedStringRevertibles(\n\t\tstate: ClientOpState,\n\t): Promise<RevertSharedStringRevertibles> {\n\t\tassert(isRevertibleSharedString(state.client.channel));\n\t\treturn {\n\t\t\ttype: \"revertSharedStringRevertibles\",\n\t\t\t// grab a random number of edits to revert\n\t\t\teditsToRevert: state.random.integer(1, state.client.channel.revertibles.length),\n\t\t};\n\t}\n\n\tconst hasRevertibles = ({ client }: ClientOpState): boolean => {\n\t\tassert(isRevertibleSharedString(client.channel));\n\t\treturn client.channel.revertibles.length > 0;\n\t};\n\n\tassert(optionsParam.weights !== undefined);\n\tconst baseGenerator = makeOperationGenerator(optionsParam, true);\n\treturn createWeightedGenerator<RevertOperation, ClientOpState>([\n\t\t[revertSharedStringRevertibles, optionsParam.weights.revertWeight, hasRevertibles],\n\t\t[baseGenerator, 1],\n\t]);\n}\n\ndescribe(\"IntervalCollection fuzz testing\", () => {\n\tconst model: DDSFuzzModel<SharedStringFuzzFactory, RevertOperation, FuzzTestState> = {\n\t\t...baseModel,\n\t\tworkloadName: \"interval collection with revertibles\",\n\t\tgeneratorFactory: () =>\n\t\t\ttake(\n\t\t\t\t100,\n\t\t\t\t// Weights are explicitly defined here while bugs are being resolved. Once resolved,\n\t\t\t\t// the weights in the defaultOptions parameter will be used.\n\t\t\t\toperationGenerator({\n\t\t\t\t\tweights: {\n\t\t\t\t\t\trevertWeight: 2,\n\t\t\t\t\t\taddText: 2,\n\t\t\t\t\t\tremoveRange: 1,\n\t\t\t\t\t\tobliterateRange: 0,\n\t\t\t\t\t\taddInterval: 2,\n\t\t\t\t\t\tdeleteInterval: 2,\n\t\t\t\t\t\tchangeInterval: 2,\n\t\t\t\t\t},\n\t\t\t\t}),\n\t\t\t),\n\t};\n\n\tcreateDDSFuzzSuite(model, optionsWithEmitter);\n});\n\ndescribe(\"IntervalCollection fuzz testing with rebasing\", () => {\n\tconst model: DDSFuzzModel<SharedStringFuzzFactory, RevertOperation, FuzzTestState> = {\n\t\t...baseModel,\n\t\tworkloadName: \"interval collection with revertibles and rebasing\",\n\t\tgeneratorFactory: () =>\n\t\t\ttake(\n\t\t\t\t100,\n\t\t\t\t// Weights are explicitly defined here while bugs are being resolved. Once resolved,\n\t\t\t\t// the weights in the defaultOptions parameter will be used.\n\t\t\t\toperationGenerator({\n\t\t\t\t\tweights: {\n\t\t\t\t\t\trevertWeight: 2,\n\t\t\t\t\t\taddText: 2,\n\t\t\t\t\t\tremoveRange: 1,\n\t\t\t\t\t\tobliterateRange: 0,\n\t\t\t\t\t\taddInterval: 2,\n\t\t\t\t\t\tdeleteInterval: 2,\n\t\t\t\t\t\tchangeInterval: 2,\n\t\t\t\t\t},\n\t\t\t\t}),\n\t\t\t),\n\t};\n\n\tcreateDDSFuzzSuite(model, {\n\t\t...optionsWithEmitter,\n\t\trebaseProbability: 0.15,\n\t\tcontainerRuntimeOptions: {\n\t\t\tflushMode: FlushMode.TurnBased,\n\t\t\tenableGroupedBatching: true,\n\t\t},\n\t});\n});\n"]}
|
|
@@ -1,91 +0,0 @@
|
|
|
1
|
-
/*!
|
|
2
|
-
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
-
* Licensed under the MIT License.
|
|
4
|
-
*/
|
|
5
|
-
import { createWeightedAsyncGenerator as createWeightedGenerator, takeAsync as take, } from "@fluid-private/stochastic-test-utils";
|
|
6
|
-
import { createDDSFuzzSuite } from "@fluid-private/test-dds-utils";
|
|
7
|
-
import { FlushMode } from "@fluidframework/runtime-definitions";
|
|
8
|
-
import { defaultIntervalOperationGenerationConfig, createSharedStringGeneratorOperations, baseModel, defaultFuzzOptions, } from "./fuzzUtils.js";
|
|
9
|
-
export function makeSharedStringOperationGenerator(optionsParam, alwaysLeaveChar = false) {
|
|
10
|
-
const { addText, removeRange, removeRangeLeaveChar, lengthSatisfies, hasNonzeroLength, isShorterThanMaxLength, } = createSharedStringGeneratorOperations(optionsParam);
|
|
11
|
-
const usableWeights = optionsParam?.weights ?? defaultIntervalOperationGenerationConfig.weights;
|
|
12
|
-
return createWeightedGenerator([
|
|
13
|
-
[addText, usableWeights.addText, isShorterThanMaxLength],
|
|
14
|
-
[
|
|
15
|
-
alwaysLeaveChar ? removeRangeLeaveChar : removeRange,
|
|
16
|
-
usableWeights.removeRange,
|
|
17
|
-
alwaysLeaveChar
|
|
18
|
-
? lengthSatisfies((length) => {
|
|
19
|
-
return length > 1;
|
|
20
|
-
})
|
|
21
|
-
: hasNonzeroLength,
|
|
22
|
-
],
|
|
23
|
-
]);
|
|
24
|
-
}
|
|
25
|
-
const baseSharedStringModel = {
|
|
26
|
-
...baseModel,
|
|
27
|
-
generatorFactory: () => take(100, makeSharedStringOperationGenerator(defaultIntervalOperationGenerationConfig)),
|
|
28
|
-
};
|
|
29
|
-
describe("SharedString fuzz testing", () => {
|
|
30
|
-
createDDSFuzzSuite({ ...baseSharedStringModel, workloadName: "default" }, {
|
|
31
|
-
...defaultFuzzOptions,
|
|
32
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
33
|
-
// replay: 0,
|
|
34
|
-
});
|
|
35
|
-
});
|
|
36
|
-
describe("SharedString fuzz with stashing", () => {
|
|
37
|
-
createDDSFuzzSuite({ ...baseSharedStringModel, workloadName: "default" }, {
|
|
38
|
-
...defaultFuzzOptions,
|
|
39
|
-
clientJoinOptions: {
|
|
40
|
-
clientAddProbability: 0.1,
|
|
41
|
-
maxNumberOfClients: Number.MAX_SAFE_INTEGER,
|
|
42
|
-
stashableClientProbability: 0.2,
|
|
43
|
-
},
|
|
44
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
45
|
-
// replay: 0,
|
|
46
|
-
});
|
|
47
|
-
});
|
|
48
|
-
describe("SharedString fuzz testing with rebased batches", () => {
|
|
49
|
-
createDDSFuzzSuite({ ...baseSharedStringModel, workloadName: "SharedString with rebasing" }, {
|
|
50
|
-
...defaultFuzzOptions,
|
|
51
|
-
reconnectProbability: 0.0,
|
|
52
|
-
numberOfClients: 3,
|
|
53
|
-
clientJoinOptions: {
|
|
54
|
-
maxNumberOfClients: 3,
|
|
55
|
-
clientAddProbability: 0.0,
|
|
56
|
-
},
|
|
57
|
-
rebaseProbability: 0.2,
|
|
58
|
-
containerRuntimeOptions: {
|
|
59
|
-
flushMode: FlushMode.TurnBased,
|
|
60
|
-
enableGroupedBatching: true,
|
|
61
|
-
},
|
|
62
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
63
|
-
// replay: 0,
|
|
64
|
-
});
|
|
65
|
-
});
|
|
66
|
-
// todo: potentially related to AB#7050
|
|
67
|
-
//
|
|
68
|
-
// `intervalRebasing.spec.ts` contains some reduced tests exhibiting the crashes
|
|
69
|
-
// linked to AB#7050
|
|
70
|
-
describe.skip("SharedString fuzz testing with rebased batches and reconnect", () => {
|
|
71
|
-
createDDSFuzzSuite({
|
|
72
|
-
...baseSharedStringModel,
|
|
73
|
-
workloadName: "SharedString with rebasing and reconnect",
|
|
74
|
-
}, {
|
|
75
|
-
...defaultFuzzOptions,
|
|
76
|
-
reconnectProbability: 0.3,
|
|
77
|
-
numberOfClients: 3,
|
|
78
|
-
clientJoinOptions: {
|
|
79
|
-
maxNumberOfClients: 3,
|
|
80
|
-
clientAddProbability: 0.0,
|
|
81
|
-
},
|
|
82
|
-
rebaseProbability: 0.2,
|
|
83
|
-
containerRuntimeOptions: {
|
|
84
|
-
flushMode: FlushMode.TurnBased,
|
|
85
|
-
enableGroupedBatching: true,
|
|
86
|
-
},
|
|
87
|
-
// Uncomment this line to replay a specific seed from its failure file:
|
|
88
|
-
// replay: 0,
|
|
89
|
-
});
|
|
90
|
-
});
|
|
91
|
-
//# sourceMappingURL=sharedString.fuzz.spec.js.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"sharedString.fuzz.spec.js","sourceRoot":"","sources":["../../../src/test/fuzz/sharedString.fuzz.spec.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport {\n\tcreateWeightedAsyncGenerator as createWeightedGenerator,\n\tAsyncGenerator as Generator,\n\ttakeAsync as take,\n} from \"@fluid-private/stochastic-test-utils\";\nimport { createDDSFuzzSuite } from \"@fluid-private/test-dds-utils\";\nimport { FlushMode } from \"@fluidframework/runtime-definitions\";\nimport {\n\tOperation,\n\tFuzzTestState,\n\tdefaultIntervalOperationGenerationConfig,\n\tcreateSharedStringGeneratorOperations,\n\tSharedStringOperationGenerationConfig,\n\tbaseModel,\n\tdefaultFuzzOptions,\n} from \"./fuzzUtils.js\";\n\ntype ClientOpState = FuzzTestState;\nexport function makeSharedStringOperationGenerator(\n\toptionsParam?: SharedStringOperationGenerationConfig,\n\talwaysLeaveChar: boolean = false,\n): Generator<Operation, ClientOpState> {\n\tconst {\n\t\taddText,\n\t\tremoveRange,\n\t\tremoveRangeLeaveChar,\n\t\tlengthSatisfies,\n\t\thasNonzeroLength,\n\t\tisShorterThanMaxLength,\n\t} = createSharedStringGeneratorOperations(optionsParam);\n\n\tconst usableWeights = optionsParam?.weights ?? defaultIntervalOperationGenerationConfig.weights;\n\treturn createWeightedGenerator<Operation, ClientOpState>([\n\t\t[addText, usableWeights.addText, isShorterThanMaxLength],\n\t\t[\n\t\t\talwaysLeaveChar ? removeRangeLeaveChar : removeRange,\n\t\t\tusableWeights.removeRange,\n\t\t\talwaysLeaveChar\n\t\t\t\t? lengthSatisfies((length) => {\n\t\t\t\t\t\treturn length > 1;\n\t\t\t\t })\n\t\t\t\t: hasNonzeroLength,\n\t\t],\n\t]);\n}\n\nconst baseSharedStringModel = {\n\t...baseModel,\n\tgeneratorFactory: () =>\n\t\ttake(100, makeSharedStringOperationGenerator(defaultIntervalOperationGenerationConfig)),\n};\n\ndescribe(\"SharedString fuzz testing\", () => {\n\tcreateDDSFuzzSuite(\n\t\t{ ...baseSharedStringModel, workloadName: \"default\" },\n\t\t{\n\t\t\t...defaultFuzzOptions,\n\t\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t\t// replay: 0,\n\t\t},\n\t);\n});\n\ndescribe(\"SharedString fuzz with stashing\", () => {\n\tcreateDDSFuzzSuite(\n\t\t{ ...baseSharedStringModel, workloadName: \"default\" },\n\t\t{\n\t\t\t...defaultFuzzOptions,\n\t\t\tclientJoinOptions: {\n\t\t\t\tclientAddProbability: 0.1,\n\t\t\t\tmaxNumberOfClients: Number.MAX_SAFE_INTEGER,\n\t\t\t\tstashableClientProbability: 0.2,\n\t\t\t},\n\t\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t\t// replay: 0,\n\t\t},\n\t);\n});\n\ndescribe(\"SharedString fuzz testing with rebased batches\", () => {\n\tcreateDDSFuzzSuite(\n\t\t{ ...baseSharedStringModel, workloadName: \"SharedString with rebasing\" },\n\t\t{\n\t\t\t...defaultFuzzOptions,\n\t\t\treconnectProbability: 0.0,\n\t\t\tnumberOfClients: 3,\n\t\t\tclientJoinOptions: {\n\t\t\t\tmaxNumberOfClients: 3,\n\t\t\t\tclientAddProbability: 0.0,\n\t\t\t},\n\t\t\trebaseProbability: 0.2,\n\t\t\tcontainerRuntimeOptions: {\n\t\t\t\tflushMode: FlushMode.TurnBased,\n\t\t\t\tenableGroupedBatching: true,\n\t\t\t},\n\t\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t\t// replay: 0,\n\t\t},\n\t);\n});\n\n// todo: potentially related to AB#7050\n//\n// `intervalRebasing.spec.ts` contains some reduced tests exhibiting the crashes\n// linked to AB#7050\ndescribe.skip(\"SharedString fuzz testing with rebased batches and reconnect\", () => {\n\tcreateDDSFuzzSuite(\n\t\t{\n\t\t\t...baseSharedStringModel,\n\t\t\tworkloadName: \"SharedString with rebasing and reconnect\",\n\t\t},\n\t\t{\n\t\t\t...defaultFuzzOptions,\n\t\t\treconnectProbability: 0.3,\n\t\t\tnumberOfClients: 3,\n\t\t\tclientJoinOptions: {\n\t\t\t\tmaxNumberOfClients: 3,\n\t\t\t\tclientAddProbability: 0.0,\n\t\t\t},\n\t\t\trebaseProbability: 0.2,\n\t\t\tcontainerRuntimeOptions: {\n\t\t\t\tflushMode: FlushMode.TurnBased,\n\t\t\t\tenableGroupedBatching: true,\n\t\t\t},\n\t\t\t// Uncomment this line to replay a specific seed from its failure file:\n\t\t\t// replay: 0,\n\t\t},\n\t);\n});\n"]}
|
|
@@ -1,138 +0,0 @@
|
|
|
1
|
-
/*!
|
|
2
|
-
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
-
* Licensed under the MIT License.
|
|
4
|
-
*/
|
|
5
|
-
// eslint-disable-next-line import/no-internal-modules
|
|
6
|
-
import { SnapshotLegacy as Snapshot } from "@fluidframework/merge-tree/test";
|
|
7
|
-
import { MersenneTwister19937, Random } from "random-js";
|
|
8
|
-
import * as mocks from "@fluidframework/test-runtime-utils";
|
|
9
|
-
import { SharedString } from "../sharedString.js";
|
|
10
|
-
import { SharedStringFactory } from "../sequenceFactory.js";
|
|
11
|
-
import { SharedStringWithV1IntervalCollection, V1IntervalCollectionSharedStringFactory, } from "./v1IntervalCollectionHelpers.js";
|
|
12
|
-
export const LocationBase = "src/test/snapshots/";
|
|
13
|
-
export const supportedVersions = new Map([
|
|
14
|
-
// the catchUpBlob had to be renamed.
|
|
15
|
-
// We are now support any name for this blob.
|
|
16
|
-
// so for legacy set it to another name to ensure
|
|
17
|
-
// we keep support
|
|
18
|
-
["legacy", { catchUpBlobName: "randomNameForCatchUpOps" }],
|
|
19
|
-
["legacyWithCatchUp", {}],
|
|
20
|
-
["v1", { newMergeTreeSnapshotFormat: true }],
|
|
21
|
-
["v1Intervals", {}],
|
|
22
|
-
]);
|
|
23
|
-
function createIntervals(sharedString) {
|
|
24
|
-
const rand = new Random(MersenneTwister19937.seed(0));
|
|
25
|
-
const collection1 = sharedString.getIntervalCollection("collection1");
|
|
26
|
-
collection1.add({ start: 1, end: 5, props: { intervalId: rand.uuid4() } });
|
|
27
|
-
const collection2 = sharedString.getIntervalCollection("collection2");
|
|
28
|
-
for (let i = 0; i < sharedString.getLength() - 5; i += 100) {
|
|
29
|
-
collection2.add({ start: i, end: i + 5, props: { intervalId: rand.uuid4() } });
|
|
30
|
-
}
|
|
31
|
-
}
|
|
32
|
-
export function* generateStrings() {
|
|
33
|
-
for (const [version, options] of supportedVersions) {
|
|
34
|
-
const documentId = "fakeId";
|
|
35
|
-
const dataStoreRuntime = new mocks.MockFluidDataStoreRuntime();
|
|
36
|
-
const createNewSharedString = () => {
|
|
37
|
-
const string = new SharedString(dataStoreRuntime, documentId, SharedStringFactory.Attributes);
|
|
38
|
-
string.initializeLocal();
|
|
39
|
-
return string;
|
|
40
|
-
};
|
|
41
|
-
const createNewV1SharedString = () => {
|
|
42
|
-
const string = new SharedStringWithV1IntervalCollection(dataStoreRuntime, documentId, V1IntervalCollectionSharedStringFactory.Attributes);
|
|
43
|
-
string.initializeLocal();
|
|
44
|
-
return string;
|
|
45
|
-
};
|
|
46
|
-
const normalized = version !== "v1Intervals";
|
|
47
|
-
for (const key of Object.keys(options)) {
|
|
48
|
-
dataStoreRuntime.options[key] = options[key];
|
|
49
|
-
}
|
|
50
|
-
const insertText = "text";
|
|
51
|
-
let sharedString = createNewSharedString();
|
|
52
|
-
// Small enough so snapshot won't have body
|
|
53
|
-
for (let i = 0; i < Snapshot.sizeOfFirstChunk / insertText.length / 2; ++i) {
|
|
54
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
55
|
-
}
|
|
56
|
-
yield {
|
|
57
|
-
snapshotPath: `${version}/headerOnly`,
|
|
58
|
-
expected: sharedString,
|
|
59
|
-
snapshotIsNormalized: normalized,
|
|
60
|
-
};
|
|
61
|
-
sharedString = createNewSharedString();
|
|
62
|
-
// Big enough that snapshot will have body
|
|
63
|
-
for (let i = 0; i < (Snapshot.sizeOfFirstChunk / insertText.length) * 2; ++i) {
|
|
64
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
65
|
-
}
|
|
66
|
-
yield {
|
|
67
|
-
snapshotPath: `${version}/headerAndBody`,
|
|
68
|
-
expected: sharedString,
|
|
69
|
-
snapshotIsNormalized: normalized,
|
|
70
|
-
};
|
|
71
|
-
sharedString = createNewSharedString();
|
|
72
|
-
// Very big sharedString
|
|
73
|
-
for (let i = 0; i < Snapshot.sizeOfFirstChunk; ++i) {
|
|
74
|
-
sharedString.insertText(0, `${insertText}-${i}`);
|
|
75
|
-
}
|
|
76
|
-
yield {
|
|
77
|
-
snapshotPath: `${version}/largeBody`,
|
|
78
|
-
expected: sharedString,
|
|
79
|
-
snapshotIsNormalized: normalized,
|
|
80
|
-
};
|
|
81
|
-
sharedString = createNewSharedString();
|
|
82
|
-
// SharedString with markers
|
|
83
|
-
for (let i = 0; i < (Snapshot.sizeOfFirstChunk / insertText.length) * 2; ++i) {
|
|
84
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
85
|
-
}
|
|
86
|
-
for (let i = 0; i < sharedString.getLength(); i += 70) {
|
|
87
|
-
sharedString.insertMarker(i, 1, {
|
|
88
|
-
ItemType: "Paragraph",
|
|
89
|
-
Properties: { Bold: false },
|
|
90
|
-
markerId: `marker${i}`,
|
|
91
|
-
referenceTileLabels: ["Eop"],
|
|
92
|
-
});
|
|
93
|
-
}
|
|
94
|
-
yield {
|
|
95
|
-
snapshotPath: `${version}/withMarkers`,
|
|
96
|
-
expected: sharedString,
|
|
97
|
-
snapshotIsNormalized: normalized,
|
|
98
|
-
};
|
|
99
|
-
sharedString = createNewSharedString();
|
|
100
|
-
// SharedString with annotations
|
|
101
|
-
for (let i = 0; i < (Snapshot.sizeOfFirstChunk / insertText.length) * 2; ++i) {
|
|
102
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
103
|
-
}
|
|
104
|
-
for (let i = 0; i < sharedString.getLength(); i += 70) {
|
|
105
|
-
sharedString.annotateRange(i, i + 10, { bold: true });
|
|
106
|
-
}
|
|
107
|
-
yield {
|
|
108
|
-
snapshotPath: `${version}/withAnnotations`,
|
|
109
|
-
expected: sharedString,
|
|
110
|
-
snapshotIsNormalized: normalized,
|
|
111
|
-
};
|
|
112
|
-
sharedString = createNewSharedString();
|
|
113
|
-
// SharedString with intervals
|
|
114
|
-
for (let i = 0; i < Snapshot.sizeOfFirstChunk / insertText.length / 2; i++) {
|
|
115
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
116
|
-
}
|
|
117
|
-
createIntervals(sharedString);
|
|
118
|
-
yield {
|
|
119
|
-
snapshotPath: `${version}/withIntervals`,
|
|
120
|
-
expected: sharedString,
|
|
121
|
-
snapshotIsNormalized: normalized,
|
|
122
|
-
};
|
|
123
|
-
if (version === "v1Intervals") {
|
|
124
|
-
sharedString = createNewV1SharedString();
|
|
125
|
-
// SharedString with V1 intervals
|
|
126
|
-
for (let i = 0; i < Snapshot.sizeOfFirstChunk / insertText.length / 2; i++) {
|
|
127
|
-
sharedString.insertText(0, `${insertText}${i}`);
|
|
128
|
-
}
|
|
129
|
-
createIntervals(sharedString);
|
|
130
|
-
yield {
|
|
131
|
-
snapshotPath: `${version}/withV1Intervals`,
|
|
132
|
-
expected: sharedString,
|
|
133
|
-
snapshotIsNormalized: normalized,
|
|
134
|
-
};
|
|
135
|
-
}
|
|
136
|
-
}
|
|
137
|
-
}
|
|
138
|
-
//# sourceMappingURL=generateSharedStrings.js.map
|