@fluidframework/tree 2.70.0-361092 → 2.70.0-361788
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/api-report/tree.alpha.api.md +36 -17
- package/api-report/tree.beta.api.md +70 -2
- package/api-report/tree.legacy.beta.api.md +70 -2
- package/dist/alpha.d.ts +15 -11
- package/dist/api.d.ts +6 -1
- package/dist/api.d.ts.map +1 -1
- package/dist/api.js +9 -1
- package/dist/api.js.map +1 -1
- package/dist/beta.d.ts +13 -0
- package/dist/codec/codec.d.ts +3 -3
- package/dist/codec/codec.js.map +1 -1
- package/dist/core/forest/forest.d.ts +3 -4
- package/dist/core/forest/forest.d.ts.map +1 -1
- package/dist/core/forest/forest.js.map +1 -1
- package/dist/core/rebase/changeRebaser.d.ts +1 -1
- package/dist/core/rebase/changeRebaser.js.map +1 -1
- package/dist/core/tree/detachedFieldIndex.d.ts.map +1 -1
- package/dist/core/tree/detachedFieldIndex.js +4 -1
- package/dist/core/tree/detachedFieldIndex.js.map +1 -1
- package/dist/feature-libraries/chunked-forest/chunkTree.d.ts +6 -0
- package/dist/feature-libraries/chunked-forest/chunkTree.d.ts.map +1 -1
- package/dist/feature-libraries/chunked-forest/chunkTree.js +11 -2
- package/dist/feature-libraries/chunked-forest/chunkTree.js.map +1 -1
- package/dist/feature-libraries/chunked-forest/chunkedForest.d.ts +1 -1
- package/dist/feature-libraries/chunked-forest/chunkedForest.d.ts.map +1 -1
- package/dist/feature-libraries/chunked-forest/chunkedForest.js +1 -1
- package/dist/feature-libraries/chunked-forest/chunkedForest.js.map +1 -1
- package/dist/feature-libraries/chunked-forest/codec/compressedEncode.d.ts +21 -20
- package/dist/feature-libraries/chunked-forest/codec/compressedEncode.d.ts.map +1 -1
- package/dist/feature-libraries/chunked-forest/codec/compressedEncode.js +17 -43
- package/dist/feature-libraries/chunked-forest/codec/compressedEncode.js.map +1 -1
- package/dist/feature-libraries/chunked-forest/index.d.ts +1 -1
- package/dist/feature-libraries/chunked-forest/index.d.ts.map +1 -1
- package/dist/feature-libraries/chunked-forest/index.js +2 -1
- package/dist/feature-libraries/chunked-forest/index.js.map +1 -1
- package/dist/feature-libraries/flex-tree/lazyField.d.ts.map +1 -1
- package/dist/feature-libraries/flex-tree/lazyField.js +2 -1
- package/dist/feature-libraries/flex-tree/lazyField.js.map +1 -1
- package/dist/feature-libraries/flex-tree/utilities.d.ts +1 -1
- package/dist/feature-libraries/flex-tree/utilities.js +1 -1
- package/dist/feature-libraries/flex-tree/utilities.js.map +1 -1
- package/dist/feature-libraries/forest-summary/incrementalSummaryBuilder.d.ts +1 -1
- package/dist/feature-libraries/forest-summary/incrementalSummaryBuilder.d.ts.map +1 -1
- package/dist/feature-libraries/forest-summary/incrementalSummaryBuilder.js +42 -47
- package/dist/feature-libraries/forest-summary/incrementalSummaryBuilder.js.map +1 -1
- package/dist/feature-libraries/incrementalSummarizationUtils.d.ts +1 -1
- package/dist/feature-libraries/incrementalSummarizationUtils.js.map +1 -1
- package/dist/feature-libraries/index.d.ts +1 -1
- package/dist/feature-libraries/index.d.ts.map +1 -1
- package/dist/feature-libraries/index.js +2 -1
- package/dist/feature-libraries/index.js.map +1 -1
- package/dist/feature-libraries/modular-schema/modularChangeFamily.d.ts +1 -1
- package/dist/feature-libraries/modular-schema/modularChangeFamily.js +1 -1
- package/dist/feature-libraries/modular-schema/modularChangeFamily.js.map +1 -1
- package/dist/feature-libraries/object-forest/objectForest.d.ts +1 -1
- package/dist/feature-libraries/object-forest/objectForest.d.ts.map +1 -1
- package/dist/feature-libraries/object-forest/objectForest.js +1 -1
- package/dist/feature-libraries/object-forest/objectForest.js.map +1 -1
- package/dist/feature-libraries/sequence-field/formatV1.d.ts +1 -1
- package/dist/feature-libraries/sequence-field/formatV1.js.map +1 -1
- package/dist/feature-libraries/sequence-field/formatV2.d.ts +1 -1
- package/dist/feature-libraries/sequence-field/formatV2.js.map +1 -1
- package/dist/feature-libraries/sequence-field/formatV3.d.ts +1 -1
- package/dist/feature-libraries/sequence-field/formatV3.js.map +1 -1
- package/dist/index.d.ts +2 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +4 -2
- package/dist/index.js.map +1 -1
- package/dist/legacy.d.ts +13 -0
- package/dist/packageVersion.d.ts +1 -1
- package/dist/packageVersion.js +1 -1
- package/dist/packageVersion.js.map +1 -1
- package/dist/shared-tree/independentView.d.ts.map +1 -1
- package/dist/shared-tree/independentView.js +2 -1
- package/dist/shared-tree/independentView.js.map +1 -1
- package/dist/shared-tree/schematizingTreeView.d.ts +4 -3
- package/dist/shared-tree/schematizingTreeView.d.ts.map +1 -1
- package/dist/shared-tree/schematizingTreeView.js +1 -1
- package/dist/shared-tree/schematizingTreeView.js.map +1 -1
- package/dist/shared-tree/sharedTree.d.ts +1 -1
- package/dist/shared-tree/sharedTree.js +1 -1
- package/dist/shared-tree/sharedTree.js.map +1 -1
- package/dist/shared-tree/treeAlpha.d.ts +28 -2
- package/dist/shared-tree/treeAlpha.d.ts.map +1 -1
- package/dist/shared-tree/treeAlpha.js +12 -0
- package/dist/shared-tree/treeAlpha.js.map +1 -1
- package/dist/shared-tree/treeCheckout.d.ts +1 -1
- package/dist/shared-tree/treeCheckout.js +1 -1
- package/dist/shared-tree/treeCheckout.js.map +1 -1
- package/dist/shared-tree-core/sharedTreeCore.js +1 -1
- package/dist/shared-tree-core/sharedTreeCore.js.map +1 -1
- package/dist/shared-tree-core/transaction.d.ts +2 -2
- package/dist/shared-tree-core/transaction.js.map +1 -1
- package/dist/simple-tree/api/incrementalAllowedTypes.d.ts +47 -0
- package/dist/simple-tree/api/incrementalAllowedTypes.d.ts.map +1 -0
- package/dist/simple-tree/api/incrementalAllowedTypes.js +90 -0
- package/dist/simple-tree/api/incrementalAllowedTypes.js.map +1 -0
- package/dist/simple-tree/api/index.d.ts +2 -1
- package/dist/simple-tree/api/index.d.ts.map +1 -1
- package/dist/simple-tree/api/index.js +4 -1
- package/dist/simple-tree/api/index.js.map +1 -1
- package/dist/simple-tree/api/schemaFactoryBeta.d.ts +2 -2
- package/dist/simple-tree/api/schemaFactoryBeta.d.ts.map +1 -1
- package/dist/simple-tree/api/schemaFactoryBeta.js.map +1 -1
- package/dist/simple-tree/api/tree.d.ts +51 -37
- package/dist/simple-tree/api/tree.d.ts.map +1 -1
- package/dist/simple-tree/api/tree.js.map +1 -1
- package/dist/simple-tree/core/allowedTypes.d.ts +10 -11
- package/dist/simple-tree/core/allowedTypes.d.ts.map +1 -1
- package/dist/simple-tree/core/allowedTypes.js +1 -1
- package/dist/simple-tree/core/allowedTypes.js.map +1 -1
- package/dist/simple-tree/core/index.d.ts +1 -1
- package/dist/simple-tree/core/index.d.ts.map +1 -1
- package/dist/simple-tree/core/index.js +2 -1
- package/dist/simple-tree/core/index.js.map +1 -1
- package/dist/simple-tree/core/treeNodeSchema.d.ts +3 -8
- package/dist/simple-tree/core/treeNodeSchema.d.ts.map +1 -1
- package/dist/simple-tree/core/treeNodeSchema.js.map +1 -1
- package/dist/simple-tree/core/treeNodeValid.d.ts +2 -2
- package/dist/simple-tree/core/treeNodeValid.d.ts.map +1 -1
- package/dist/simple-tree/core/treeNodeValid.js +2 -2
- package/dist/simple-tree/core/treeNodeValid.js.map +1 -1
- package/dist/simple-tree/core/walkSchema.d.ts.map +1 -1
- package/dist/simple-tree/core/walkSchema.js +1 -1
- package/dist/simple-tree/core/walkSchema.js.map +1 -1
- package/dist/simple-tree/core/withType.d.ts +20 -0
- package/dist/simple-tree/core/withType.d.ts.map +1 -1
- package/dist/simple-tree/core/withType.js +21 -1
- package/dist/simple-tree/core/withType.js.map +1 -1
- package/dist/simple-tree/createContext.d.ts.map +1 -1
- package/dist/simple-tree/createContext.js +1 -1
- package/dist/simple-tree/createContext.js.map +1 -1
- package/dist/simple-tree/index.d.ts +2 -2
- package/dist/simple-tree/index.d.ts.map +1 -1
- package/dist/simple-tree/index.js +5 -2
- package/dist/simple-tree/index.js.map +1 -1
- package/dist/simple-tree/leafNodeSchema.js +1 -1
- package/dist/simple-tree/leafNodeSchema.js.map +1 -1
- package/dist/simple-tree/node-kinds/array/arrayNode.d.ts.map +1 -1
- package/dist/simple-tree/node-kinds/array/arrayNode.js +1 -1
- package/dist/simple-tree/node-kinds/array/arrayNode.js.map +1 -1
- package/dist/simple-tree/node-kinds/map/mapNode.js +1 -1
- package/dist/simple-tree/node-kinds/map/mapNode.js.map +1 -1
- package/dist/simple-tree/node-kinds/object/objectNode.d.ts.map +1 -1
- package/dist/simple-tree/node-kinds/object/objectNode.js +1 -1
- package/dist/simple-tree/node-kinds/object/objectNode.js.map +1 -1
- package/dist/simple-tree/node-kinds/record/recordNode.js +1 -1
- package/dist/simple-tree/node-kinds/record/recordNode.js.map +1 -1
- package/dist/simple-tree/unhydratedFlexTreeFromInsertable.d.ts +1 -0
- package/dist/simple-tree/unhydratedFlexTreeFromInsertable.d.ts.map +1 -1
- package/dist/simple-tree/unhydratedFlexTreeFromInsertable.js +12 -0
- package/dist/simple-tree/unhydratedFlexTreeFromInsertable.js.map +1 -1
- package/dist/util/nestedMap.d.ts +1 -1
- package/dist/util/nestedMap.js +1 -1
- package/dist/util/nestedMap.js.map +1 -1
- package/dist/util/referenceCounting.d.ts +1 -1
- package/dist/util/referenceCounting.js.map +1 -1
- package/lib/alpha.d.ts +15 -11
- package/lib/api.d.ts +6 -1
- package/lib/api.d.ts.map +1 -1
- package/lib/api.js +7 -0
- package/lib/api.js.map +1 -1
- package/lib/beta.d.ts +13 -0
- package/lib/codec/codec.d.ts +3 -3
- package/lib/codec/codec.js.map +1 -1
- package/lib/core/forest/forest.d.ts +3 -4
- package/lib/core/forest/forest.d.ts.map +1 -1
- package/lib/core/forest/forest.js.map +1 -1
- package/lib/core/rebase/changeRebaser.d.ts +1 -1
- package/lib/core/rebase/changeRebaser.js.map +1 -1
- package/lib/core/tree/detachedFieldIndex.d.ts.map +1 -1
- package/lib/core/tree/detachedFieldIndex.js +4 -1
- package/lib/core/tree/detachedFieldIndex.js.map +1 -1
- package/lib/feature-libraries/chunked-forest/chunkTree.d.ts +6 -0
- package/lib/feature-libraries/chunked-forest/chunkTree.d.ts.map +1 -1
- package/lib/feature-libraries/chunked-forest/chunkTree.js +8 -0
- package/lib/feature-libraries/chunked-forest/chunkTree.js.map +1 -1
- package/lib/feature-libraries/chunked-forest/chunkedForest.d.ts +1 -1
- package/lib/feature-libraries/chunked-forest/chunkedForest.d.ts.map +1 -1
- package/lib/feature-libraries/chunked-forest/chunkedForest.js +2 -2
- package/lib/feature-libraries/chunked-forest/chunkedForest.js.map +1 -1
- package/lib/feature-libraries/chunked-forest/codec/compressedEncode.d.ts +21 -20
- package/lib/feature-libraries/chunked-forest/codec/compressedEncode.d.ts.map +1 -1
- package/lib/feature-libraries/chunked-forest/codec/compressedEncode.js +17 -43
- package/lib/feature-libraries/chunked-forest/codec/compressedEncode.js.map +1 -1
- package/lib/feature-libraries/chunked-forest/index.d.ts +1 -1
- package/lib/feature-libraries/chunked-forest/index.d.ts.map +1 -1
- package/lib/feature-libraries/chunked-forest/index.js +1 -1
- package/lib/feature-libraries/chunked-forest/index.js.map +1 -1
- package/lib/feature-libraries/flex-tree/lazyField.d.ts.map +1 -1
- package/lib/feature-libraries/flex-tree/lazyField.js +2 -1
- package/lib/feature-libraries/flex-tree/lazyField.js.map +1 -1
- package/lib/feature-libraries/flex-tree/utilities.d.ts +1 -1
- package/lib/feature-libraries/flex-tree/utilities.js +1 -1
- package/lib/feature-libraries/flex-tree/utilities.js.map +1 -1
- package/lib/feature-libraries/forest-summary/incrementalSummaryBuilder.d.ts +1 -1
- package/lib/feature-libraries/forest-summary/incrementalSummaryBuilder.d.ts.map +1 -1
- package/lib/feature-libraries/forest-summary/incrementalSummaryBuilder.js +42 -47
- package/lib/feature-libraries/forest-summary/incrementalSummaryBuilder.js.map +1 -1
- package/lib/feature-libraries/incrementalSummarizationUtils.d.ts +1 -1
- package/lib/feature-libraries/incrementalSummarizationUtils.js.map +1 -1
- package/lib/feature-libraries/index.d.ts +1 -1
- package/lib/feature-libraries/index.d.ts.map +1 -1
- package/lib/feature-libraries/index.js +1 -1
- package/lib/feature-libraries/index.js.map +1 -1
- package/lib/feature-libraries/modular-schema/modularChangeFamily.d.ts +1 -1
- package/lib/feature-libraries/modular-schema/modularChangeFamily.js +1 -1
- package/lib/feature-libraries/modular-schema/modularChangeFamily.js.map +1 -1
- package/lib/feature-libraries/object-forest/objectForest.d.ts +1 -1
- package/lib/feature-libraries/object-forest/objectForest.d.ts.map +1 -1
- package/lib/feature-libraries/object-forest/objectForest.js +2 -2
- package/lib/feature-libraries/object-forest/objectForest.js.map +1 -1
- package/lib/feature-libraries/sequence-field/formatV1.d.ts +1 -1
- package/lib/feature-libraries/sequence-field/formatV1.js.map +1 -1
- package/lib/feature-libraries/sequence-field/formatV2.d.ts +1 -1
- package/lib/feature-libraries/sequence-field/formatV2.js.map +1 -1
- package/lib/feature-libraries/sequence-field/formatV3.d.ts +1 -1
- package/lib/feature-libraries/sequence-field/formatV3.js.map +1 -1
- package/lib/index.d.ts +2 -2
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +2 -2
- package/lib/index.js.map +1 -1
- package/lib/legacy.d.ts +13 -0
- package/lib/packageVersion.d.ts +1 -1
- package/lib/packageVersion.js +1 -1
- package/lib/packageVersion.js.map +1 -1
- package/lib/shared-tree/independentView.d.ts.map +1 -1
- package/lib/shared-tree/independentView.js +2 -1
- package/lib/shared-tree/independentView.js.map +1 -1
- package/lib/shared-tree/schematizingTreeView.d.ts +4 -3
- package/lib/shared-tree/schematizingTreeView.d.ts.map +1 -1
- package/lib/shared-tree/schematizingTreeView.js +2 -2
- package/lib/shared-tree/schematizingTreeView.js.map +1 -1
- package/lib/shared-tree/sharedTree.d.ts +1 -1
- package/lib/shared-tree/sharedTree.js +1 -1
- package/lib/shared-tree/sharedTree.js.map +1 -1
- package/lib/shared-tree/treeAlpha.d.ts +28 -2
- package/lib/shared-tree/treeAlpha.d.ts.map +1 -1
- package/lib/shared-tree/treeAlpha.js +13 -1
- package/lib/shared-tree/treeAlpha.js.map +1 -1
- package/lib/shared-tree/treeCheckout.d.ts +1 -1
- package/lib/shared-tree/treeCheckout.js +1 -1
- package/lib/shared-tree/treeCheckout.js.map +1 -1
- package/lib/shared-tree-core/sharedTreeCore.js +1 -1
- package/lib/shared-tree-core/sharedTreeCore.js.map +1 -1
- package/lib/shared-tree-core/transaction.d.ts +2 -2
- package/lib/shared-tree-core/transaction.js.map +1 -1
- package/lib/simple-tree/api/incrementalAllowedTypes.d.ts +47 -0
- package/lib/simple-tree/api/incrementalAllowedTypes.d.ts.map +1 -0
- package/lib/simple-tree/api/incrementalAllowedTypes.js +86 -0
- package/lib/simple-tree/api/incrementalAllowedTypes.js.map +1 -0
- package/lib/simple-tree/api/index.d.ts +2 -1
- package/lib/simple-tree/api/index.d.ts.map +1 -1
- package/lib/simple-tree/api/index.js +1 -0
- package/lib/simple-tree/api/index.js.map +1 -1
- package/lib/simple-tree/api/schemaFactoryBeta.d.ts +2 -2
- package/lib/simple-tree/api/schemaFactoryBeta.d.ts.map +1 -1
- package/lib/simple-tree/api/schemaFactoryBeta.js.map +1 -1
- package/lib/simple-tree/api/tree.d.ts +51 -37
- package/lib/simple-tree/api/tree.d.ts.map +1 -1
- package/lib/simple-tree/api/tree.js.map +1 -1
- package/lib/simple-tree/core/allowedTypes.d.ts +10 -11
- package/lib/simple-tree/core/allowedTypes.d.ts.map +1 -1
- package/lib/simple-tree/core/allowedTypes.js +1 -1
- package/lib/simple-tree/core/allowedTypes.js.map +1 -1
- package/lib/simple-tree/core/index.d.ts +1 -1
- package/lib/simple-tree/core/index.d.ts.map +1 -1
- package/lib/simple-tree/core/index.js +1 -1
- package/lib/simple-tree/core/index.js.map +1 -1
- package/lib/simple-tree/core/treeNodeSchema.d.ts +3 -8
- package/lib/simple-tree/core/treeNodeSchema.d.ts.map +1 -1
- package/lib/simple-tree/core/treeNodeSchema.js.map +1 -1
- package/lib/simple-tree/core/treeNodeValid.d.ts +2 -2
- package/lib/simple-tree/core/treeNodeValid.d.ts.map +1 -1
- package/lib/simple-tree/core/treeNodeValid.js +2 -2
- package/lib/simple-tree/core/treeNodeValid.js.map +1 -1
- package/lib/simple-tree/core/walkSchema.d.ts.map +1 -1
- package/lib/simple-tree/core/walkSchema.js +1 -1
- package/lib/simple-tree/core/walkSchema.js.map +1 -1
- package/lib/simple-tree/core/withType.d.ts +20 -0
- package/lib/simple-tree/core/withType.d.ts.map +1 -1
- package/lib/simple-tree/core/withType.js +20 -0
- package/lib/simple-tree/core/withType.js.map +1 -1
- package/lib/simple-tree/createContext.d.ts.map +1 -1
- package/lib/simple-tree/createContext.js +2 -2
- package/lib/simple-tree/createContext.js.map +1 -1
- package/lib/simple-tree/index.d.ts +2 -2
- package/lib/simple-tree/index.d.ts.map +1 -1
- package/lib/simple-tree/index.js +2 -2
- package/lib/simple-tree/index.js.map +1 -1
- package/lib/simple-tree/leafNodeSchema.js +1 -1
- package/lib/simple-tree/leafNodeSchema.js.map +1 -1
- package/lib/simple-tree/node-kinds/array/arrayNode.d.ts.map +1 -1
- package/lib/simple-tree/node-kinds/array/arrayNode.js +1 -1
- package/lib/simple-tree/node-kinds/array/arrayNode.js.map +1 -1
- package/lib/simple-tree/node-kinds/map/mapNode.js +1 -1
- package/lib/simple-tree/node-kinds/map/mapNode.js.map +1 -1
- package/lib/simple-tree/node-kinds/object/objectNode.d.ts.map +1 -1
- package/lib/simple-tree/node-kinds/object/objectNode.js +1 -1
- package/lib/simple-tree/node-kinds/object/objectNode.js.map +1 -1
- package/lib/simple-tree/node-kinds/record/recordNode.js +1 -1
- package/lib/simple-tree/node-kinds/record/recordNode.js.map +1 -1
- package/lib/simple-tree/unhydratedFlexTreeFromInsertable.d.ts +1 -0
- package/lib/simple-tree/unhydratedFlexTreeFromInsertable.d.ts.map +1 -1
- package/lib/simple-tree/unhydratedFlexTreeFromInsertable.js +13 -1
- package/lib/simple-tree/unhydratedFlexTreeFromInsertable.js.map +1 -1
- package/lib/util/nestedMap.d.ts +1 -1
- package/lib/util/nestedMap.js +1 -1
- package/lib/util/nestedMap.js.map +1 -1
- package/lib/util/referenceCounting.d.ts +1 -1
- package/lib/util/referenceCounting.js.map +1 -1
- package/package.json +21 -21
- package/src/api.ts +11 -0
- package/src/codec/codec.ts +3 -3
- package/src/core/forest/forest.ts +3 -4
- package/src/core/rebase/changeRebaser.ts +1 -1
- package/src/core/tree/detachedFieldIndex.ts +4 -1
- package/src/feature-libraries/chunked-forest/chunkTree.ts +9 -0
- package/src/feature-libraries/chunked-forest/chunkedForest.ts +3 -3
- package/src/feature-libraries/chunked-forest/codec/compressedEncode.ts +20 -58
- package/src/feature-libraries/chunked-forest/index.ts +1 -0
- package/src/feature-libraries/flex-tree/lazyField.ts +3 -1
- package/src/feature-libraries/flex-tree/utilities.ts +1 -1
- package/src/feature-libraries/forest-summary/incrementalSummaryBuilder.ts +64 -70
- package/src/feature-libraries/incrementalSummarizationUtils.ts +1 -1
- package/src/feature-libraries/index.ts +1 -0
- package/src/feature-libraries/modular-schema/modularChangeFamily.ts +1 -1
- package/src/feature-libraries/object-forest/objectForest.ts +3 -3
- package/src/feature-libraries/sequence-field/formatV1.ts +1 -1
- package/src/feature-libraries/sequence-field/formatV2.ts +1 -1
- package/src/feature-libraries/sequence-field/formatV3.ts +1 -1
- package/src/index.ts +4 -1
- package/src/packageVersion.ts +1 -1
- package/src/shared-tree/independentView.ts +4 -1
- package/src/shared-tree/schematizingTreeView.ts +10 -5
- package/src/shared-tree/sharedTree.ts +1 -1
- package/src/shared-tree/treeAlpha.ts +50 -2
- package/src/shared-tree/treeCheckout.ts +1 -1
- package/src/shared-tree-core/sharedTreeCore.ts +1 -1
- package/src/shared-tree-core/transaction.ts +2 -2
- package/src/simple-tree/api/incrementalAllowedTypes.ts +107 -0
- package/src/simple-tree/api/index.ts +6 -0
- package/src/simple-tree/api/schemaFactoryBeta.ts +6 -2
- package/src/simple-tree/api/tree.ts +64 -44
- package/src/simple-tree/core/allowedTypes.ts +10 -11
- package/src/simple-tree/core/index.ts +6 -1
- package/src/simple-tree/core/treeNodeSchema.ts +3 -8
- package/src/simple-tree/core/treeNodeValid.ts +3 -3
- package/src/simple-tree/core/walkSchema.ts +1 -2
- package/src/simple-tree/core/withType.ts +24 -0
- package/src/simple-tree/createContext.ts +1 -4
- package/src/simple-tree/index.ts +5 -0
- package/src/simple-tree/leafNodeSchema.ts +1 -1
- package/src/simple-tree/node-kinds/array/arrayNode.ts +5 -2
- package/src/simple-tree/node-kinds/map/mapNode.ts +1 -1
- package/src/simple-tree/node-kinds/object/objectNode.ts +1 -4
- package/src/simple-tree/node-kinds/record/recordNode.ts +1 -1
- package/src/simple-tree/unhydratedFlexTreeFromInsertable.ts +13 -0
- package/src/util/nestedMap.ts +1 -1
- package/src/util/referenceCounting.ts +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"nestedMap.js","sourceRoot":"","sources":["../../src/util/nestedMap.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 { oob } from \"@fluidframework/core-utils/internal\";\n\nimport { getOrAddInMap, getOrCreate } from \"./utils.js\";\n\n/**\n * A dictionary whose values are keyed off of two objects (key1, key2).\n * As it is a nested map, size() will return the number of distinct key1s.\n * If you need constant-time access to the number of values, use SizedNestedMap instead.\n *\n * This code assumes values will not be undefined (keys can be undefined).\n */\nexport type NestedMap<Key1, Key2, Value> = Map<Key1, Map<Key2, Value>>;\n\n/**\n * A read-only version of {@link NestedMap}.\n */\nexport type ReadonlyNestedMap<Key1, Key2, Value> = ReadonlyMap<Key1, ReadonlyMap<Key2, Value>>;\n\n/**\n * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is returned.\n */\nexport function tryAddToNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value | undefined {\n\tlet innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\tinnerMap = new Map();\n\t\tmap.set(key1, innerMap);\n\t}\n\tif (innerMap.has(key2)) {\n\t\treturn innerMap.get(key2);\n\t}\n\tinnerMap.set(key2, value);\n\treturn undefined;\n}\n\n/**\n * Copies over all entries from the source map into the destination map.\n *\n * @param source - The map to copy data from. Not mutated.\n * @param destination - The map to copy data into. Both the outer and inner map may be mutated.\n * @param override - Whether existing entries in `destination` should be replaced by corresponding entries in `source`.\n *\n * @remarks - This function performs deep copying when necessary.\n * This ensures that mutating `destination` after this call will not result in unexpected mutations to `source`.\n */\nexport function populateNestedMap<Key1, Key2, Value>(\n\tsource: ReadonlyNestedMap<Key1, Key2, Value>,\n\tdestination: NestedMap<Key1, Key2, Value>,\n\toverride: boolean,\n): void {\n\tfor (const [key1, sourceInner] of source) {\n\t\tlet destinationInner = destination.get(key1);\n\t\tif (destinationInner === undefined) {\n\t\t\tdestinationInner = new Map(sourceInner);\n\t\t\tdestination.set(key1, destinationInner);\n\t\t} else {\n\t\t\tfor (const [key2, value] of sourceInner) {\n\t\t\t\tif (override || !destinationInner.has(key2)) {\n\t\t\t\t\tdestinationInner.set(key2, value);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n\n/**\n * Sets the value at (key1, key2) in map to value.\n * If there already is a value for (key1, key2), it is replaced with the provided one.\n */\nexport function setInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): void {\n\tconst innerMap = getOrAddInMap(map, key1, new Map<Key2, Value>());\n\tinnerMap.set(key2, value);\n}\n\n/**\n * {@link getOrCreate} for {@link NestedMap}.\n */\nexport function getOrCreateInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tdefaultValue: (key1: Key1, key2: Key2) => Value,\n): Value {\n\tconst innerMap = getOrAddInMap(map, key1, new Map<Key2, Value>());\n\treturn getOrCreate(innerMap, key2, (): Value => defaultValue(key1, key2));\n}\n\n/**\n * Returns the value at (key1, key2) in map, or undefined if not present.\n */\nexport function tryGetFromNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n): Value | undefined {\n\tconst innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\treturn undefined;\n\t}\n\treturn innerMap.get(key2);\n}\n\n/**\n * If (key1, key2) is not in the map, add value to the map.\n * Returns whatever is at (key1, key2) in map (which will be value if it was empty before).\n */\nexport function getOrAddInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value {\n\tconst existing = tryAddToNestedMap(map, key1, key2, value);\n\tif (existing !== undefined) {\n\t\treturn existing;\n\t}\n\treturn value;\n}\n\n/**\n * Does not change map.\n * If (key1, key2) is not in map, returns value.\n * If (key1, key2) is in map, return its entry.\n */\nexport function getOrDefaultInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value {\n\tconst existing = tryGetFromNestedMap(map, key1, key2);\n\tif (existing !== undefined) {\n\t\treturn existing;\n\t}\n\treturn value;\n}\n\n/**\n * Removes the value at (key1, key2) from the map.\n *\n * @returns true iff found.\n */\nexport function deleteFromNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n): boolean {\n\tconst innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\treturn false;\n\t}\n\tconst deleted = innerMap.delete(key2);\n\tif (innerMap.size === 0) {\n\t\tmap.delete(key1);\n\t}\n\treturn deleted;\n}\n\n/**\n * Converts a nested map to a flat list of triplets.\n */\nexport function nestedMapToFlatList<Key1, Key2, Value>(\n\tmap: ReadonlyNestedMap<Key1, Key2, Value>,\n): [Key1, Key2, Value][] {\n\tconst list: [Key1, Key2, Value][] = [];\n\tmap.forEach((innerMap, key1) => {\n\t\tinnerMap.forEach((val, key2) => {\n\t\t\tlist.push([key1, key2, val]);\n\t\t});\n\t});\n\treturn list;\n}\n\n/**\n * Builds a nested map from a flat list of triplets.\n */\nexport function nestedMapFromFlatList<Key1, Key2, Value>(\n\tlist: readonly (readonly [Key1, Key2, Value])[],\n): NestedMap<Key1, Key2, Value> {\n\tconst map = new Map<Key1, Map<Key2, Value>>();\n\tfor (const [key1, key2, val] of list) {\n\t\tgetOrAddInMap(map, key1, new Map<Key2, Value>()).set(key2, val);\n\t}\n\treturn map;\n}\n\nexport function forEachInNestedMap<Key1, Key2, Value>(\n\tmap: ReadonlyNestedMap<Key1, Key2, Value>,\n\tdelegate: (value: Value, key1: Key1, key2: Key2) => void,\n): void {\n\tmap.forEach((innerMap, keyFirst) => {\n\t\tinnerMap.forEach((val, keySecond) => {\n\t\t\tdelegate(val, keyFirst, keySecond);\n\t\t});\n\t});\n}\n\n/**\n * Maps the `input` map values using the provided `delegate`.\n *\n * @param input - The `NestedMap` whose contents are being mapped.\n * @param delegate - The delegate to use for mapping values,\n * @returns A new `NestedMap` with the same keys as `input`, but with the values produced by `delegate`.\n */\nexport function mapNestedMap<Key1, Key2, ValueIn, ValueOut = ValueIn>(\n\tinput: ReadonlyNestedMap<Key1, Key2, ValueIn>,\n\tdelegate: (value: ValueIn, key1: Key1, key2: Key2) => ValueOut,\n): NestedMap<Key1, Key2, ValueOut> {\n\tconst output = new Map<Key1, Map<Key2, ValueOut>>();\n\tinput.forEach((inputInnerMap, keyFirst) => {\n\t\tconst outputInnerMap = new Map<Key2, ValueOut>();\n\t\tinputInnerMap.forEach((val, keySecond) => {\n\t\t\tconst mappedValue = delegate(val, keyFirst, keySecond);\n\t\t\toutputInnerMap.set(keySecond, mappedValue);\n\t\t});\n\t\toutput.set(keyFirst, outputInnerMap);\n\t});\n\treturn output;\n}\n\n/**\n * Map with two keys; same semantics as NestedMap, but maintains a size count for the entire collection.\n * Note: undefined is not supported as a value, and will cause incorrect behavior.\n */\nexport class SizedNestedMap<Key1, Key2, Value> {\n\tprivate readonly nestedMap: NestedMap<Key1, Key2, Value> = new Map();\n\tprivate count = 0;\n\n\t/**\n\t * Returns the total number of elements in this nested map.\n\t */\n\tpublic get size(): number {\n\t\treturn this.count;\n\t}\n\n\t/**\n\t * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is\n\t * returned.\n\t */\n\tpublic tryGet(key1: Key1, key2: Key2): Value | undefined {\n\t\treturn tryGetFromNestedMap(this.nestedMap, key1, key2);\n\t}\n\n\t/**\n\t * Does not change map.\n\t * If (key1, key2) is not in map, returns value.\n\t * If (key1, key2) is in map, return its entry.\n\t */\n\tpublic getOrDefault(key1: Key1, key2: Key2, value: Value): Value {\n\t\treturn getOrDefaultInNestedMap(this.nestedMap, key1, key2, value);\n\t}\n\n\t/**\n\t * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is\n\t * returned.\n\t */\n\tpublic tryAdd(key1: Key1, key2: Key2, value: Value): Value | undefined {\n\t\tconst currentVal = tryAddToNestedMap(this.nestedMap, key1, key2, value);\n\t\tif (currentVal === undefined) {\n\t\t\tthis.count++;\n\t\t}\n\t\treturn currentVal;\n\t}\n\n\t/**\n\t * Sets the value at (key1, key2) in map to value.\n\t * If there already is a value for (key1, key2), it is replaced with the provided one.\n\t */\n\tpublic set(key1: Key1, key2: Key2, value: Value): void {\n\t\tif (this.tryAdd(key1, key2, value) !== undefined) {\n\t\t\tsetInNestedMap(this.nestedMap, key1, key2, value);\n\t\t}\n\t}\n\n\t/**\n\t * Removes the value at (key1, key2) from the map.\n\t * Returns true iff found.\n\t */\n\tpublic delete(key1: Key1, key2: Key2): boolean {\n\t\tconst deleted = deleteFromNestedMap(this.nestedMap, key1, key2);\n\t\tif (deleted) {\n\t\t\tthis.count--;\n\t\t}\n\t\treturn deleted;\n\t}\n\n\t/**\n\t * Runs the supplied delegate for every (value, key1, key2).\n\t */\n\tpublic forEach(delegate: (value: Value, key1: Key1, key2: Key2) => void): void {\n\t\tforEachInNestedMap(this.nestedMap, delegate);\n\t}\n\n\t/**\n\t * Clears the map.\n\t */\n\tpublic clear(): void {\n\t\tthis.count = 0;\n\t\tthis.nestedMap.clear();\n\t}\n\n\tpublic values(): IterableIterator<Value> {\n\t\treturn (\n\t\t\tArray.from(this.nestedMap.values()).flatMap((innerMap) => innerMap.values())[0] ?? oob()\n\t\t);\n\t}\n\n\tpublic [Symbol.iterator](): IterableIterator<[Key1, Map<Key2, Value>]> {\n\t\treturn this.nestedMap[Symbol.iterator]();\n\t}\n}\n"]}
|
|
1
|
+
{"version":3,"file":"nestedMap.js","sourceRoot":"","sources":["../../src/util/nestedMap.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 { oob } from \"@fluidframework/core-utils/internal\";\n\nimport { getOrAddInMap, getOrCreate } from \"./utils.js\";\n\n/**\n * A dictionary whose values are keyed off of two objects (key1, key2).\n * As it is a nested map, size() will return the number of distinct key1s.\n * If you need constant-time access to the number of values, use SizedNestedMap instead.\n *\n * This code assumes values will not be undefined (keys can be undefined).\n */\nexport type NestedMap<Key1, Key2, Value> = Map<Key1, Map<Key2, Value>>;\n\n/**\n * A read-only version of {@link NestedMap}.\n */\nexport type ReadonlyNestedMap<Key1, Key2, Value> = ReadonlyMap<Key1, ReadonlyMap<Key2, Value>>;\n\n/**\n * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is returned.\n */\nexport function tryAddToNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value | undefined {\n\tlet innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\tinnerMap = new Map();\n\t\tmap.set(key1, innerMap);\n\t}\n\tif (innerMap.has(key2)) {\n\t\treturn innerMap.get(key2);\n\t}\n\tinnerMap.set(key2, value);\n\treturn undefined;\n}\n\n/**\n * Copies over all entries from the source map into the destination map.\n *\n * @param source - The map to copy data from. Not mutated.\n * @param destination - The map to copy data into. Both the outer and inner map may be mutated.\n * @param override - Whether existing entries in `destination` should be replaced by corresponding entries in `source`.\n *\n * @remarks This function performs deep copying when necessary.\n * This ensures that mutating `destination` after this call will not result in unexpected mutations to `source`.\n */\nexport function populateNestedMap<Key1, Key2, Value>(\n\tsource: ReadonlyNestedMap<Key1, Key2, Value>,\n\tdestination: NestedMap<Key1, Key2, Value>,\n\toverride: boolean,\n): void {\n\tfor (const [key1, sourceInner] of source) {\n\t\tlet destinationInner = destination.get(key1);\n\t\tif (destinationInner === undefined) {\n\t\t\tdestinationInner = new Map(sourceInner);\n\t\t\tdestination.set(key1, destinationInner);\n\t\t} else {\n\t\t\tfor (const [key2, value] of sourceInner) {\n\t\t\t\tif (override || !destinationInner.has(key2)) {\n\t\t\t\t\tdestinationInner.set(key2, value);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n\n/**\n * Sets the value at (key1, key2) in map to value.\n * If there already is a value for (key1, key2), it is replaced with the provided one.\n */\nexport function setInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): void {\n\tconst innerMap = getOrAddInMap(map, key1, new Map<Key2, Value>());\n\tinnerMap.set(key2, value);\n}\n\n/**\n * {@link getOrCreate} for {@link NestedMap}.\n */\nexport function getOrCreateInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tdefaultValue: (key1: Key1, key2: Key2) => Value,\n): Value {\n\tconst innerMap = getOrAddInMap(map, key1, new Map<Key2, Value>());\n\treturn getOrCreate(innerMap, key2, (): Value => defaultValue(key1, key2));\n}\n\n/**\n * Returns the value at (key1, key2) in map, or undefined if not present.\n */\nexport function tryGetFromNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n): Value | undefined {\n\tconst innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\treturn undefined;\n\t}\n\treturn innerMap.get(key2);\n}\n\n/**\n * If (key1, key2) is not in the map, add value to the map.\n * Returns whatever is at (key1, key2) in map (which will be value if it was empty before).\n */\nexport function getOrAddInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value {\n\tconst existing = tryAddToNestedMap(map, key1, key2, value);\n\tif (existing !== undefined) {\n\t\treturn existing;\n\t}\n\treturn value;\n}\n\n/**\n * Does not change map.\n * If (key1, key2) is not in map, returns value.\n * If (key1, key2) is in map, return its entry.\n */\nexport function getOrDefaultInNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n\tvalue: Value,\n): Value {\n\tconst existing = tryGetFromNestedMap(map, key1, key2);\n\tif (existing !== undefined) {\n\t\treturn existing;\n\t}\n\treturn value;\n}\n\n/**\n * Removes the value at (key1, key2) from the map.\n *\n * @returns true iff found.\n */\nexport function deleteFromNestedMap<Key1, Key2, Value>(\n\tmap: NestedMap<Key1, Key2, Value>,\n\tkey1: Key1,\n\tkey2: Key2,\n): boolean {\n\tconst innerMap = map.get(key1);\n\tif (innerMap === undefined) {\n\t\treturn false;\n\t}\n\tconst deleted = innerMap.delete(key2);\n\tif (innerMap.size === 0) {\n\t\tmap.delete(key1);\n\t}\n\treturn deleted;\n}\n\n/**\n * Converts a nested map to a flat list of triplets.\n */\nexport function nestedMapToFlatList<Key1, Key2, Value>(\n\tmap: ReadonlyNestedMap<Key1, Key2, Value>,\n): [Key1, Key2, Value][] {\n\tconst list: [Key1, Key2, Value][] = [];\n\tmap.forEach((innerMap, key1) => {\n\t\tinnerMap.forEach((val, key2) => {\n\t\t\tlist.push([key1, key2, val]);\n\t\t});\n\t});\n\treturn list;\n}\n\n/**\n * Builds a nested map from a flat list of triplets.\n */\nexport function nestedMapFromFlatList<Key1, Key2, Value>(\n\tlist: readonly (readonly [Key1, Key2, Value])[],\n): NestedMap<Key1, Key2, Value> {\n\tconst map = new Map<Key1, Map<Key2, Value>>();\n\tfor (const [key1, key2, val] of list) {\n\t\tgetOrAddInMap(map, key1, new Map<Key2, Value>()).set(key2, val);\n\t}\n\treturn map;\n}\n\nexport function forEachInNestedMap<Key1, Key2, Value>(\n\tmap: ReadonlyNestedMap<Key1, Key2, Value>,\n\tdelegate: (value: Value, key1: Key1, key2: Key2) => void,\n): void {\n\tmap.forEach((innerMap, keyFirst) => {\n\t\tinnerMap.forEach((val, keySecond) => {\n\t\t\tdelegate(val, keyFirst, keySecond);\n\t\t});\n\t});\n}\n\n/**\n * Maps the `input` map values using the provided `delegate`.\n *\n * @param input - The `NestedMap` whose contents are being mapped.\n * @param delegate - The delegate to use for mapping values,\n * @returns A new `NestedMap` with the same keys as `input`, but with the values produced by `delegate`.\n */\nexport function mapNestedMap<Key1, Key2, ValueIn, ValueOut = ValueIn>(\n\tinput: ReadonlyNestedMap<Key1, Key2, ValueIn>,\n\tdelegate: (value: ValueIn, key1: Key1, key2: Key2) => ValueOut,\n): NestedMap<Key1, Key2, ValueOut> {\n\tconst output = new Map<Key1, Map<Key2, ValueOut>>();\n\tinput.forEach((inputInnerMap, keyFirst) => {\n\t\tconst outputInnerMap = new Map<Key2, ValueOut>();\n\t\tinputInnerMap.forEach((val, keySecond) => {\n\t\t\tconst mappedValue = delegate(val, keyFirst, keySecond);\n\t\t\toutputInnerMap.set(keySecond, mappedValue);\n\t\t});\n\t\toutput.set(keyFirst, outputInnerMap);\n\t});\n\treturn output;\n}\n\n/**\n * Map with two keys; same semantics as NestedMap, but maintains a size count for the entire collection.\n * Note: undefined is not supported as a value, and will cause incorrect behavior.\n */\nexport class SizedNestedMap<Key1, Key2, Value> {\n\tprivate readonly nestedMap: NestedMap<Key1, Key2, Value> = new Map();\n\tprivate count = 0;\n\n\t/**\n\t * Returns the total number of elements in this nested map.\n\t */\n\tpublic get size(): number {\n\t\treturn this.count;\n\t}\n\n\t/**\n\t * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is\n\t * returned.\n\t */\n\tpublic tryGet(key1: Key1, key2: Key2): Value | undefined {\n\t\treturn tryGetFromNestedMap(this.nestedMap, key1, key2);\n\t}\n\n\t/**\n\t * Does not change map.\n\t * If (key1, key2) is not in map, returns value.\n\t * If (key1, key2) is in map, return its entry.\n\t */\n\tpublic getOrDefault(key1: Key1, key2: Key2, value: Value): Value {\n\t\treturn getOrDefaultInNestedMap(this.nestedMap, key1, key2, value);\n\t}\n\n\t/**\n\t * If (key1, key2) already has a value in the map, it is returned, otherwise value is added under (key1, key2) and undefined is\n\t * returned.\n\t */\n\tpublic tryAdd(key1: Key1, key2: Key2, value: Value): Value | undefined {\n\t\tconst currentVal = tryAddToNestedMap(this.nestedMap, key1, key2, value);\n\t\tif (currentVal === undefined) {\n\t\t\tthis.count++;\n\t\t}\n\t\treturn currentVal;\n\t}\n\n\t/**\n\t * Sets the value at (key1, key2) in map to value.\n\t * If there already is a value for (key1, key2), it is replaced with the provided one.\n\t */\n\tpublic set(key1: Key1, key2: Key2, value: Value): void {\n\t\tif (this.tryAdd(key1, key2, value) !== undefined) {\n\t\t\tsetInNestedMap(this.nestedMap, key1, key2, value);\n\t\t}\n\t}\n\n\t/**\n\t * Removes the value at (key1, key2) from the map.\n\t * Returns true iff found.\n\t */\n\tpublic delete(key1: Key1, key2: Key2): boolean {\n\t\tconst deleted = deleteFromNestedMap(this.nestedMap, key1, key2);\n\t\tif (deleted) {\n\t\t\tthis.count--;\n\t\t}\n\t\treturn deleted;\n\t}\n\n\t/**\n\t * Runs the supplied delegate for every (value, key1, key2).\n\t */\n\tpublic forEach(delegate: (value: Value, key1: Key1, key2: Key2) => void): void {\n\t\tforEachInNestedMap(this.nestedMap, delegate);\n\t}\n\n\t/**\n\t * Clears the map.\n\t */\n\tpublic clear(): void {\n\t\tthis.count = 0;\n\t\tthis.nestedMap.clear();\n\t}\n\n\tpublic values(): IterableIterator<Value> {\n\t\treturn (\n\t\t\tArray.from(this.nestedMap.values()).flatMap((innerMap) => innerMap.values())[0] ?? oob()\n\t\t);\n\t}\n\n\tpublic [Symbol.iterator](): IterableIterator<[Key1, Map<Key2, Value>]> {\n\t\treturn this.nestedMap[Symbol.iterator]();\n\t}\n}\n"]}
|
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
/**
|
|
6
6
|
* An object which counts the number of users / references to it.
|
|
7
7
|
* @remarks
|
|
8
|
-
* This implements the
|
|
8
|
+
* This implements the {@link https://en.wikipedia.org/wiki/Reference_counting | Reference counting} pattern.
|
|
9
9
|
* Getting the reference count correct is difficult in TypeScript and great care must be used.
|
|
10
10
|
* Because of this, this interface should not be used in the public API.
|
|
11
11
|
*/
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"referenceCounting.js","sourceRoot":"","sources":["../../src/util/referenceCounting.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,MAAM,EAAE,MAAM,qCAAqC,CAAC;AAgC7D;;GAEG;AACH,MAAM,OAAgB,oBAAoB;IACzC,YAA8B,WAAmB,CAAC;QAApB,aAAQ,GAAR,QAAQ,CAAY;IAAG,CAAC;IAE/C,cAAc,CAAC,KAAK,GAAG,CAAC;QAC9B,IAAI,CAAC,QAAQ,IAAI,KAAK,CAAC;IACxB,CAAC;IAEM,gBAAgB,CAAC,KAAK,GAAG,CAAC;QAChC,IAAI,CAAC,QAAQ,IAAI,KAAK,CAAC;QACvB,MAAM,CAAC,IAAI,CAAC,QAAQ,IAAI,CAAC,EAAE,KAAK,CAAC,wBAAwB,CAAC,CAAC;QAC3D,IAAI,IAAI,CAAC,QAAQ,KAAK,CAAC,EAAE,CAAC;YACzB,IAAI,CAAC,cAAc,EAAE,CAAC;QACvB,CAAC;IACF,CAAC;IAEM,QAAQ;QACd,OAAO,IAAI,CAAC,QAAQ,GAAG,CAAC,CAAC;IAC1B,CAAC;IAEM,cAAc;QACpB,OAAO,IAAI,CAAC,QAAQ,KAAK,CAAC,CAAC;IAC5B,CAAC;CAMD","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { assert } from \"@fluidframework/core-utils/internal\";\n\n/**\n * An object which counts the number of users / references to it.\n * @remarks\n * This implements the
|
|
1
|
+
{"version":3,"file":"referenceCounting.js","sourceRoot":"","sources":["../../src/util/referenceCounting.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,OAAO,EAAE,MAAM,EAAE,MAAM,qCAAqC,CAAC;AAgC7D;;GAEG;AACH,MAAM,OAAgB,oBAAoB;IACzC,YAA8B,WAAmB,CAAC;QAApB,aAAQ,GAAR,QAAQ,CAAY;IAAG,CAAC;IAE/C,cAAc,CAAC,KAAK,GAAG,CAAC;QAC9B,IAAI,CAAC,QAAQ,IAAI,KAAK,CAAC;IACxB,CAAC;IAEM,gBAAgB,CAAC,KAAK,GAAG,CAAC;QAChC,IAAI,CAAC,QAAQ,IAAI,KAAK,CAAC;QACvB,MAAM,CAAC,IAAI,CAAC,QAAQ,IAAI,CAAC,EAAE,KAAK,CAAC,wBAAwB,CAAC,CAAC;QAC3D,IAAI,IAAI,CAAC,QAAQ,KAAK,CAAC,EAAE,CAAC;YACzB,IAAI,CAAC,cAAc,EAAE,CAAC;QACvB,CAAC;IACF,CAAC;IAEM,QAAQ;QACd,OAAO,IAAI,CAAC,QAAQ,GAAG,CAAC,CAAC;IAC1B,CAAC;IAEM,cAAc;QACpB,OAAO,IAAI,CAAC,QAAQ,KAAK,CAAC,CAAC;IAC5B,CAAC;CAMD","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { assert } from \"@fluidframework/core-utils/internal\";\n\n/**\n * An object which counts the number of users / references to it.\n * @remarks\n * This implements the {@link https://en.wikipedia.org/wiki/Reference_counting | Reference counting} pattern.\n * Getting the reference count correct is difficult in TypeScript and great care must be used.\n * Because of this, this interface should not be used in the public API.\n */\nexport interface ReferenceCounted {\n\t/**\n\t * Called to increase the reference count tracked by this object.\n\t * @remarks\n\t * When a user of this object allows something else to use it,\n\t * this should be called.\n\t */\n\treferenceAdded(): void;\n\t/**\n\t * Called to decrease the reference count tracked by this object.\n\t * @remarks\n\t * When a user of this object will no longer use it, this should be called.\n\t */\n\treferenceRemoved(): void;\n\n\t/**\n\t * @returns true if mutating this object may impact other users of it.\n\t *\n\t * Implementations can return true if the refcount is 1 OR the content is logically immutable.\n\t */\n\tisShared(): boolean;\n}\n\n/**\n * Base class to assist with implementing ReferenceCounted.\n */\nexport abstract class ReferenceCountedBase implements ReferenceCounted {\n\tprotected constructor(private refCount: number = 1) {}\n\n\tpublic referenceAdded(count = 1): void {\n\t\tthis.refCount += count;\n\t}\n\n\tpublic referenceRemoved(count = 1): void {\n\t\tthis.refCount -= count;\n\t\tassert(this.refCount >= 0, 0x4c4 /* Negative ref count */);\n\t\tif (this.refCount === 0) {\n\t\t\tthis.onUnreferenced();\n\t\t}\n\t}\n\n\tpublic isShared(): boolean {\n\t\treturn this.refCount > 1;\n\t}\n\n\tpublic isUnreferenced(): boolean {\n\t\treturn this.refCount === 0;\n\t}\n\n\t/**\n\t * Called when refcount reaches 0.\n\t */\n\tprotected abstract onUnreferenced(): void;\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fluidframework/tree",
|
|
3
|
-
"version": "2.70.0-
|
|
3
|
+
"version": "2.70.0-361788",
|
|
4
4
|
"description": "Distributed tree",
|
|
5
5
|
"homepage": "https://fluidframework.com",
|
|
6
6
|
"repository": {
|
|
@@ -101,17 +101,17 @@
|
|
|
101
101
|
"temp-directory": "nyc/.nyc_output"
|
|
102
102
|
},
|
|
103
103
|
"dependencies": {
|
|
104
|
-
"@fluid-internal/client-utils": "2.70.0-
|
|
105
|
-
"@fluidframework/container-runtime": "2.70.0-
|
|
106
|
-
"@fluidframework/core-interfaces": "2.70.0-
|
|
107
|
-
"@fluidframework/core-utils": "2.70.0-
|
|
108
|
-
"@fluidframework/datastore-definitions": "2.70.0-
|
|
109
|
-
"@fluidframework/driver-definitions": "2.70.0-
|
|
110
|
-
"@fluidframework/id-compressor": "2.70.0-
|
|
111
|
-
"@fluidframework/runtime-definitions": "2.70.0-
|
|
112
|
-
"@fluidframework/runtime-utils": "2.70.0-
|
|
113
|
-
"@fluidframework/shared-object-base": "2.70.0-
|
|
114
|
-
"@fluidframework/telemetry-utils": "2.70.0-
|
|
104
|
+
"@fluid-internal/client-utils": "2.70.0-361788",
|
|
105
|
+
"@fluidframework/container-runtime": "2.70.0-361788",
|
|
106
|
+
"@fluidframework/core-interfaces": "2.70.0-361788",
|
|
107
|
+
"@fluidframework/core-utils": "2.70.0-361788",
|
|
108
|
+
"@fluidframework/datastore-definitions": "2.70.0-361788",
|
|
109
|
+
"@fluidframework/driver-definitions": "2.70.0-361788",
|
|
110
|
+
"@fluidframework/id-compressor": "2.70.0-361788",
|
|
111
|
+
"@fluidframework/runtime-definitions": "2.70.0-361788",
|
|
112
|
+
"@fluidframework/runtime-utils": "2.70.0-361788",
|
|
113
|
+
"@fluidframework/shared-object-base": "2.70.0-361788",
|
|
114
|
+
"@fluidframework/telemetry-utils": "2.70.0-361788",
|
|
115
115
|
"@sinclair/typebox": "^0.34.13",
|
|
116
116
|
"@tylerbu/sorted-btree-es6": "^1.8.0",
|
|
117
117
|
"@types/ungap__structured-clone": "^1.2.0",
|
|
@@ -122,19 +122,19 @@
|
|
|
122
122
|
"devDependencies": {
|
|
123
123
|
"@arethetypeswrong/cli": "^0.17.1",
|
|
124
124
|
"@biomejs/biome": "~1.9.3",
|
|
125
|
-
"@fluid-internal/mocha-test-setup": "2.70.0-
|
|
126
|
-
"@fluid-private/stochastic-test-utils": "2.70.0-
|
|
127
|
-
"@fluid-private/test-dds-utils": "2.70.0-
|
|
128
|
-
"@fluid-private/test-drivers": "2.70.0-
|
|
125
|
+
"@fluid-internal/mocha-test-setup": "2.70.0-361788",
|
|
126
|
+
"@fluid-private/stochastic-test-utils": "2.70.0-361788",
|
|
127
|
+
"@fluid-private/test-dds-utils": "2.70.0-361788",
|
|
128
|
+
"@fluid-private/test-drivers": "2.70.0-361788",
|
|
129
129
|
"@fluid-tools/benchmark": "^0.51.0",
|
|
130
130
|
"@fluid-tools/build-cli": "^0.58.3",
|
|
131
131
|
"@fluidframework/build-common": "^2.0.3",
|
|
132
132
|
"@fluidframework/build-tools": "^0.58.3",
|
|
133
|
-
"@fluidframework/container-definitions": "2.70.0-
|
|
134
|
-
"@fluidframework/container-loader": "2.70.0-
|
|
133
|
+
"@fluidframework/container-definitions": "2.70.0-361788",
|
|
134
|
+
"@fluidframework/container-loader": "2.70.0-361788",
|
|
135
135
|
"@fluidframework/eslint-config-fluid": "^6.1.0",
|
|
136
|
-
"@fluidframework/test-runtime-utils": "2.70.0-
|
|
137
|
-
"@fluidframework/test-utils": "2.70.0-
|
|
136
|
+
"@fluidframework/test-runtime-utils": "2.70.0-361788",
|
|
137
|
+
"@fluidframework/test-utils": "2.70.0-361788",
|
|
138
138
|
"@fluidframework/tree-previous": "npm:@fluidframework/tree@2.63.0",
|
|
139
139
|
"@microsoft/api-extractor": "7.52.11",
|
|
140
140
|
"@types/diff": "^3.5.1",
|
|
@@ -147,7 +147,7 @@
|
|
|
147
147
|
"concurrently": "^8.2.1",
|
|
148
148
|
"copyfiles": "^2.4.1",
|
|
149
149
|
"cross-env": "^7.0.3",
|
|
150
|
-
"dependency-cruiser": "^
|
|
150
|
+
"dependency-cruiser": "^17.1.0",
|
|
151
151
|
"diff": "^3.5.0",
|
|
152
152
|
"easy-table": "^1.1.1",
|
|
153
153
|
"eslint": "~8.57.1",
|
package/src/api.ts
CHANGED
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
import {
|
|
7
7
|
type TreeView,
|
|
8
8
|
type TreeViewAlpha,
|
|
9
|
+
type TreeViewBeta,
|
|
9
10
|
type ImplicitFieldSchema,
|
|
10
11
|
// eslint-disable-next-line import/no-deprecated
|
|
11
12
|
asTreeViewAlpha,
|
|
@@ -28,3 +29,13 @@ export function asAlpha<TSchema extends ImplicitFieldSchema>(
|
|
|
28
29
|
// eslint-disable-next-line import/no-deprecated
|
|
29
30
|
return asTreeViewAlpha(view);
|
|
30
31
|
}
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* Retrieve the {@link TreeViewBeta | beta API} for a {@link TreeView}.
|
|
35
|
+
* @beta
|
|
36
|
+
*/
|
|
37
|
+
export function asBeta<TSchema extends ImplicitFieldSchema>(
|
|
38
|
+
view: TreeView<TSchema>,
|
|
39
|
+
): TreeViewBeta<TSchema> {
|
|
40
|
+
return view as TreeViewBeta<TSchema>;
|
|
41
|
+
}
|
package/src/codec/codec.ts
CHANGED
|
@@ -164,7 +164,7 @@ export interface CodecWriteOptions extends ICodecOptions {
|
|
|
164
164
|
* appropriate one, but depending on API layering this might be less ergonomic.
|
|
165
165
|
* - Context for the object currently being encoded, which might enable more efficient encoding. When used in this fashion, the codec author
|
|
166
166
|
* should be careful to include the context somewhere in the encoded data such that decoding can correctly round-trip.
|
|
167
|
-
* For example, a composed set of codecs could implement a form of
|
|
167
|
+
* For example, a composed set of codecs could implement a form of {@link https://en.wikipedia.org/wiki/Dictionary_coder | dictionary coding}
|
|
168
168
|
* using a context map which was created by the top-level codec and passed to the inner codecs.
|
|
169
169
|
* This pattern is used:
|
|
170
170
|
* - To avoid repeatedly encoding session ids on commits (only recording it once at the top level)
|
|
@@ -227,14 +227,14 @@ export interface IMultiFormatCodec<
|
|
|
227
227
|
* allows avoiding some duplicate work at encode/decode time, since the vast majority of document usage will not
|
|
228
228
|
* involve mixed format versions.
|
|
229
229
|
*
|
|
230
|
-
* @privateRemarks
|
|
230
|
+
* @privateRemarks This interface currently assumes all codecs in a family require the same encode/decode context,
|
|
231
231
|
* which isn't necessarily true.
|
|
232
232
|
* This may need to be relaxed in the future.
|
|
233
233
|
*/
|
|
234
234
|
export interface ICodecFamily<TDecoded, TContext = void> {
|
|
235
235
|
/**
|
|
236
236
|
* @returns a codec that can be used to encode and decode data in the specified format.
|
|
237
|
-
* @throws
|
|
237
|
+
* @throws if the format version is not supported by this family.
|
|
238
238
|
* @remarks Implementations should typically emit telemetry (either indirectly by throwing a well-known error with
|
|
239
239
|
* logged properties or directly using some logger) when a format version is requested that is not supported.
|
|
240
240
|
* This ensures that applications can diagnose compatibility issues.
|
|
@@ -84,15 +84,14 @@ export interface IForestSubscription {
|
|
|
84
84
|
clone(schema: TreeStoredSchemaSubscription, anchors: AnchorSet): IEditableForest;
|
|
85
85
|
|
|
86
86
|
/**
|
|
87
|
-
* Generate a TreeChunk for the
|
|
87
|
+
* Generate a TreeChunk[] for the current field (and its children) of cursor.
|
|
88
88
|
* This can be used to chunk data that is then inserted into the forest.
|
|
89
89
|
*
|
|
90
90
|
* @remarks
|
|
91
|
-
*
|
|
92
|
-
* While any TreeChunk is compatible with any forest, this method creates one optimized for this specific forest.
|
|
91
|
+
* Similar to {@link chunkField} but it creates chunks optimized for this specific forest by using its compression policy.
|
|
93
92
|
* The provided data must be compatible with the forest's current schema.
|
|
94
93
|
*/
|
|
95
|
-
chunkField(cursor: ITreeCursorSynchronous): TreeChunk;
|
|
94
|
+
chunkField(cursor: ITreeCursorSynchronous): TreeChunk[];
|
|
96
95
|
|
|
97
96
|
/**
|
|
98
97
|
* Allocates a cursor in the "cleared" state.
|
|
@@ -12,7 +12,7 @@ import type { RevisionTag } from "./types.js";
|
|
|
12
12
|
*
|
|
13
13
|
* This interface is used to provide rebase policy to `Rebaser`.
|
|
14
14
|
*
|
|
15
|
-
* The implementation must ensure TChangeset forms a
|
|
15
|
+
* The implementation must ensure TChangeset forms a {@link https://en.wikipedia.org/wiki/Group_(mathematics | group}) where:
|
|
16
16
|
* - `compose([])` is the identity element.
|
|
17
17
|
* - associativity is defined as `compose([...a, ...b])` is equal to
|
|
18
18
|
* `compose([compose(a), compose(b)])` for all `a` and `b`.
|
|
@@ -293,7 +293,10 @@ export class DetachedFieldIndex {
|
|
|
293
293
|
root: brand<ForestRootId>(root + i),
|
|
294
294
|
latestRelevantRevision: revision,
|
|
295
295
|
});
|
|
296
|
-
setInNestedMap(this.latestRelevantRevisionToFields, revision, root,
|
|
296
|
+
setInNestedMap(this.latestRelevantRevisionToFields, revision, root + i, {
|
|
297
|
+
major: nodeId.major,
|
|
298
|
+
minor: nodeId.minor + i,
|
|
299
|
+
});
|
|
297
300
|
}
|
|
298
301
|
}
|
|
299
302
|
return root;
|
|
@@ -197,6 +197,15 @@ export function chunkFieldSingle(
|
|
|
197
197
|
policy: ChunkCompressor,
|
|
198
198
|
): TreeChunk {
|
|
199
199
|
const chunks = chunkField(cursor, policy);
|
|
200
|
+
return combineChunks(chunks);
|
|
201
|
+
}
|
|
202
|
+
|
|
203
|
+
/**
|
|
204
|
+
* Create a single TreeChunk from an array of TreeChunks.
|
|
205
|
+
* @remarks
|
|
206
|
+
* This takes ownership of the provided TreeChunk references, and returns an owned referenced.
|
|
207
|
+
*/
|
|
208
|
+
export function combineChunks(chunks: TreeChunk[]): TreeChunk {
|
|
200
209
|
if (chunks.length === 1) {
|
|
201
210
|
return chunks[0] ?? oob();
|
|
202
211
|
}
|
|
@@ -44,7 +44,7 @@ import {
|
|
|
44
44
|
} from "../../util/index.js";
|
|
45
45
|
|
|
46
46
|
import { BasicChunk, BasicChunkCursor, type SiblingsOrKey } from "./basicChunk.js";
|
|
47
|
-
import { type IChunker, basicChunkTree,
|
|
47
|
+
import { type IChunker, basicChunkTree, chunkField, chunkTree } from "./chunkTree.js";
|
|
48
48
|
|
|
49
49
|
function makeRoot(): BasicChunk {
|
|
50
50
|
return new BasicChunk(aboveRootPlaceholder, new Map());
|
|
@@ -90,8 +90,8 @@ export class ChunkedForest implements IEditableForest {
|
|
|
90
90
|
return new ChunkedForest(this.roots, schema, this.chunker.clone(schema), anchors);
|
|
91
91
|
}
|
|
92
92
|
|
|
93
|
-
public chunkField(cursor: ITreeCursorSynchronous): TreeChunk {
|
|
94
|
-
return
|
|
93
|
+
public chunkField(cursor: ITreeCursorSynchronous): TreeChunk[] {
|
|
94
|
+
return chunkField(cursor, { idCompressor: this.idCompressor, policy: this.chunker });
|
|
95
95
|
}
|
|
96
96
|
|
|
97
97
|
public forgetAnchor(anchor: Anchor): void {
|
|
@@ -36,7 +36,7 @@ import {
|
|
|
36
36
|
SpecialField,
|
|
37
37
|
version,
|
|
38
38
|
} from "./format.js";
|
|
39
|
-
import type {
|
|
39
|
+
import type { IncrementalEncoder } from "./codecs.js";
|
|
40
40
|
|
|
41
41
|
/**
|
|
42
42
|
* Encode data from `FieldBatch` into an `EncodedFieldBatch`.
|
|
@@ -223,8 +223,8 @@ export const anyNodeEncoder: NodeEncoder = {
|
|
|
223
223
|
outputBuffer: BufferFormat,
|
|
224
224
|
): void {
|
|
225
225
|
// TODO: Fast path uniform chunk content.
|
|
226
|
-
const
|
|
227
|
-
AnyShape.encodeNode(cursor, context, outputBuffer,
|
|
226
|
+
const nodeEncoder = context.nodeEncoderFromSchema(cursor.type);
|
|
227
|
+
AnyShape.encodeNode(cursor, context, outputBuffer, nodeEncoder);
|
|
228
228
|
},
|
|
229
229
|
|
|
230
230
|
shape: AnyShape.instance,
|
|
@@ -350,7 +350,7 @@ export class InlineArrayEncoder
|
|
|
350
350
|
}
|
|
351
351
|
|
|
352
352
|
/**
|
|
353
|
-
* Encodes the shape for a nested array as {@link
|
|
353
|
+
* Encodes the shape for a nested array as {@link EncodedNestedArrayShape} shape.
|
|
354
354
|
*/
|
|
355
355
|
export class NestedArrayShape extends ShapeGeneric<EncodedChunkShape> {
|
|
356
356
|
/**
|
|
@@ -420,30 +420,9 @@ export class NestedArrayEncoder implements FieldEncoder {
|
|
|
420
420
|
}
|
|
421
421
|
|
|
422
422
|
/**
|
|
423
|
-
* Encodes
|
|
424
|
-
* This chunks will be encoded separately, i.e., the contents of the chunk will not be part of the main buffer.
|
|
425
|
-
* A reference to the chunk will be stored in the main buffer as an {@link ChunkReferenceId}.
|
|
423
|
+
* Encodes the shape for an incremental chunk as {@link EncodedIncrementalChunkShape} shape.
|
|
426
424
|
*/
|
|
427
425
|
export class IncrementalChunkShape extends ShapeGeneric<EncodedChunkShape> {
|
|
428
|
-
/**
|
|
429
|
-
* Encodes all the nodes in the chunk at the cursor position using `InlineArrayShape`.
|
|
430
|
-
*/
|
|
431
|
-
public static encodeChunk(chunk: TreeChunk, context: EncoderContext): BufferFormat {
|
|
432
|
-
const chunkOutputBuffer: BufferFormat = [];
|
|
433
|
-
const nodesEncoder = asNodesEncoder(anyNodeEncoder);
|
|
434
|
-
const chunkCursor = chunk.cursor();
|
|
435
|
-
chunkCursor.firstNode();
|
|
436
|
-
const chunkLength = chunkCursor.chunkLength;
|
|
437
|
-
for (let index = 0; index < chunkLength; index++) {
|
|
438
|
-
nodesEncoder.encodeNodes(chunkCursor, context, chunkOutputBuffer);
|
|
439
|
-
}
|
|
440
|
-
assert(
|
|
441
|
-
chunkCursor.mode === CursorLocationType.Fields,
|
|
442
|
-
0xc29 /* should return to fields mode when finished encoding */,
|
|
443
|
-
);
|
|
444
|
-
return chunkOutputBuffer;
|
|
445
|
-
}
|
|
446
|
-
|
|
447
426
|
public encodeShape(
|
|
448
427
|
identifiers: DeduplicationTable<string>,
|
|
449
428
|
shapes: DeduplicationTable<Shape>,
|
|
@@ -464,9 +443,10 @@ export class IncrementalChunkShape extends ShapeGeneric<EncodedChunkShape> {
|
|
|
464
443
|
}
|
|
465
444
|
|
|
466
445
|
/**
|
|
467
|
-
* Encodes an incremental field whose chunks are encoded separately and referenced by their {@link ChunkReferenceId}.
|
|
468
|
-
* The shape of the content of this field is {@link
|
|
469
|
-
* the {@link
|
|
446
|
+
* Encodes an incremental field whose tree chunks are encoded separately and referenced by their {@link ChunkReferenceId}.
|
|
447
|
+
* The shape of the content of this field is {@link NestedArrayShape}.
|
|
448
|
+
* The inner items of the array have shape {@link IncrementalChunkShape} and are {@link ChunkReferenceId}s
|
|
449
|
+
* of the encoded chunks.
|
|
470
450
|
*/
|
|
471
451
|
export const incrementalFieldEncoder: FieldEncoder = {
|
|
472
452
|
encodeField(
|
|
@@ -475,12 +455,13 @@ export const incrementalFieldEncoder: FieldEncoder = {
|
|
|
475
455
|
outputBuffer: BufferFormat,
|
|
476
456
|
): void {
|
|
477
457
|
assert(
|
|
478
|
-
context.
|
|
479
|
-
|
|
458
|
+
context.incrementalEncoder !== undefined,
|
|
459
|
+
"incremental encoder must be defined to use incrementalFieldEncoder",
|
|
480
460
|
);
|
|
481
461
|
|
|
482
|
-
const chunkReferenceIds = context.encodeIncrementalField(
|
|
483
|
-
|
|
462
|
+
const chunkReferenceIds = context.incrementalEncoder.encodeIncrementalField(
|
|
463
|
+
cursor,
|
|
464
|
+
(chunk: TreeChunk) => compressedEncode([chunk.cursor()], context),
|
|
484
465
|
);
|
|
485
466
|
outputBuffer.push(chunkReferenceIds);
|
|
486
467
|
},
|
|
@@ -540,7 +521,12 @@ export class EncoderContext implements NodeEncodeBuilder, FieldEncodeBuilder {
|
|
|
540
521
|
private readonly fieldEncoderFromPolicy: FieldEncoderPolicy,
|
|
541
522
|
public readonly fieldShapes: ReadonlyMap<FieldKindIdentifier, FlexFieldKind>,
|
|
542
523
|
public readonly idCompressor: IIdCompressor,
|
|
543
|
-
|
|
524
|
+
/**
|
|
525
|
+
* To be used to encode incremental chunks, if any.
|
|
526
|
+
* @remarks
|
|
527
|
+
* See {@link IncrementalEncoder} for more information.
|
|
528
|
+
*/
|
|
529
|
+
public readonly incrementalEncoder: IncrementalEncoder | undefined,
|
|
544
530
|
) {}
|
|
545
531
|
|
|
546
532
|
public nodeEncoderFromSchema(schemaName: TreeNodeSchemaIdentifier): NodeEncoder {
|
|
@@ -556,30 +542,6 @@ export class EncoderContext implements NodeEncodeBuilder, FieldEncodeBuilder {
|
|
|
556
542
|
public nestedArrayEncoder(inner: NodeEncoder): NestedArrayEncoder {
|
|
557
543
|
return getOrCreate(this.nestedArrayEncoders, inner, () => new NestedArrayEncoder(inner));
|
|
558
544
|
}
|
|
559
|
-
|
|
560
|
-
public get shouldEncodeIncrementally(): boolean {
|
|
561
|
-
return this.incrementalEncoder !== undefined;
|
|
562
|
-
}
|
|
563
|
-
|
|
564
|
-
/**
|
|
565
|
-
* {@link IncrementalEncoder.encodeIncrementalField}
|
|
566
|
-
*/
|
|
567
|
-
public encodeIncrementalField(
|
|
568
|
-
cursor: ITreeCursorSynchronous,
|
|
569
|
-
encoder: (chunk: TreeChunk) => BufferFormat,
|
|
570
|
-
): ChunkReferenceId[] {
|
|
571
|
-
assert(
|
|
572
|
-
this.incrementalEncoder !== undefined,
|
|
573
|
-
0xc2b /* incremental encoding must be enabled */,
|
|
574
|
-
);
|
|
575
|
-
// Encoder for the chunk that encodes its data using the provided encoder function and
|
|
576
|
-
// updates the encoded data for shapes and identifiers.
|
|
577
|
-
const chunkEncoder = (chunk: TreeChunk): EncodedFieldBatch => {
|
|
578
|
-
const chunkOutputBuffer = encoder(chunk);
|
|
579
|
-
return updateShapesAndIdentifiersEncoding(version, [chunkOutputBuffer]);
|
|
580
|
-
};
|
|
581
|
-
return this.incrementalEncoder.encodeIncrementalField(cursor, chunkEncoder);
|
|
582
|
-
}
|
|
583
545
|
}
|
|
584
546
|
|
|
585
547
|
export interface NodeEncodeBuilder {
|
|
@@ -53,6 +53,7 @@ import {
|
|
|
53
53
|
import { LazyEntity } from "./lazyEntity.js";
|
|
54
54
|
import { type LazyTreeNode, getOrCreateHydratedFlexTreeNode } from "./lazyNode.js";
|
|
55
55
|
import { indexForAt, treeStatusFromAnchorCache } from "./utilities.js";
|
|
56
|
+
import { combineChunks } from "../chunked-forest/index.js";
|
|
56
57
|
|
|
57
58
|
/**
|
|
58
59
|
* Reuse fields.
|
|
@@ -247,7 +248,8 @@ export abstract class LazyField extends LazyEntity<FieldAnchor> implements FlexT
|
|
|
247
248
|
protected getEditor(): IDefaultEditBuilder<ITreeCursorSynchronous> {
|
|
248
249
|
return new MappedEditBuilder(
|
|
249
250
|
this.context.checkout.editor,
|
|
250
|
-
(cursor: ITreeCursorSynchronous) =>
|
|
251
|
+
(cursor: ITreeCursorSynchronous) =>
|
|
252
|
+
combineChunks(this.context.checkout.forest.chunkField(cursor)),
|
|
251
253
|
);
|
|
252
254
|
}
|
|
253
255
|
}
|
|
@@ -31,7 +31,7 @@ export function treeStatusFromDetachedField(detachedField: DetachedField): TreeS
|
|
|
31
31
|
*
|
|
32
32
|
* @param anchors - the {@link AnchorSet} to compare your anchorNode cache to.
|
|
33
33
|
* @param anchorNode - the {@link AnchorNode} to get the {@link TreeStatus} of.
|
|
34
|
-
* @returns
|
|
34
|
+
* @returns the {@link TreeStatus} of the anchorNode provided.
|
|
35
35
|
*/
|
|
36
36
|
export function treeStatusFromAnchorCache(anchorNode: AnchorNode): TreeStatus {
|
|
37
37
|
const cache = anchorNode.slots.get(detachedFieldSlot);
|
|
@@ -288,7 +288,7 @@ export class ForestIncrementalSummaryBuilder implements IncrementalEncoderDecode
|
|
|
288
288
|
|
|
289
289
|
public constructor(
|
|
290
290
|
private readonly enableIncrementalSummary: boolean,
|
|
291
|
-
private readonly getChunkAtCursor: (cursor: ITreeCursorSynchronous) => TreeChunk,
|
|
291
|
+
private readonly getChunkAtCursor: (cursor: ITreeCursorSynchronous) => TreeChunk[],
|
|
292
292
|
public readonly shouldEncodeIncrementally: IncrementalEncodingPolicy,
|
|
293
293
|
private readonly initialSequenceNumber: number,
|
|
294
294
|
) {}
|
|
@@ -392,80 +392,74 @@ export class ForestIncrementalSummaryBuilder implements IncrementalEncoderDecode
|
|
|
392
392
|
// Validate that a summary is currently being tracked and that the tracked summary properties are defined.
|
|
393
393
|
validateTrackingSummary(this.forestSummaryState, this.trackedSummaryProperties);
|
|
394
394
|
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
395
|
+
const chunkReferenceIds: ChunkReferenceId[] = [];
|
|
396
|
+
const chunks = this.getChunkAtCursor(cursor);
|
|
397
|
+
for (const chunk of chunks) {
|
|
398
|
+
let chunkProperties: ChunkSummaryProperties;
|
|
399
|
+
|
|
400
|
+
// Try and get the properties of the chunk from the latest successful summary.
|
|
401
|
+
// If it exists and the summary is not a full tree, use the properties to generate a summary handle.
|
|
402
|
+
// If it does not exist, encode the chunk and generate new properties for it.
|
|
403
|
+
const previousChunkProperties = tryGetFromNestedMap(
|
|
404
|
+
this.chunkTrackingPropertiesMap,
|
|
405
|
+
this.latestSummarySequenceNumber,
|
|
406
|
+
chunk,
|
|
407
|
+
);
|
|
408
|
+
if (previousChunkProperties !== undefined && !this.trackedSummaryProperties.fullTree) {
|
|
409
|
+
chunkProperties = previousChunkProperties;
|
|
410
|
+
this.trackedSummaryProperties.parentSummaryBuilder.addHandle(
|
|
411
|
+
`${chunkProperties.referenceId}`,
|
|
412
|
+
SummaryType.Tree,
|
|
413
|
+
`${this.trackedSummaryProperties.latestSummaryBasePath}/${chunkProperties.summaryPath}`,
|
|
414
|
+
);
|
|
415
|
+
} else {
|
|
416
|
+
// Generate a new reference ID for the chunk.
|
|
417
|
+
const newReferenceId: ChunkReferenceId = brand(this.nextReferenceId++);
|
|
418
|
+
|
|
419
|
+
// Add the reference ID of this chunk to the chunk summary path and use the path as the summary path
|
|
420
|
+
// for the chunk in its summary properties.
|
|
421
|
+
// This is done before encoding the chunk so that the summary path is updated correctly when encoding
|
|
422
|
+
// any incremental chunks that are under this chunk.
|
|
423
|
+
this.trackedSummaryProperties.chunkSummaryPath.push(newReferenceId);
|
|
424
|
+
|
|
425
|
+
chunkProperties = {
|
|
426
|
+
referenceId: newReferenceId,
|
|
427
|
+
summaryPath: this.trackedSummaryProperties.chunkSummaryPath.join("/"),
|
|
428
|
+
};
|
|
429
|
+
|
|
430
|
+
const parentSummaryBuilder = this.trackedSummaryProperties.parentSummaryBuilder;
|
|
431
|
+
// Create a new summary builder for this chunk to build its summary tree which will be stored in the
|
|
432
|
+
// parent's summary tree under its reference ID.
|
|
433
|
+
// Before encoding the chunk, set the parent summary builder to this chunk's summary builder so that
|
|
434
|
+
// any incremental chunks in the subtree of this chunk will use that as their parent summary builder.
|
|
435
|
+
const chunkSummaryBuilder = new SummaryTreeBuilder();
|
|
436
|
+
this.trackedSummaryProperties.parentSummaryBuilder = chunkSummaryBuilder;
|
|
437
|
+
chunkSummaryBuilder.addBlob(
|
|
438
|
+
chunkContentsBlobKey,
|
|
439
|
+
this.trackedSummaryProperties.stringify(chunkEncoder(chunk)),
|
|
440
|
+
);
|
|
401
441
|
|
|
402
|
-
|
|
403
|
-
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
|
|
442
|
+
// Add this chunk's summary tree to the parent's summary tree. The summary tree contains its encoded
|
|
443
|
+
// contents and the summary trees of any incremental chunks under it.
|
|
444
|
+
parentSummaryBuilder.addWithStats(
|
|
445
|
+
`${newReferenceId}`,
|
|
446
|
+
chunkSummaryBuilder.getSummaryTree(),
|
|
447
|
+
);
|
|
407
448
|
|
|
408
|
-
|
|
409
|
-
|
|
410
|
-
|
|
411
|
-
|
|
412
|
-
this.chunkTrackingPropertiesMap,
|
|
413
|
-
this.latestSummarySequenceNumber,
|
|
414
|
-
chunk,
|
|
415
|
-
);
|
|
416
|
-
if (previousChunkProperties !== undefined && !this.trackedSummaryProperties.fullTree) {
|
|
417
|
-
chunkProperties = previousChunkProperties;
|
|
418
|
-
chunkReferenceId = previousChunkProperties.referenceId;
|
|
419
|
-
this.trackedSummaryProperties.parentSummaryBuilder.addHandle(
|
|
420
|
-
`${chunkReferenceId}`,
|
|
421
|
-
SummaryType.Tree,
|
|
422
|
-
`${this.trackedSummaryProperties.latestSummaryBasePath}/${previousChunkProperties.summaryPath}`,
|
|
423
|
-
);
|
|
424
|
-
} else {
|
|
425
|
-
// Generate a new reference ID for the chunk.
|
|
426
|
-
chunkReferenceId = brand(this.nextReferenceId++);
|
|
427
|
-
// Add the reference ID of this chunk to the chunk summary path and use the path as the summary path
|
|
428
|
-
// for the chunk in its summary properties.
|
|
429
|
-
// This is done before encoding the chunk so that the summary path is updated correctly when encoding
|
|
430
|
-
// any incremental chunks that are under this chunk.
|
|
431
|
-
this.trackedSummaryProperties.chunkSummaryPath.push(chunkReferenceId);
|
|
432
|
-
|
|
433
|
-
chunkProperties = {
|
|
434
|
-
referenceId: chunkReferenceId,
|
|
435
|
-
summaryPath: this.trackedSummaryProperties.chunkSummaryPath.join("/"),
|
|
436
|
-
};
|
|
437
|
-
|
|
438
|
-
const parentSummaryBuilder = this.trackedSummaryProperties.parentSummaryBuilder;
|
|
439
|
-
// Create a new summary builder for this chunk to build its summary tree which will be stored in the
|
|
440
|
-
// parent's summary tree under its reference ID.
|
|
441
|
-
// Before encoding the chunk, set the parent summary builder to this chunk's summary builder so that
|
|
442
|
-
// any incremental chunks in the subtree of this chunk will use that as their parent summary builder.
|
|
443
|
-
const chunkSummaryBuilder = new SummaryTreeBuilder();
|
|
444
|
-
this.trackedSummaryProperties.parentSummaryBuilder = chunkSummaryBuilder;
|
|
445
|
-
chunkSummaryBuilder.addBlob(
|
|
446
|
-
chunkContentsBlobKey,
|
|
447
|
-
this.trackedSummaryProperties.stringify(chunkEncoder(chunk)),
|
|
448
|
-
);
|
|
449
|
+
// Restore the parent summary builder and chunk summary path.
|
|
450
|
+
this.trackedSummaryProperties.parentSummaryBuilder = parentSummaryBuilder;
|
|
451
|
+
this.trackedSummaryProperties.chunkSummaryPath.pop();
|
|
452
|
+
}
|
|
449
453
|
|
|
450
|
-
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
|
|
454
|
-
|
|
454
|
+
setInNestedMap(
|
|
455
|
+
this.chunkTrackingPropertiesMap,
|
|
456
|
+
this.trackedSummaryProperties.summarySequenceNumber,
|
|
457
|
+
chunk,
|
|
458
|
+
chunkProperties,
|
|
455
459
|
);
|
|
456
|
-
|
|
457
|
-
// Restore the parent summary builder and chunk summary path.
|
|
458
|
-
this.trackedSummaryProperties.parentSummaryBuilder = parentSummaryBuilder;
|
|
459
|
-
this.trackedSummaryProperties.chunkSummaryPath.pop();
|
|
460
|
+
chunkReferenceIds.push(chunkProperties.referenceId);
|
|
460
461
|
}
|
|
461
|
-
|
|
462
|
-
setInNestedMap(
|
|
463
|
-
this.chunkTrackingPropertiesMap,
|
|
464
|
-
this.trackedSummaryProperties.summarySequenceNumber,
|
|
465
|
-
chunk,
|
|
466
|
-
chunkProperties,
|
|
467
|
-
);
|
|
468
|
-
return [chunkReferenceId];
|
|
462
|
+
return chunkReferenceIds;
|
|
469
463
|
}
|
|
470
464
|
|
|
471
465
|
/**
|