@fluidframework/merge-tree 2.0.0-internal.3.0.0 → 2.0.0-internal.3.1.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/.eslintrc.js +12 -15
- package/.mocharc.js +2 -2
- package/.vscode/launch.json +15 -14
- package/README.md +13 -13
- package/api-extractor.json +2 -2
- package/dist/MergeTreeTextHelper.d.ts.map +1 -1
- package/dist/MergeTreeTextHelper.js +2 -3
- package/dist/MergeTreeTextHelper.js.map +1 -1
- package/dist/attributionCollection.d.ts +35 -4
- package/dist/attributionCollection.d.ts.map +1 -1
- package/dist/attributionCollection.js +102 -23
- package/dist/attributionCollection.js.map +1 -1
- package/dist/base.d.ts.map +1 -1
- package/dist/base.js.map +1 -1
- package/dist/client.d.ts.map +1 -1
- package/dist/client.js +26 -9
- package/dist/client.js.map +1 -1
- package/dist/collections/heap.d.ts.map +1 -1
- package/dist/collections/heap.js +3 -3
- package/dist/collections/heap.js.map +1 -1
- package/dist/collections/list.d.ts.map +1 -1
- package/dist/collections/list.js +8 -8
- package/dist/collections/list.js.map +1 -1
- package/dist/collections/rbTree.d.ts.map +1 -1
- package/dist/collections/rbTree.js +17 -17
- package/dist/collections/rbTree.js.map +1 -1
- package/dist/collections/stack.d.ts.map +1 -1
- package/dist/collections/stack.js.map +1 -1
- package/dist/endOfTreeSegment.d.ts.map +1 -1
- package/dist/endOfTreeSegment.js +1 -1
- package/dist/endOfTreeSegment.js.map +1 -1
- package/dist/index.d.ts +3 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +4 -2
- package/dist/index.js.map +1 -1
- package/dist/localReference.d.ts +12 -12
- package/dist/localReference.d.ts.map +1 -1
- package/dist/localReference.js +29 -32
- package/dist/localReference.js.map +1 -1
- package/dist/mergeTree.d.ts +42 -0
- package/dist/mergeTree.d.ts.map +1 -1
- package/dist/mergeTree.js +148 -126
- package/dist/mergeTree.js.map +1 -1
- package/dist/mergeTreeDeltaCallback.d.ts.map +1 -1
- package/dist/mergeTreeDeltaCallback.js.map +1 -1
- package/dist/mergeTreeNodeWalk.d.ts.map +1 -1
- package/dist/mergeTreeNodeWalk.js +5 -4
- package/dist/mergeTreeNodeWalk.js.map +1 -1
- package/dist/mergeTreeNodes.d.ts +1 -18
- package/dist/mergeTreeNodes.d.ts.map +1 -1
- package/dist/mergeTreeNodes.js +7 -8
- package/dist/mergeTreeNodes.js.map +1 -1
- package/dist/mergeTreeTracking.d.ts.map +1 -1
- package/dist/mergeTreeTracking.js +3 -3
- package/dist/mergeTreeTracking.js.map +1 -1
- package/dist/opBuilder.d.ts.map +1 -1
- package/dist/opBuilder.js.map +1 -1
- package/dist/ops.d.ts.map +1 -1
- package/dist/ops.js.map +1 -1
- package/dist/ordinal.d.ts.map +1 -1
- package/dist/ordinal.js +3 -3
- package/dist/ordinal.js.map +1 -1
- package/dist/partialLengths.d.ts +2 -2
- package/dist/partialLengths.d.ts.map +1 -1
- package/dist/partialLengths.js +11 -12
- package/dist/partialLengths.js.map +1 -1
- package/dist/properties.d.ts.map +1 -1
- package/dist/properties.js +2 -2
- package/dist/properties.js.map +1 -1
- package/dist/referencePositions.d.ts +24 -0
- package/dist/referencePositions.d.ts.map +1 -1
- package/dist/referencePositions.js +7 -4
- package/dist/referencePositions.js.map +1 -1
- package/dist/revertibles.d.ts.map +1 -1
- package/dist/revertibles.js +15 -11
- package/dist/revertibles.js.map +1 -1
- package/dist/segmentGroupCollection.d.ts.map +1 -1
- package/dist/segmentGroupCollection.js.map +1 -1
- package/dist/segmentPropertiesManager.d.ts.map +1 -1
- package/dist/segmentPropertiesManager.js +14 -10
- package/dist/segmentPropertiesManager.js.map +1 -1
- package/dist/snapshotChunks.d.ts.map +1 -1
- package/dist/snapshotChunks.js.map +1 -1
- package/dist/snapshotLoader.d.ts.map +1 -1
- package/dist/snapshotLoader.js +21 -11
- package/dist/snapshotLoader.js.map +1 -1
- package/dist/snapshotV1.d.ts.map +1 -1
- package/dist/snapshotV1.js +21 -11
- package/dist/snapshotV1.js.map +1 -1
- package/dist/snapshotlegacy.d.ts.map +1 -1
- package/dist/snapshotlegacy.js +17 -10
- package/dist/snapshotlegacy.js.map +1 -1
- package/dist/sortedSegmentSet.d.ts.map +1 -1
- package/dist/sortedSegmentSet.js +2 -2
- package/dist/sortedSegmentSet.js.map +1 -1
- package/dist/sortedSet.d.ts.map +1 -1
- package/dist/sortedSet.js.map +1 -1
- package/dist/textSegment.d.ts.map +1 -1
- package/dist/textSegment.js +6 -8
- package/dist/textSegment.js.map +1 -1
- package/dist/zamboni.d.ts.map +1 -1
- package/dist/zamboni.js +10 -8
- package/dist/zamboni.js.map +1 -1
- package/docs/Attribution.md +66 -67
- package/docs/DEV.md +6 -3
- package/docs/Obliterate.md +123 -115
- package/docs/REFERENCEPOSITIONS.md +32 -32
- package/lib/MergeTreeTextHelper.d.ts.map +1 -1
- package/lib/MergeTreeTextHelper.js +2 -3
- package/lib/MergeTreeTextHelper.js.map +1 -1
- package/lib/attributionCollection.d.ts +35 -4
- package/lib/attributionCollection.d.ts.map +1 -1
- package/lib/attributionCollection.js +100 -23
- package/lib/attributionCollection.js.map +1 -1
- package/lib/base.d.ts.map +1 -1
- package/lib/base.js.map +1 -1
- package/lib/client.d.ts.map +1 -1
- package/lib/client.js +26 -9
- package/lib/client.js.map +1 -1
- package/lib/collections/heap.d.ts.map +1 -1
- package/lib/collections/heap.js +3 -3
- package/lib/collections/heap.js.map +1 -1
- package/lib/collections/list.d.ts.map +1 -1
- package/lib/collections/list.js +8 -8
- package/lib/collections/list.js.map +1 -1
- package/lib/collections/rbTree.d.ts.map +1 -1
- package/lib/collections/rbTree.js +17 -17
- package/lib/collections/rbTree.js.map +1 -1
- package/lib/collections/stack.d.ts.map +1 -1
- package/lib/collections/stack.js.map +1 -1
- package/lib/endOfTreeSegment.d.ts.map +1 -1
- package/lib/endOfTreeSegment.js +1 -1
- package/lib/endOfTreeSegment.js.map +1 -1
- package/lib/index.d.ts +3 -3
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -0
- package/lib/index.js.map +1 -1
- package/lib/localReference.d.ts +12 -12
- package/lib/localReference.d.ts.map +1 -1
- package/lib/localReference.js +29 -32
- package/lib/localReference.js.map +1 -1
- package/lib/mergeTree.d.ts +42 -0
- package/lib/mergeTree.d.ts.map +1 -1
- package/lib/mergeTree.js +151 -129
- package/lib/mergeTree.js.map +1 -1
- package/lib/mergeTreeDeltaCallback.d.ts.map +1 -1
- package/lib/mergeTreeDeltaCallback.js.map +1 -1
- package/lib/mergeTreeNodeWalk.d.ts.map +1 -1
- package/lib/mergeTreeNodeWalk.js +5 -4
- package/lib/mergeTreeNodeWalk.js.map +1 -1
- package/lib/mergeTreeNodes.d.ts +1 -18
- package/lib/mergeTreeNodes.d.ts.map +1 -1
- package/lib/mergeTreeNodes.js +11 -12
- package/lib/mergeTreeNodes.js.map +1 -1
- package/lib/mergeTreeTracking.d.ts.map +1 -1
- package/lib/mergeTreeTracking.js +3 -3
- package/lib/mergeTreeTracking.js.map +1 -1
- package/lib/opBuilder.d.ts.map +1 -1
- package/lib/opBuilder.js.map +1 -1
- package/lib/ops.d.ts.map +1 -1
- package/lib/ops.js.map +1 -1
- package/lib/ordinal.d.ts.map +1 -1
- package/lib/ordinal.js +3 -3
- package/lib/ordinal.js.map +1 -1
- package/lib/partialLengths.d.ts +2 -2
- package/lib/partialLengths.d.ts.map +1 -1
- package/lib/partialLengths.js +11 -12
- package/lib/partialLengths.js.map +1 -1
- package/lib/properties.d.ts.map +1 -1
- package/lib/properties.js +2 -2
- package/lib/properties.js.map +1 -1
- package/lib/referencePositions.d.ts +24 -0
- package/lib/referencePositions.d.ts.map +1 -1
- package/lib/referencePositions.js +7 -4
- package/lib/referencePositions.js.map +1 -1
- package/lib/revertibles.d.ts.map +1 -1
- package/lib/revertibles.js +16 -12
- package/lib/revertibles.js.map +1 -1
- package/lib/segmentGroupCollection.d.ts.map +1 -1
- package/lib/segmentGroupCollection.js.map +1 -1
- package/lib/segmentPropertiesManager.d.ts.map +1 -1
- package/lib/segmentPropertiesManager.js +15 -11
- package/lib/segmentPropertiesManager.js.map +1 -1
- package/lib/snapshotChunks.d.ts.map +1 -1
- package/lib/snapshotChunks.js.map +1 -1
- package/lib/snapshotLoader.d.ts.map +1 -1
- package/lib/snapshotLoader.js +22 -12
- package/lib/snapshotLoader.js.map +1 -1
- package/lib/snapshotV1.d.ts.map +1 -1
- package/lib/snapshotV1.js +22 -12
- package/lib/snapshotV1.js.map +1 -1
- package/lib/snapshotlegacy.d.ts.map +1 -1
- package/lib/snapshotlegacy.js +17 -10
- package/lib/snapshotlegacy.js.map +1 -1
- package/lib/sortedSegmentSet.d.ts.map +1 -1
- package/lib/sortedSegmentSet.js +2 -2
- package/lib/sortedSegmentSet.js.map +1 -1
- package/lib/sortedSet.d.ts.map +1 -1
- package/lib/sortedSet.js.map +1 -1
- package/lib/textSegment.d.ts.map +1 -1
- package/lib/textSegment.js +6 -8
- package/lib/textSegment.js.map +1 -1
- package/lib/zamboni.d.ts.map +1 -1
- package/lib/zamboni.js +10 -8
- package/lib/zamboni.js.map +1 -1
- package/package.json +120 -130
- package/prettier.config.cjs +1 -1
- package/src/MergeTreeTextHelper.ts +57 -50
- package/src/attributionCollection.ts +339 -184
- package/src/base.ts +2 -2
- package/src/client.ts +1115 -997
- package/src/collections/heap.ts +53 -53
- package/src/collections/list.ts +178 -176
- package/src/collections/rbTree.ts +648 -580
- package/src/collections/stack.ts +13 -13
- package/src/endOfTreeSegment.ts +94 -95
- package/src/index.ts +30 -29
- package/src/localReference.ts +527 -523
- package/src/mergeTree.ts +2433 -2175
- package/src/mergeTreeDeltaCallback.ts +65 -59
- package/src/mergeTreeNodeWalk.ts +135 -134
- package/src/mergeTreeNodes.ts +621 -632
- package/src/mergeTreeTracking.ts +96 -95
- package/src/opBuilder.ts +50 -46
- package/src/ops.ts +74 -74
- package/src/ordinal.ts +22 -20
- package/src/partialLengths.ts +949 -889
- package/src/properties.ts +134 -129
- package/src/referencePositions.ts +76 -44
- package/src/revertibles.ts +277 -283
- package/src/segmentGroupCollection.ts +52 -53
- package/src/segmentPropertiesManager.ts +170 -164
- package/src/snapshotChunks.ts +144 -131
- package/src/snapshotLoader.ts +271 -245
- package/src/snapshotV1.ts +277 -251
- package/src/snapshotlegacy.ts +226 -182
- package/src/sortedSegmentSet.ts +74 -67
- package/src/sortedSet.ts +57 -57
- package/src/textSegment.ts +97 -91
- package/src/zamboni.ts +163 -153
- package/tsconfig.esnext.json +6 -6
- package/tsconfig.json +9 -13
package/.eslintrc.js
CHANGED
|
@@ -4,18 +4,15 @@
|
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
6
|
module.exports = {
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
"prefer-arrow/prefer-arrow-functions": "off"
|
|
20
|
-
}
|
|
21
|
-
}
|
|
7
|
+
extends: [require.resolve("@fluidframework/eslint-config-fluid/minimal"), "prettier"],
|
|
8
|
+
parserOptions: {
|
|
9
|
+
project: ["./tsconfig.json", "./src/test/tsconfig.json"],
|
|
10
|
+
},
|
|
11
|
+
rules: {
|
|
12
|
+
"@typescript-eslint/no-use-before-define": "off",
|
|
13
|
+
"@typescript-eslint/strict-boolean-expressions": "off",
|
|
14
|
+
"keyword-spacing": "off", // Off because it conflicts with typescript-formatter
|
|
15
|
+
"no-case-declarations": "off",
|
|
16
|
+
"prefer-arrow/prefer-arrow-functions": "off",
|
|
17
|
+
},
|
|
18
|
+
};
|
package/.mocharc.js
CHANGED
|
@@ -3,9 +3,9 @@
|
|
|
3
3
|
* Licensed under the MIT License.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
|
|
6
|
+
"use strict";
|
|
7
7
|
|
|
8
|
-
const getFluidTestMochaConfig = require(
|
|
8
|
+
const getFluidTestMochaConfig = require("@fluidframework/mocha-test-setup/mocharc-common");
|
|
9
9
|
|
|
10
10
|
const packageDir = __dirname;
|
|
11
11
|
const config = getFluidTestMochaConfig(packageDir);
|
package/.vscode/launch.json
CHANGED
|
@@ -1,15 +1,16 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
2
|
+
// Use IntelliSense to learn about possible attributes.
|
|
3
|
+
// Hover to view descriptions of existing attributes.
|
|
4
|
+
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
|
|
5
|
+
"version": "0.2.0",
|
|
6
|
+
"configurations": [
|
|
7
|
+
{
|
|
8
|
+
"name": "Merge Tree Test",
|
|
9
|
+
"type": "node",
|
|
10
|
+
"request": "launch",
|
|
11
|
+
"program": "${workspaceRoot}/../../../node_modules/mocha/bin/_mocha",
|
|
12
|
+
"args": ["dist/test", " --recursive", "--no-timeouts", "--exit"],
|
|
13
|
+
"cwd": "${workspaceRoot}"
|
|
14
|
+
}
|
|
15
|
+
]
|
|
16
|
+
}
|
package/README.md
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# @fluidframework/merge-tree
|
|
2
2
|
|
|
3
3
|
MergeTree is not a complete DDS by itself, but provides a reusable data structure for DDSes that must maintain a
|
|
4
|
-
sequence of collaboratively edited items.
|
|
4
|
+
sequence of collaboratively edited items. MergeTree is used in both SharedSequence and SharedMatrix.
|
|
5
5
|
|
|
6
6
|
See [GitHub](https://github.com/microsoft/FluidFramework) for more details on the Fluid Framework and packages within.
|
|
7
7
|
|
|
@@ -9,14 +9,14 @@ See [GitHub](https://github.com/microsoft/FluidFramework) for more details on th
|
|
|
9
9
|
|
|
10
10
|
The three basic operations provided by MergeTree are:
|
|
11
11
|
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
12
|
+
- `insert(start, segment)`
|
|
13
|
+
- `remove(start, end)`
|
|
14
|
+
- `annotate(start, end, propertySet)`
|
|
15
15
|
|
|
16
16
|
## Implementation
|
|
17
17
|
|
|
18
18
|
MergeTrees represent a sequence as an ordered list of segments. Each segment contains one or more consecutive values in
|
|
19
|
-
the sequence.
|
|
19
|
+
the sequence. For example, a SharedString contains segments of characters:
|
|
20
20
|
|
|
21
21
|
```
|
|
22
22
|
["The cat"], [" sat on the mat."]
|
|
@@ -64,9 +64,9 @@ remote client performed the operation on its MergeTree.
|
|
|
64
64
|
|
|
65
65
|
Conceptually, this is done by adjusting our naive linear search for the (segment, offset) in the following way:
|
|
66
66
|
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
67
|
+
- Segments inserted "after" the remote client's operation are skipped (i.e., have length 0)
|
|
68
|
+
- Segments tombstoned "after" the remote client's operation, but were inserted "prior" are included
|
|
69
|
+
(i.e., have their original length prior to tombstoning.)
|
|
70
70
|
|
|
71
71
|
...where "after" means the remote client's MergeTree had not yet applied the operation that inserted and/or
|
|
72
72
|
tombstoned the segment.
|
|
@@ -76,7 +76,7 @@ MergeTree we do two things:
|
|
|
76
76
|
|
|
77
77
|
1. The MergeTree tracks which client inserted/removed each segment and the sequence number (abbreviated "seq") assigned by the Fluid service to the
|
|
78
78
|
insertion/removal operation.
|
|
79
|
-
2. When sending a MergeTree op, the client includes the last seq# it has processed from the Fluid service.
|
|
79
|
+
2. When sending a MergeTree op, the client includes the last seq# it has processed from the Fluid service. This number
|
|
80
80
|
is known as an op's "reference sequence number" or "refSeq#"
|
|
81
81
|
|
|
82
82
|
The 'client' and 'refSeq' become new arguments to our search function:
|
|
@@ -87,10 +87,10 @@ The 'client' and 'refSeq' become new arguments to our search function:
|
|
|
87
87
|
|
|
88
88
|
A segment was inserted and/or removed on the remote client at the time client sent the operation if either:
|
|
89
89
|
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
90
|
+
- The referenced sequence number is greater than or equal the server-assigned sequence number of the operation
|
|
91
|
+
that inserted/removed the segment.
|
|
92
|
+
- The client sent the operation that resulted in insertion/removal. (In which case, the client hadn't yet received
|
|
93
|
+
their sequenced op from the server but was aware of the insertion/removal because the client produced it locally.)
|
|
94
94
|
|
|
95
95
|
If both above conditions are false, then the insertion/removal happened "after" the remote operation, and
|
|
96
96
|
consequently should be ignored during the search.
|
package/api-extractor.json
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
{
|
|
2
|
-
|
|
3
|
-
|
|
2
|
+
"$schema": "https://developer.microsoft.com/json-schemas/api-extractor/v7/api-extractor.schema.json",
|
|
3
|
+
"extends": "@fluidframework/build-common/api-extractor-common-report.json"
|
|
4
4
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MergeTreeTextHelper.d.ts","sourceRoot":"","sources":["../src/MergeTreeTextHelper.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,oBAAoB,EAAe,MAAM,eAAe,CAAC;AAQlE,qBAAa,mBAAoB,YAAW,oBAAoB;
|
|
1
|
+
{"version":3,"file":"MergeTreeTextHelper.d.ts","sourceRoot":"","sources":["../src/MergeTreeTextHelper.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAC;AACxC,OAAO,EAAE,oBAAoB,EAAe,MAAM,eAAe,CAAC;AAQlE,qBAAa,mBAAoB,YAAW,oBAAoB;IACnD,OAAO,CAAC,QAAQ,CAAC,SAAS;gBAAT,SAAS,EAAE,SAAS;IAE1C,OAAO,CACb,MAAM,EAAE,MAAM,EACd,QAAQ,EAAE,MAAM,EAChB,WAAW,SAAK,EAChB,KAAK,CAAC,EAAE,MAAM,EACd,GAAG,CAAC,EAAE,MAAM;IAiBb,OAAO,CAAC,aAAa;CAYrB"}
|
|
@@ -27,7 +27,7 @@ class MergeTreeTextHelper {
|
|
|
27
27
|
exports.MergeTreeTextHelper = MergeTreeTextHelper;
|
|
28
28
|
function gatherText(segment, pos, refSeq, clientId, start, end, { textSegment, placeholder }) {
|
|
29
29
|
if (textSegment_1.TextSegment.is(segment)) {
|
|
30
|
-
if (
|
|
30
|
+
if (start <= 0 && end >= segment.text.length) {
|
|
31
31
|
textSegment.text += segment.text;
|
|
32
32
|
}
|
|
33
33
|
else {
|
|
@@ -38,8 +38,7 @@ function gatherText(segment, pos, refSeq, clientId, start, end, { textSegment, p
|
|
|
38
38
|
}
|
|
39
39
|
}
|
|
40
40
|
else if (placeholder && placeholder.length > 0) {
|
|
41
|
-
const placeholderText = placeholder === "*" ?
|
|
42
|
-
`\n${segment}` : placeholder.repeat(segment.cachedLength);
|
|
41
|
+
const placeholderText = placeholder === "*" ? `\n${segment}` : placeholder.repeat(segment.cachedLength);
|
|
43
42
|
textSegment.text += placeholderText;
|
|
44
43
|
}
|
|
45
44
|
return true;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"MergeTreeTextHelper.js","sourceRoot":"","sources":["../src/MergeTreeTextHelper.ts"],"names":[],"mappings":";AAAA;;;GAGG;;;AAKH,+CAAkE;AAQlE,MAAa,mBAAmB;
|
|
1
|
+
{"version":3,"file":"MergeTreeTextHelper.js","sourceRoot":"","sources":["../src/MergeTreeTextHelper.ts"],"names":[],"mappings":";AAAA;;;GAGG;;;AAKH,+CAAkE;AAQlE,MAAa,mBAAmB;IAC/B,YAA6B,SAAoB;QAApB,cAAS,GAAT,SAAS,CAAW;IAAG,CAAC;IAE9C,OAAO,CACb,MAAc,EACd,QAAgB,EAChB,WAAW,GAAG,EAAE,EAChB,KAAc,EACd,GAAY;QAEZ,MAAM,KAAK,GAAG,IAAI,CAAC,aAAa,CAAC,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,QAAQ,CAAC,CAAC;QAE/D,MAAM,KAAK,GAAqB,EAAE,WAAW,EAAE,IAAI,yBAAW,CAAC,EAAE,CAAC,EAAE,WAAW,EAAE,CAAC;QAElF,IAAI,CAAC,SAAS,CAAC,QAAQ,CACtB,UAAU,EACV,MAAM,EACN,QAAQ,EACR,KAAK,EACL,KAAK,CAAC,KAAK,EACX,KAAK,CAAC,GAAG,CACT,CAAC;QACF,OAAO,KAAK,CAAC,WAAW,CAAC,IAAI,CAAC;IAC/B,CAAC;IAEO,aAAa,CACpB,KAAyB,EACzB,GAAuB,EACvB,MAAc,EACd,QAAgB;QAEhB,MAAM,KAAK,GAAkB;YAC5B,GAAG,EAAE,GAAG,aAAH,GAAG,cAAH,GAAG,GAAI,IAAI,CAAC,SAAS,CAAC,SAAS,CAAC,MAAM,EAAE,QAAQ,CAAC;YACtD,KAAK,EAAE,KAAK,aAAL,KAAK,cAAL,KAAK,GAAI,CAAC;SACjB,CAAC;QACF,OAAO,KAAK,CAAC;IACd,CAAC;CACD;AArCD,kDAqCC;AAED,SAAS,UAAU,CAClB,OAAiB,EACjB,GAAW,EACX,MAAc,EACd,QAAgB,EAChB,KAAa,EACb,GAAW,EACX,EAAE,WAAW,EAAE,WAAW,EAAoB;IAE9C,IAAI,yBAAW,CAAC,EAAE,CAAC,OAAO,CAAC,EAAE;QAC5B,IAAI,KAAK,IAAI,CAAC,IAAI,GAAG,IAAI,OAAO,CAAC,IAAI,CAAC,MAAM,EAAE;YAC7C,WAAW,CAAC,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC;SACjC;aAAM;YACN,MAAM,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,MAAM,CAAC;YACnC,MAAM,MAAM,GAAG,KAAK,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,KAAK,CAAC;YACrC,MAAM,IAAI,GAAG,GAAG,IAAI,MAAM,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,GAAG,CAAC;YAC7C,WAAW,CAAC,IAAI,IAAI,OAAO,CAAC,IAAI,CAAC,SAAS,CAAC,MAAM,EAAE,IAAI,CAAC,CAAC;SACzD;KACD;SAAM,IAAI,WAAW,IAAI,WAAW,CAAC,MAAM,GAAG,CAAC,EAAE;QACjD,MAAM,eAAe,GACpB,WAAW,KAAK,GAAG,CAAC,CAAC,CAAC,KAAK,OAAO,EAAE,CAAC,CAAC,CAAC,WAAW,CAAC,MAAM,CAAC,OAAO,CAAC,YAAY,CAAC,CAAC;QACjF,WAAW,CAAC,IAAI,IAAI,eAAe,CAAC;KACpC;IAED,OAAO,IAAI,CAAC;AACb,CAAC","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { IIntegerRange } from \"./base\";\nimport { ISegment } from \"./mergeTreeNodes\";\nimport { MergeTree } from \"./mergeTree\";\nimport { IMergeTreeTextHelper, TextSegment } from \"./textSegment\";\n\ninterface ITextAccumulator {\n\ttextSegment: TextSegment;\n\tplaceholder?: string;\n\tparallelArrays?: boolean;\n}\n\nexport class MergeTreeTextHelper implements IMergeTreeTextHelper {\n\tconstructor(private readonly mergeTree: MergeTree) {}\n\n\tpublic getText(\n\t\trefSeq: number,\n\t\tclientId: number,\n\t\tplaceholder = \"\",\n\t\tstart?: number,\n\t\tend?: number,\n\t) {\n\t\tconst range = this.getValidRange(start, end, refSeq, clientId);\n\n\t\tconst accum: ITextAccumulator = { textSegment: new TextSegment(\"\"), placeholder };\n\n\t\tthis.mergeTree.mapRange<ITextAccumulator>(\n\t\t\tgatherText,\n\t\t\trefSeq,\n\t\t\tclientId,\n\t\t\taccum,\n\t\t\trange.start,\n\t\t\trange.end,\n\t\t);\n\t\treturn accum.textSegment.text;\n\t}\n\n\tprivate getValidRange(\n\t\tstart: number | undefined,\n\t\tend: number | undefined,\n\t\trefSeq: number,\n\t\tclientId: number,\n\t): IIntegerRange {\n\t\tconst range: IIntegerRange = {\n\t\t\tend: end ?? this.mergeTree.getLength(refSeq, clientId),\n\t\t\tstart: start ?? 0,\n\t\t};\n\t\treturn range;\n\t}\n}\n\nfunction gatherText(\n\tsegment: ISegment,\n\tpos: number,\n\trefSeq: number,\n\tclientId: number,\n\tstart: number,\n\tend: number,\n\t{ textSegment, placeholder }: ITextAccumulator,\n): boolean {\n\tif (TextSegment.is(segment)) {\n\t\tif (start <= 0 && end >= segment.text.length) {\n\t\t\ttextSegment.text += segment.text;\n\t\t} else {\n\t\t\tconst seglen = segment.text.length;\n\t\t\tconst _start = start < 0 ? 0 : start;\n\t\t\tconst _end = end >= seglen ? undefined : end;\n\t\t\ttextSegment.text += segment.text.substring(_start, _end);\n\t\t}\n\t} else if (placeholder && placeholder.length > 0) {\n\t\tconst placeholderText =\n\t\t\tplaceholder === \"*\" ? `\\n${segment}` : placeholder.repeat(segment.cachedLength);\n\t\ttextSegment.text += placeholderText;\n\t}\n\n\treturn true;\n}\n"]}
|
|
@@ -2,7 +2,12 @@
|
|
|
2
2
|
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
3
|
* Licensed under the MIT License.
|
|
4
4
|
*/
|
|
5
|
-
import { AttributionKey
|
|
5
|
+
import { AttributionKey } from "@fluidframework/runtime-definitions";
|
|
6
|
+
import { AttributionPolicy } from "./mergeTree";
|
|
7
|
+
import { ISegment } from "./mergeTreeNodes";
|
|
8
|
+
/**
|
|
9
|
+
* @internal
|
|
10
|
+
*/
|
|
6
11
|
export interface SerializedAttributionCollection {
|
|
7
12
|
/**
|
|
8
13
|
* Parallel array with posBreakpoints which tracks the seq of insertion.
|
|
@@ -10,10 +15,28 @@ export interface SerializedAttributionCollection {
|
|
|
10
15
|
* between offsets 0 and 3 was inserted at seq 45 and the section of the string between
|
|
11
16
|
* 3 and the length of the string was inserted at seq 46.
|
|
12
17
|
*/
|
|
13
|
-
seqs: number[];
|
|
18
|
+
seqs: (number | AttributionKey)[];
|
|
14
19
|
posBreakpoints: number[];
|
|
15
20
|
length: number;
|
|
16
21
|
}
|
|
22
|
+
/**
|
|
23
|
+
* @internal
|
|
24
|
+
* @sealed
|
|
25
|
+
*/
|
|
26
|
+
export interface IAttributionCollectionSerializer {
|
|
27
|
+
/**
|
|
28
|
+
* @internal
|
|
29
|
+
*/
|
|
30
|
+
serializeAttributionCollections(segments: Iterable<{
|
|
31
|
+
attribution?: IAttributionCollection<AttributionKey>;
|
|
32
|
+
cachedLength: number;
|
|
33
|
+
}>): SerializedAttributionCollection;
|
|
34
|
+
/**
|
|
35
|
+
* Populates attribution information on segments using the provided summary.
|
|
36
|
+
* @internal
|
|
37
|
+
*/
|
|
38
|
+
populateAttributionCollections(segments: Iterable<ISegment>, summary: SerializedAttributionCollection): void;
|
|
39
|
+
}
|
|
17
40
|
/**
|
|
18
41
|
* @alpha
|
|
19
42
|
*/
|
|
@@ -44,11 +67,12 @@ export interface IAttributionCollection<T> {
|
|
|
44
67
|
/** @internal */
|
|
45
68
|
clone(): IAttributionCollection<T>;
|
|
46
69
|
}
|
|
70
|
+
export declare function areEqualAttributionKeys(a: AttributionKey, b: AttributionKey): boolean;
|
|
47
71
|
export declare class AttributionCollection implements IAttributionCollection<AttributionKey> {
|
|
48
72
|
private _length;
|
|
49
73
|
private offsets;
|
|
50
|
-
private
|
|
51
|
-
constructor(baseEntry:
|
|
74
|
+
private keys;
|
|
75
|
+
constructor(baseEntry: AttributionKey, _length: number);
|
|
52
76
|
getAtOffset(offset: number): AttributionKey;
|
|
53
77
|
private findIndex;
|
|
54
78
|
get length(): number;
|
|
@@ -74,4 +98,11 @@ export declare class AttributionCollection implements IAttributionCollection<Att
|
|
|
74
98
|
cachedLength: number;
|
|
75
99
|
}>): SerializedAttributionCollection;
|
|
76
100
|
}
|
|
101
|
+
/**
|
|
102
|
+
* @alpha
|
|
103
|
+
* @returns - An {@link AttributionPolicy} which tracks only insertion of content.
|
|
104
|
+
* Content is only attributed at ack time, unless the container is in a detached state.
|
|
105
|
+
* Detached content is attributed with a {@link @fluidframework/runtime-definitions#DetachedAttributionKey}.
|
|
106
|
+
*/
|
|
107
|
+
export declare function createInsertOnlyAttributionPolicy(): AttributionPolicy;
|
|
77
108
|
//# sourceMappingURL=attributionCollection.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"attributionCollection.d.ts","sourceRoot":"","sources":["../src/attributionCollection.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAGH,OAAO,
|
|
1
|
+
{"version":3,"file":"attributionCollection.d.ts","sourceRoot":"","sources":["../src/attributionCollection.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAGH,OAAO,EACN,cAAc,EAGd,MAAM,qCAAqC,CAAC;AAC7C,OAAO,EAAE,iBAAiB,EAAE,MAAM,aAAa,CAAC;AAQhD,OAAO,EAAE,QAAQ,EAAE,MAAM,kBAAkB,CAAC;AAG5C;;GAEG;AACH,MAAM,WAAW,+BAA+B;IAC/C;;;;;OAKG;IACH,IAAI,EAAE,CAAC,MAAM,GAAG,cAAc,CAAC,EAAE,CAAC;IAClC,cAAc,EAAE,MAAM,EAAE,CAAC;IAEzB,MAAM,EAAE,MAAM,CAAC;CACf;AAED;;;GAGG;AACH,MAAM,WAAW,gCAAgC;IAChD;;OAEG;IACH,+BAA+B,CAC9B,QAAQ,EAAE,QAAQ,CAAC;QAClB,WAAW,CAAC,EAAE,sBAAsB,CAAC,cAAc,CAAC,CAAC;QACrD,YAAY,EAAE,MAAM,CAAC;KACrB,CAAC,GACA,+BAA+B,CAAC;IAEnC;;;OAGG;IACH,8BAA8B,CAC7B,QAAQ,EAAE,QAAQ,CAAC,QAAQ,CAAC,EAC5B,OAAO,EAAE,+BAA+B,GACtC,IAAI,CAAC;CACR;AAED;;GAEG;AACH,MAAM,WAAW,sBAAsB,CAAC,CAAC;IACxC;;OAEG;IACH,WAAW,CAAC,MAAM,EAAE,MAAM,GAAG,CAAC,CAAC;IAE/B;;OAEG;IACH,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IAExB;;;;;;OAMG;IACH,MAAM,IAAI,QAAQ,CAAC;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,CAAC,CAAA;KAAE,CAAC,CAAC;IAE/C,gBAAgB;IAChB,OAAO,CAAC,GAAG,EAAE,MAAM,GAAG,sBAAsB,CAAC,CAAC,CAAC,CAAC;IAEhD,gBAAgB;IAChB,MAAM,CAAC,KAAK,EAAE,sBAAsB,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;IAE/C,gBAAgB;IAChB,KAAK,IAAI,sBAAsB,CAAC,CAAC,CAAC,CAAC;CACnC;AAED,wBAAgB,uBAAuB,CAAC,CAAC,EAAE,cAAc,EAAE,CAAC,EAAE,cAAc,GAAG,OAAO,CAcrF;AAED,qBAAa,qBAAsB,YAAW,sBAAsB,CAAC,cAAc,CAAC;IAIrC,OAAO,CAAC,OAAO;IAH7D,OAAO,CAAC,OAAO,CAAW;IAC1B,OAAO,CAAC,IAAI,CAAmB;gBAEZ,SAAS,EAAE,cAAc,EAAU,OAAO,EAAE,MAAM;IAK9D,WAAW,CAAC,MAAM,EAAE,MAAM,GAAG,cAAc;IAKlD,OAAO,CAAC,SAAS;IAWjB,IAAW,MAAM,IAAI,MAAM,CAE1B;IAED;;OAEG;IACI,OAAO,CAAC,GAAG,EAAE,MAAM,GAAG,qBAAqB;IAgB3C,MAAM,CAAC,KAAK,EAAE,qBAAqB,GAAG,IAAI;IAW1C,MAAM,IAAI;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,cAAc,CAAA;KAAE,EAAE;IAQnD,KAAK,IAAI,qBAAqB;IAOrC;;OAEG;WACW,8BAA8B,CAC3C,QAAQ,EAAE,QAAQ,CAAC,QAAQ,CAAC,EAC5B,OAAO,EAAE,+BAA+B,GACtC,IAAI;IAsCP;;OAEG;WACW,+BAA+B,CAC5C,QAAQ,EAAE,QAAQ,CAAC;QAClB,WAAW,CAAC,EAAE,sBAAsB,CAAC,cAAc,CAAC,CAAC;QACrD,YAAY,EAAE,MAAM,CAAC;KACrB,CAAC,GACA,+BAA+B;CAwClC;AAED;;;;;GAKG;AACH,wBAAgB,iCAAiC,IAAI,iBAAiB,CAsErE"}
|
|
@@ -4,17 +4,35 @@
|
|
|
4
4
|
* Licensed under the MIT License.
|
|
5
5
|
*/
|
|
6
6
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
7
|
-
exports.AttributionCollection = void 0;
|
|
7
|
+
exports.createInsertOnlyAttributionPolicy = exports.AttributionCollection = exports.areEqualAttributionKeys = void 0;
|
|
8
8
|
const common_utils_1 = require("@fluidframework/common-utils");
|
|
9
|
+
const constants_1 = require("./constants");
|
|
10
|
+
const mergeTreeDeltaCallback_1 = require("./mergeTreeDeltaCallback");
|
|
11
|
+
const ops_1 = require("./ops");
|
|
12
|
+
function areEqualAttributionKeys(a, b) {
|
|
13
|
+
if (a.type !== b.type) {
|
|
14
|
+
return false;
|
|
15
|
+
}
|
|
16
|
+
// Note: TS can't narrow the type of b inside this switch statement, hence the need for casting.
|
|
17
|
+
switch (a.type) {
|
|
18
|
+
case "op":
|
|
19
|
+
return a.seq === b.seq;
|
|
20
|
+
case "detached":
|
|
21
|
+
return a.id === b.id;
|
|
22
|
+
default:
|
|
23
|
+
(0, common_utils_1.unreachableCase)(a, "Unhandled AttributionKey type");
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
exports.areEqualAttributionKeys = areEqualAttributionKeys;
|
|
9
27
|
class AttributionCollection {
|
|
10
28
|
constructor(baseEntry, _length) {
|
|
11
29
|
this._length = _length;
|
|
12
30
|
this.offsets = [0];
|
|
13
|
-
this.
|
|
31
|
+
this.keys = [baseEntry];
|
|
14
32
|
}
|
|
15
33
|
getAtOffset(offset) {
|
|
16
34
|
(0, common_utils_1.assert)(offset >= 0 && offset < this._length, 0x443 /* Requested offset should be valid */);
|
|
17
|
-
return
|
|
35
|
+
return this.keys[this.findIndex(offset)];
|
|
18
36
|
}
|
|
19
37
|
findIndex(offset) {
|
|
20
38
|
// Note: maximum length here is 256 for text segments. Perf testing shows that linear scan beats binary search
|
|
@@ -34,38 +52,38 @@ class AttributionCollection {
|
|
|
34
52
|
*/
|
|
35
53
|
splitAt(pos) {
|
|
36
54
|
const splitIndex = this.findIndex(pos);
|
|
37
|
-
const splitBaseEntry = this.
|
|
55
|
+
const splitBaseEntry = this.keys[splitIndex];
|
|
38
56
|
const splitCollection = new AttributionCollection(splitBaseEntry, this.length - pos);
|
|
39
|
-
for (let i = splitIndex + 1; i < this.
|
|
57
|
+
for (let i = splitIndex + 1; i < this.keys.length; i++) {
|
|
40
58
|
splitCollection.offsets.push(this.offsets[i] - pos);
|
|
41
|
-
splitCollection.
|
|
59
|
+
splitCollection.keys.push(this.keys[i]);
|
|
42
60
|
}
|
|
43
61
|
const spliceIndex = this.offsets[splitIndex] === pos ? splitIndex : splitIndex + 1;
|
|
44
|
-
this.
|
|
62
|
+
this.keys.splice(spliceIndex);
|
|
45
63
|
this.offsets.splice(spliceIndex);
|
|
46
64
|
this._length = pos;
|
|
47
65
|
return splitCollection;
|
|
48
66
|
}
|
|
49
67
|
append(other) {
|
|
50
|
-
const lastEntry = this.
|
|
51
|
-
for (let i = 0; i < other.
|
|
52
|
-
if (i !== 0 || lastEntry
|
|
68
|
+
const lastEntry = this.keys[this.keys.length - 1];
|
|
69
|
+
for (let i = 0; i < other.keys.length; i++) {
|
|
70
|
+
if (i !== 0 || !areEqualAttributionKeys(lastEntry, other.keys[i])) {
|
|
53
71
|
this.offsets.push(other.offsets[i] + this.length);
|
|
54
|
-
this.
|
|
72
|
+
this.keys.push(other.keys[i]);
|
|
55
73
|
}
|
|
56
74
|
}
|
|
57
75
|
this._length += other.length;
|
|
58
76
|
}
|
|
59
77
|
getAll() {
|
|
60
|
-
const results = new Array(this.
|
|
61
|
-
for (let i = 0; i < this.
|
|
62
|
-
results[i] = { offset: this.offsets[i], key:
|
|
78
|
+
const results = new Array(this.keys.length);
|
|
79
|
+
for (let i = 0; i < this.keys.length; i++) {
|
|
80
|
+
results[i] = { offset: this.offsets[i], key: this.keys[i] };
|
|
63
81
|
}
|
|
64
82
|
return results;
|
|
65
83
|
}
|
|
66
84
|
clone() {
|
|
67
|
-
const copy = new AttributionCollection(0, this.length);
|
|
68
|
-
copy.
|
|
85
|
+
const copy = new AttributionCollection(this.keys[0], this.length);
|
|
86
|
+
copy.keys = this.keys.slice();
|
|
69
87
|
copy.offsets = this.offsets.slice();
|
|
70
88
|
return copy;
|
|
71
89
|
}
|
|
@@ -79,13 +97,15 @@ class AttributionCollection {
|
|
|
79
97
|
let currentInfo = seqs[curIndex];
|
|
80
98
|
let cumulativeSegPos = 0;
|
|
81
99
|
for (const segment of segments) {
|
|
82
|
-
const attribution = new AttributionCollection(currentInfo, segment.cachedLength);
|
|
100
|
+
const attribution = new AttributionCollection(typeof currentInfo === "object" ? currentInfo : { type: "op", seq: currentInfo }, segment.cachedLength);
|
|
83
101
|
while (posBreakpoints[curIndex] < cumulativeSegPos + segment.cachedLength) {
|
|
84
102
|
currentInfo = seqs[curIndex];
|
|
85
103
|
const nextOffset = posBreakpoints[curIndex] - cumulativeSegPos;
|
|
86
104
|
if (attribution.offsets[attribution.offsets.length - 1] !== nextOffset) {
|
|
87
105
|
attribution.offsets.push(nextOffset);
|
|
88
|
-
attribution.
|
|
106
|
+
attribution.keys.push(typeof currentInfo === "object"
|
|
107
|
+
? currentInfo
|
|
108
|
+
: { type: "op", seq: currentInfo });
|
|
89
109
|
}
|
|
90
110
|
curIndex++;
|
|
91
111
|
}
|
|
@@ -110,12 +130,13 @@ class AttributionCollection {
|
|
|
110
130
|
for (const segment of segments) {
|
|
111
131
|
if (segment.attribution) {
|
|
112
132
|
segmentsWithAttribution++;
|
|
113
|
-
for (const { offset, key
|
|
114
|
-
if (
|
|
133
|
+
for (const { offset, key } of (_b = (_a = segment.attribution) === null || _a === void 0 ? void 0 : _a.getAll()) !== null && _b !== void 0 ? _b : []) {
|
|
134
|
+
if (!mostRecentAttributionKey ||
|
|
135
|
+
!areEqualAttributionKeys(key, mostRecentAttributionKey)) {
|
|
115
136
|
posBreakpoints.push(offset + cumulativePos);
|
|
116
|
-
seqs.push(
|
|
137
|
+
seqs.push(key.type === "op" ? key.seq : key);
|
|
117
138
|
}
|
|
118
|
-
mostRecentAttributionKey =
|
|
139
|
+
mostRecentAttributionKey = key;
|
|
119
140
|
}
|
|
120
141
|
}
|
|
121
142
|
else {
|
|
@@ -124,9 +145,67 @@ class AttributionCollection {
|
|
|
124
145
|
cumulativePos += segment.cachedLength;
|
|
125
146
|
}
|
|
126
147
|
(0, common_utils_1.assert)(segmentsWithAttribution === 0 || segmentsWithoutAttribution === 0, 0x446 /* Expected either all segments or no segments to have attribution information. */);
|
|
127
|
-
const blobContents = {
|
|
148
|
+
const blobContents = {
|
|
149
|
+
seqs,
|
|
150
|
+
posBreakpoints,
|
|
151
|
+
length: cumulativePos,
|
|
152
|
+
};
|
|
128
153
|
return blobContents;
|
|
129
154
|
}
|
|
130
155
|
}
|
|
131
156
|
exports.AttributionCollection = AttributionCollection;
|
|
157
|
+
/**
|
|
158
|
+
* @alpha
|
|
159
|
+
* @returns - An {@link AttributionPolicy} which tracks only insertion of content.
|
|
160
|
+
* Content is only attributed at ack time, unless the container is in a detached state.
|
|
161
|
+
* Detached content is attributed with a {@link @fluidframework/runtime-definitions#DetachedAttributionKey}.
|
|
162
|
+
*/
|
|
163
|
+
function createInsertOnlyAttributionPolicy() {
|
|
164
|
+
let unsubscribe;
|
|
165
|
+
return {
|
|
166
|
+
attach: (client) => {
|
|
167
|
+
(0, common_utils_1.assert)(unsubscribe === undefined, 0x557 /* cannot attach to multiple clients at once */);
|
|
168
|
+
const deltaCallback = (opArgs, { deltaSegments, operation }) => {
|
|
169
|
+
var _a;
|
|
170
|
+
if (operation !== ops_1.MergeTreeDeltaType.INSERT) {
|
|
171
|
+
return;
|
|
172
|
+
}
|
|
173
|
+
for (const { segment } of deltaSegments) {
|
|
174
|
+
if (segment.seq !== undefined && segment.seq !== constants_1.UnassignedSequenceNumber) {
|
|
175
|
+
const key = segment.seq === constants_1.UniversalSequenceNumber
|
|
176
|
+
? { type: "detached", id: 0 }
|
|
177
|
+
: { type: "op", seq: segment.seq };
|
|
178
|
+
(_a = segment.attribution) !== null && _a !== void 0 ? _a : (segment.attribution = new AttributionCollection(key, segment.cachedLength));
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
};
|
|
182
|
+
const maintenanceCallback = ({ deltaSegments, operation }, opArgs) => {
|
|
183
|
+
if (operation !== mergeTreeDeltaCallback_1.MergeTreeMaintenanceType.ACKNOWLEDGED ||
|
|
184
|
+
opArgs === undefined ||
|
|
185
|
+
opArgs.op.type !== ops_1.MergeTreeDeltaType.INSERT) {
|
|
186
|
+
return;
|
|
187
|
+
}
|
|
188
|
+
for (const { segment } of deltaSegments) {
|
|
189
|
+
(0, common_utils_1.assert)(segment.seq !== undefined, 0x558 /* segment.seq should be set after ack. */);
|
|
190
|
+
segment.attribution = new AttributionCollection({ type: "op", seq: segment.seq }, segment.cachedLength);
|
|
191
|
+
}
|
|
192
|
+
};
|
|
193
|
+
client.on("delta", deltaCallback);
|
|
194
|
+
client.on("maintenance", maintenanceCallback);
|
|
195
|
+
unsubscribe = () => {
|
|
196
|
+
client.off("delta", deltaCallback);
|
|
197
|
+
client.off("maintenance", maintenanceCallback);
|
|
198
|
+
};
|
|
199
|
+
},
|
|
200
|
+
detach: () => {
|
|
201
|
+
unsubscribe === null || unsubscribe === void 0 ? void 0 : unsubscribe();
|
|
202
|
+
unsubscribe = undefined;
|
|
203
|
+
},
|
|
204
|
+
get isAttached() {
|
|
205
|
+
return unsubscribe !== undefined;
|
|
206
|
+
},
|
|
207
|
+
serializer: AttributionCollection,
|
|
208
|
+
};
|
|
209
|
+
}
|
|
210
|
+
exports.createInsertOnlyAttributionPolicy = createInsertOnlyAttributionPolicy;
|
|
132
211
|
//# sourceMappingURL=attributionCollection.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"attributionCollection.js","sourceRoot":"","sources":["../src/attributionCollection.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 { assert } from \"@fluidframework/common-utils\";\nimport { AttributionKey, ISegment } from \"./mergeTreeNodes\";\n\nexport interface SerializedAttributionCollection {\n /**\n * Parallel array with posBreakpoints which tracks the seq of insertion.\n * Ex: if seqs is [45, 46] and posBreakpoints is [0, 3], the section of the string\n * between offsets 0 and 3 was inserted at seq 45 and the section of the string between\n * 3 and the length of the string was inserted at seq 46.\n */\n seqs: number[];\n posBreakpoints: number[];\n /* Total length; only necessary for validation */\n length: number;\n}\n\n/**\n * @alpha\n */\nexport interface IAttributionCollection<T> {\n /**\n * Retrieves the attribution key associated with the provided offset.\n */\n getAtOffset(offset: number): T;\n\n /**\n * Total length of all attribution keys in this collection.\n */\n readonly length: number;\n\n /**\n * Retrieve all key/offset pairs stored on this segment. Entries should be ordered by offset, such that\n * the `i`th result's attribution key applies to offsets in the open range between the `i`th offset and the\n * `i+1`th offset.\n * The last entry's key applies to the open interval from the last entry's offset to this collection's length.\n * @internal\n */\n getAll(): Iterable<{ offset: number; key: T; }>;\n\n /** @internal */\n splitAt(pos: number): IAttributionCollection<T>;\n\n /** @internal */\n append(other: IAttributionCollection<T>): void;\n\n /** @internal */\n clone(): IAttributionCollection<T>;\n}\n\n\nexport class AttributionCollection implements IAttributionCollection<AttributionKey> {\n private offsets: number[];\n private seqs: number[];\n\n public constructor(baseEntry: number, private _length: number) {\n this.offsets = [0];\n this.seqs = [baseEntry];\n }\n\n public getAtOffset(offset: number): AttributionKey {\n assert(offset >= 0 && offset < this._length, 0x443 /* Requested offset should be valid */);\n return { type: \"op\", seq: this.seqs[this.findIndex(offset)] };\n }\n\n private findIndex(offset: number): number {\n // Note: maximum length here is 256 for text segments. Perf testing shows that linear scan beats binary search\n // for attribution collections with under ~64 entries, and even at maximum size (which would require a maximum\n // length segment with every offset having different attribution), getAtOffset is on the order of 100ns.\n let i = 0;\n while (i < this.offsets.length && offset > this.offsets[i]) {\n i++;\n }\n return this.offsets[i] === offset ? i : i - 1;\n }\n\n public get length(): number {\n return this._length;\n }\n\n /**\n * Splits this attribution collection into two with entries for [0, pos) and [pos, length).\n */\n public splitAt(pos: number): AttributionCollection {\n const splitIndex = this.findIndex(pos);\n const splitBaseEntry = this.seqs[splitIndex];\n const splitCollection = new AttributionCollection(splitBaseEntry, this.length - pos);\n for (let i = splitIndex + 1; i < this.seqs.length; i++) {\n splitCollection.offsets.push(this.offsets[i] - pos);\n splitCollection.seqs.push(this.seqs[i]);\n }\n\n const spliceIndex = this.offsets[splitIndex] === pos ? splitIndex : splitIndex + 1\n this.seqs.splice(spliceIndex);\n this.offsets.splice(spliceIndex);\n this._length = pos;\n return splitCollection;\n }\n\n public append(other: AttributionCollection): void {\n const lastEntry = this.seqs[this.seqs.length - 1];\n for (let i = 0; i < other.seqs.length; i++) {\n if (i !== 0 || lastEntry !== other.seqs[i]) {\n this.offsets.push(other.offsets[i] + this.length);\n this.seqs.push(other.seqs[i]);\n }\n }\n this._length += other.length;\n }\n\n public getAll(): { offset: number; key: AttributionKey; }[] {\n const results: { offset: number; key: AttributionKey }[] = new Array(this.seqs.length);\n for (let i = 0; i < this.seqs.length; i++) {\n results[i] = { offset: this.offsets[i], key: { type: \"op\", seq: this.seqs[i] }};\n }\n return results;\n }\n\n public clone(): AttributionCollection {\n const copy = new AttributionCollection(0, this.length);\n copy.seqs = this.seqs.slice();\n copy.offsets = this.offsets.slice();\n return copy;\n }\n\n /**\n * Rehydrates attribution information from its serialized form into the provided iterable of consecutive segments.\n */\n public static populateAttributionCollections(\n segments: Iterable<ISegment>,\n summary: SerializedAttributionCollection,\n ): void {\n const { seqs, posBreakpoints } = summary;\n assert(\n seqs.length === posBreakpoints.length && seqs.length > 0,\n 0x445 /* Invalid attribution summary blob provided */);\n let curIndex = 0;\n let currentInfo = seqs[curIndex];\n let cumulativeSegPos = 0;\n \n for (const segment of segments) {\n const attribution = new AttributionCollection(currentInfo, segment.cachedLength);\n while (posBreakpoints[curIndex] < cumulativeSegPos + segment.cachedLength) {\n currentInfo = seqs[curIndex];\n const nextOffset = posBreakpoints[curIndex] - cumulativeSegPos;\n if (attribution.offsets[attribution.offsets.length - 1] !== nextOffset) {\n attribution.offsets.push(nextOffset);\n attribution.seqs.push(currentInfo);\n }\n curIndex++;\n }\n\n if (posBreakpoints[curIndex] === cumulativeSegPos + segment.cachedLength) {\n currentInfo = seqs[curIndex];\n }\n\n segment.attribution = attribution;\n cumulativeSegPos += segment.cachedLength;\n }\n }\n\n /**\n * Condenses attribution information on consecutive segments into a `SerializedAttributionCollection`\n */\n public static serializeAttributionCollections(\n segments: Iterable<{ attribution?: IAttributionCollection<AttributionKey>; cachedLength: number; }>,\n ): SerializedAttributionCollection {\n const posBreakpoints: number[] = [];\n const seqs: number[] = [];\n let mostRecentAttributionKey: number | undefined;\n let cumulativePos = 0;\n\n let segmentsWithAttribution = 0;\n let segmentsWithoutAttribution = 0;\n for (const segment of segments) {\n if (segment.attribution) {\n segmentsWithAttribution++;\n for (const { offset, key: info } of segment.attribution?.getAll() ?? []) {\n if (info.seq !== mostRecentAttributionKey) {\n posBreakpoints.push(offset + cumulativePos);\n seqs.push(info.seq);\n }\n mostRecentAttributionKey = info.seq;\n }\n } else {\n segmentsWithoutAttribution++;\n }\n\n cumulativePos += segment.cachedLength;\n }\n\n assert(segmentsWithAttribution === 0 || segmentsWithoutAttribution === 0,\n 0x446 /* Expected either all segments or no segments to have attribution information. */);\n\n const blobContents: SerializedAttributionCollection = { seqs, posBreakpoints, length: cumulativePos };\n return blobContents;\n }\n}\n"]}
|
|
1
|
+
{"version":3,"file":"attributionCollection.js","sourceRoot":"","sources":["../src/attributionCollection.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 { assert, unreachableCase } from \"@fluidframework/common-utils\";\nimport {\n\tAttributionKey,\n\tOpAttributionKey,\n\tDetachedAttributionKey,\n} from \"@fluidframework/runtime-definitions\";\nimport { AttributionPolicy } from \"./mergeTree\";\nimport { Client } from \"./client\";\nimport { UnassignedSequenceNumber, UniversalSequenceNumber } from \"./constants\";\nimport {\n\tMergeTreeDeltaCallback,\n\tMergeTreeMaintenanceCallback,\n\tMergeTreeMaintenanceType,\n} from \"./mergeTreeDeltaCallback\";\nimport { ISegment } from \"./mergeTreeNodes\";\nimport { MergeTreeDeltaType } from \"./ops\";\n\n/**\n * @internal\n */\nexport interface SerializedAttributionCollection {\n\t/**\n\t * Parallel array with posBreakpoints which tracks the seq of insertion.\n\t * Ex: if seqs is [45, 46] and posBreakpoints is [0, 3], the section of the string\n\t * between offsets 0 and 3 was inserted at seq 45 and the section of the string between\n\t * 3 and the length of the string was inserted at seq 46.\n\t */\n\tseqs: (number | AttributionKey)[];\n\tposBreakpoints: number[];\n\t/* Total length; only necessary for validation */\n\tlength: number;\n}\n\n/**\n * @internal\n * @sealed\n */\nexport interface IAttributionCollectionSerializer {\n\t/**\n\t * @internal\n\t */\n\tserializeAttributionCollections(\n\t\tsegments: Iterable<{\n\t\t\tattribution?: IAttributionCollection<AttributionKey>;\n\t\t\tcachedLength: number;\n\t\t}>,\n\t): SerializedAttributionCollection;\n\n\t/**\n\t * Populates attribution information on segments using the provided summary.\n\t * @internal\n\t */\n\tpopulateAttributionCollections(\n\t\tsegments: Iterable<ISegment>,\n\t\tsummary: SerializedAttributionCollection,\n\t): void;\n}\n\n/**\n * @alpha\n */\nexport interface IAttributionCollection<T> {\n\t/**\n\t * Retrieves the attribution key associated with the provided offset.\n\t */\n\tgetAtOffset(offset: number): T;\n\n\t/**\n\t * Total length of all attribution keys in this collection.\n\t */\n\treadonly length: number;\n\n\t/**\n\t * Retrieve all key/offset pairs stored on this segment. Entries should be ordered by offset, such that\n\t * the `i`th result's attribution key applies to offsets in the open range between the `i`th offset and the\n\t * `i+1`th offset.\n\t * The last entry's key applies to the open interval from the last entry's offset to this collection's length.\n\t * @internal\n\t */\n\tgetAll(): Iterable<{ offset: number; key: T }>;\n\n\t/** @internal */\n\tsplitAt(pos: number): IAttributionCollection<T>;\n\n\t/** @internal */\n\tappend(other: IAttributionCollection<T>): void;\n\n\t/** @internal */\n\tclone(): IAttributionCollection<T>;\n}\n\nexport function areEqualAttributionKeys(a: AttributionKey, b: AttributionKey): boolean {\n\tif (a.type !== b.type) {\n\t\treturn false;\n\t}\n\n\t// Note: TS can't narrow the type of b inside this switch statement, hence the need for casting.\n\tswitch (a.type) {\n\t\tcase \"op\":\n\t\t\treturn a.seq === (b as OpAttributionKey).seq;\n\t\tcase \"detached\":\n\t\t\treturn a.id === (b as DetachedAttributionKey).id;\n\t\tdefault:\n\t\t\tunreachableCase(a, \"Unhandled AttributionKey type\");\n\t}\n}\n\nexport class AttributionCollection implements IAttributionCollection<AttributionKey> {\n\tprivate offsets: number[];\n\tprivate keys: AttributionKey[];\n\n\tpublic constructor(baseEntry: AttributionKey, private _length: number) {\n\t\tthis.offsets = [0];\n\t\tthis.keys = [baseEntry];\n\t}\n\n\tpublic getAtOffset(offset: number): AttributionKey {\n\t\tassert(offset >= 0 && offset < this._length, 0x443 /* Requested offset should be valid */);\n\t\treturn this.keys[this.findIndex(offset)];\n\t}\n\n\tprivate findIndex(offset: number): number {\n\t\t// Note: maximum length here is 256 for text segments. Perf testing shows that linear scan beats binary search\n\t\t// for attribution collections with under ~64 entries, and even at maximum size (which would require a maximum\n\t\t// length segment with every offset having different attribution), getAtOffset is on the order of 100ns.\n\t\tlet i = 0;\n\t\twhile (i < this.offsets.length && offset > this.offsets[i]) {\n\t\t\ti++;\n\t\t}\n\t\treturn this.offsets[i] === offset ? i : i - 1;\n\t}\n\n\tpublic get length(): number {\n\t\treturn this._length;\n\t}\n\n\t/**\n\t * Splits this attribution collection into two with entries for [0, pos) and [pos, length).\n\t */\n\tpublic splitAt(pos: number): AttributionCollection {\n\t\tconst splitIndex = this.findIndex(pos);\n\t\tconst splitBaseEntry = this.keys[splitIndex];\n\t\tconst splitCollection = new AttributionCollection(splitBaseEntry, this.length - pos);\n\t\tfor (let i = splitIndex + 1; i < this.keys.length; i++) {\n\t\t\tsplitCollection.offsets.push(this.offsets[i] - pos);\n\t\t\tsplitCollection.keys.push(this.keys[i]);\n\t\t}\n\n\t\tconst spliceIndex = this.offsets[splitIndex] === pos ? splitIndex : splitIndex + 1;\n\t\tthis.keys.splice(spliceIndex);\n\t\tthis.offsets.splice(spliceIndex);\n\t\tthis._length = pos;\n\t\treturn splitCollection;\n\t}\n\n\tpublic append(other: AttributionCollection): void {\n\t\tconst lastEntry = this.keys[this.keys.length - 1];\n\t\tfor (let i = 0; i < other.keys.length; i++) {\n\t\t\tif (i !== 0 || !areEqualAttributionKeys(lastEntry, other.keys[i])) {\n\t\t\t\tthis.offsets.push(other.offsets[i] + this.length);\n\t\t\t\tthis.keys.push(other.keys[i]);\n\t\t\t}\n\t\t}\n\t\tthis._length += other.length;\n\t}\n\n\tpublic getAll(): { offset: number; key: AttributionKey }[] {\n\t\tconst results: { offset: number; key: AttributionKey }[] = new Array(this.keys.length);\n\t\tfor (let i = 0; i < this.keys.length; i++) {\n\t\t\tresults[i] = { offset: this.offsets[i], key: this.keys[i] };\n\t\t}\n\t\treturn results;\n\t}\n\n\tpublic clone(): AttributionCollection {\n\t\tconst copy = new AttributionCollection(this.keys[0], this.length);\n\t\tcopy.keys = this.keys.slice();\n\t\tcopy.offsets = this.offsets.slice();\n\t\treturn copy;\n\t}\n\n\t/**\n\t * Rehydrates attribution information from its serialized form into the provided iterable of consecutive segments.\n\t */\n\tpublic static populateAttributionCollections(\n\t\tsegments: Iterable<ISegment>,\n\t\tsummary: SerializedAttributionCollection,\n\t): void {\n\t\tconst { seqs, posBreakpoints } = summary;\n\t\tassert(\n\t\t\tseqs.length === posBreakpoints.length && seqs.length > 0,\n\t\t\t0x445 /* Invalid attribution summary blob provided */,\n\t\t);\n\t\tlet curIndex = 0;\n\t\tlet currentInfo = seqs[curIndex];\n\t\tlet cumulativeSegPos = 0;\n\n\t\tfor (const segment of segments) {\n\t\t\tconst attribution = new AttributionCollection(\n\t\t\t\ttypeof currentInfo === \"object\" ? currentInfo : { type: \"op\", seq: currentInfo },\n\t\t\t\tsegment.cachedLength,\n\t\t\t);\n\t\t\twhile (posBreakpoints[curIndex] < cumulativeSegPos + segment.cachedLength) {\n\t\t\t\tcurrentInfo = seqs[curIndex];\n\t\t\t\tconst nextOffset = posBreakpoints[curIndex] - cumulativeSegPos;\n\t\t\t\tif (attribution.offsets[attribution.offsets.length - 1] !== nextOffset) {\n\t\t\t\t\tattribution.offsets.push(nextOffset);\n\t\t\t\t\tattribution.keys.push(\n\t\t\t\t\t\ttypeof currentInfo === \"object\"\n\t\t\t\t\t\t\t? currentInfo\n\t\t\t\t\t\t\t: { type: \"op\", seq: currentInfo },\n\t\t\t\t\t);\n\t\t\t\t}\n\t\t\t\tcurIndex++;\n\t\t\t}\n\n\t\t\tif (posBreakpoints[curIndex] === cumulativeSegPos + segment.cachedLength) {\n\t\t\t\tcurrentInfo = seqs[curIndex];\n\t\t\t}\n\n\t\t\tsegment.attribution = attribution;\n\t\t\tcumulativeSegPos += segment.cachedLength;\n\t\t}\n\t}\n\n\t/**\n\t * Condenses attribution information on consecutive segments into a `SerializedAttributionCollection`\n\t */\n\tpublic static serializeAttributionCollections(\n\t\tsegments: Iterable<{\n\t\t\tattribution?: IAttributionCollection<AttributionKey>;\n\t\t\tcachedLength: number;\n\t\t}>,\n\t): SerializedAttributionCollection {\n\t\tconst posBreakpoints: number[] = [];\n\t\tconst seqs: (number | AttributionKey)[] = [];\n\t\tlet mostRecentAttributionKey: AttributionKey | undefined;\n\t\tlet cumulativePos = 0;\n\n\t\tlet segmentsWithAttribution = 0;\n\t\tlet segmentsWithoutAttribution = 0;\n\t\tfor (const segment of segments) {\n\t\t\tif (segment.attribution) {\n\t\t\t\tsegmentsWithAttribution++;\n\t\t\t\tfor (const { offset, key } of segment.attribution?.getAll() ?? []) {\n\t\t\t\t\tif (\n\t\t\t\t\t\t!mostRecentAttributionKey ||\n\t\t\t\t\t\t!areEqualAttributionKeys(key, mostRecentAttributionKey)\n\t\t\t\t\t) {\n\t\t\t\t\t\tposBreakpoints.push(offset + cumulativePos);\n\t\t\t\t\t\tseqs.push(key.type === \"op\" ? key.seq : key);\n\t\t\t\t\t}\n\t\t\t\t\tmostRecentAttributionKey = key;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tsegmentsWithoutAttribution++;\n\t\t\t}\n\n\t\t\tcumulativePos += segment.cachedLength;\n\t\t}\n\n\t\tassert(\n\t\t\tsegmentsWithAttribution === 0 || segmentsWithoutAttribution === 0,\n\t\t\t0x446 /* Expected either all segments or no segments to have attribution information. */,\n\t\t);\n\n\t\tconst blobContents: SerializedAttributionCollection = {\n\t\t\tseqs,\n\t\t\tposBreakpoints,\n\t\t\tlength: cumulativePos,\n\t\t};\n\t\treturn blobContents;\n\t}\n}\n\n/**\n * @alpha\n * @returns - An {@link AttributionPolicy} which tracks only insertion of content.\n * Content is only attributed at ack time, unless the container is in a detached state.\n * Detached content is attributed with a {@link @fluidframework/runtime-definitions#DetachedAttributionKey}.\n */\nexport function createInsertOnlyAttributionPolicy(): AttributionPolicy {\n\tlet unsubscribe: undefined | (() => void);\n\treturn {\n\t\tattach: (client: Client) => {\n\t\t\tassert(\n\t\t\t\tunsubscribe === undefined,\n\t\t\t\t0x557 /* cannot attach to multiple clients at once */,\n\t\t\t);\n\t\t\tconst deltaCallback: MergeTreeDeltaCallback = (\n\t\t\t\topArgs,\n\t\t\t\t{ deltaSegments, operation },\n\t\t\t) => {\n\t\t\t\tif (operation !== MergeTreeDeltaType.INSERT) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\n\t\t\t\tfor (const { segment } of deltaSegments) {\n\t\t\t\t\tif (segment.seq !== undefined && segment.seq !== UnassignedSequenceNumber) {\n\t\t\t\t\t\tconst key: AttributionKey =\n\t\t\t\t\t\t\tsegment.seq === UniversalSequenceNumber\n\t\t\t\t\t\t\t\t? { type: \"detached\", id: 0 }\n\t\t\t\t\t\t\t\t: { type: \"op\", seq: segment.seq };\n\t\t\t\t\t\tsegment.attribution ??= new AttributionCollection(\n\t\t\t\t\t\t\tkey,\n\t\t\t\t\t\t\tsegment.cachedLength,\n\t\t\t\t\t\t);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t};\n\n\t\t\tconst maintenanceCallback: MergeTreeMaintenanceCallback = (\n\t\t\t\t{ deltaSegments, operation },\n\t\t\t\topArgs,\n\t\t\t) => {\n\t\t\t\tif (\n\t\t\t\t\toperation !== MergeTreeMaintenanceType.ACKNOWLEDGED ||\n\t\t\t\t\topArgs === undefined ||\n\t\t\t\t\topArgs.op.type !== MergeTreeDeltaType.INSERT\n\t\t\t\t) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tfor (const { segment } of deltaSegments) {\n\t\t\t\t\tassert(\n\t\t\t\t\t\tsegment.seq !== undefined,\n\t\t\t\t\t\t0x558 /* segment.seq should be set after ack. */,\n\t\t\t\t\t);\n\t\t\t\t\tsegment.attribution = new AttributionCollection(\n\t\t\t\t\t\t{ type: \"op\", seq: segment.seq },\n\t\t\t\t\t\tsegment.cachedLength,\n\t\t\t\t\t);\n\t\t\t\t}\n\t\t\t};\n\n\t\t\tclient.on(\"delta\", deltaCallback);\n\t\t\tclient.on(\"maintenance\", maintenanceCallback);\n\n\t\t\tunsubscribe = () => {\n\t\t\t\tclient.off(\"delta\", deltaCallback);\n\t\t\t\tclient.off(\"maintenance\", maintenanceCallback);\n\t\t\t};\n\t\t},\n\t\tdetach: () => {\n\t\t\tunsubscribe?.();\n\t\t\tunsubscribe = undefined;\n\t\t},\n\t\tget isAttached() {\n\t\t\treturn unsubscribe !== undefined;\n\t\t},\n\t\tserializer: AttributionCollection,\n\t};\n}\n"]}
|
package/dist/base.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../src/base.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH;;;;GAIG;AACH,MAAM,WAAW,aAAa;
|
|
1
|
+
{"version":3,"file":"base.d.ts","sourceRoot":"","sources":["../src/base.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH;;;;GAIG;AACH,MAAM,WAAW,aAAa;IAC7B,KAAK,EAAE,MAAM,CAAC;IACd,GAAG,EAAE,MAAM,CAAC;CACZ"}
|
package/dist/base.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"base.js","sourceRoot":"","sources":["../src/base.ts"],"names":[],"mappings":";AAAA;;;GAGG","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\n/**\n * A range [start, end)\n * @deprecated for internal use only. public export will be removed.\n * @internal\n */\nexport interface IIntegerRange {\n
|
|
1
|
+
{"version":3,"file":"base.js","sourceRoot":"","sources":["../src/base.ts"],"names":[],"mappings":";AAAA;;;GAGG","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\n/**\n * A range [start, end)\n * @deprecated for internal use only. public export will be removed.\n * @internal\n */\nexport interface IIntegerRange {\n\tstart: number;\n\tend: number;\n}\n"]}
|
package/dist/client.d.ts.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,OAAO,EAAE,YAAY,EAAE,MAAM,iCAAiC,CAAC;AAC/D,OAAO,EAAE,gBAAgB,EAAE,MAAM,oCAAoC,CAAC;AACtE,OAAO,EAAE,yBAAyB,EAAe,MAAM,sCAAsC,CAAC;AAC9F,OAAO,
|
|
1
|
+
{"version":3,"file":"client.d.ts","sourceRoot":"","sources":["../src/client.ts"],"names":[],"mappings":"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"}
|