@fluidframework/container-runtime 2.0.0-dev-rc.2.0.0.245554 → 2.0.0-dev-rc.3.0.0.250606
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/container-runtime.api.md +81 -27
- package/dist/batchTracker.d.ts +1 -1
- package/dist/batchTracker.d.ts.map +1 -1
- package/dist/batchTracker.js +2 -2
- package/dist/batchTracker.js.map +1 -1
- package/dist/blobManager.d.ts +3 -3
- package/dist/blobManager.d.ts.map +1 -1
- package/dist/blobManager.js +3 -3
- package/dist/blobManager.js.map +1 -1
- package/dist/channelCollection.d.ts +6 -5
- package/dist/channelCollection.d.ts.map +1 -1
- package/dist/channelCollection.js +57 -19
- package/dist/channelCollection.js.map +1 -1
- package/dist/connectionTelemetry.d.ts +2 -2
- package/dist/connectionTelemetry.d.ts.map +1 -1
- package/dist/connectionTelemetry.js +3 -3
- package/dist/connectionTelemetry.js.map +1 -1
- package/dist/container-runtime-alpha.d.ts +205 -12
- package/dist/container-runtime-beta.d.ts +16 -3
- package/dist/container-runtime-public.d.ts +16 -3
- package/dist/container-runtime-untrimmed.d.ts +207 -26
- package/dist/containerHandleContext.d.ts.map +1 -1
- package/dist/containerHandleContext.js.map +1 -1
- package/dist/containerRuntime.d.ts +32 -26
- package/dist/containerRuntime.d.ts.map +1 -1
- package/dist/containerRuntime.js +235 -133
- package/dist/containerRuntime.js.map +1 -1
- package/dist/dataStore.d.ts +1 -1
- package/dist/dataStore.d.ts.map +1 -1
- package/dist/dataStore.js +2 -2
- package/dist/dataStore.js.map +1 -1
- package/dist/dataStoreContext.d.ts +4 -4
- package/dist/dataStoreContext.d.ts.map +1 -1
- package/dist/dataStoreContext.js +18 -18
- package/dist/dataStoreContext.js.map +1 -1
- package/dist/dataStoreContexts.d.ts.map +1 -1
- package/dist/dataStoreContexts.js.map +1 -1
- package/dist/dataStoreRegistry.d.ts +4 -0
- package/dist/dataStoreRegistry.d.ts.map +1 -1
- package/dist/dataStoreRegistry.js +2 -2
- package/dist/dataStoreRegistry.js.map +1 -1
- package/dist/deltaScheduler.d.ts +1 -1
- package/dist/deltaScheduler.d.ts.map +1 -1
- package/dist/deltaScheduler.js +1 -1
- package/dist/deltaScheduler.js.map +1 -1
- package/dist/gc/garbageCollection.d.ts +1 -1
- package/dist/gc/garbageCollection.d.ts.map +1 -1
- package/dist/gc/garbageCollection.js +1 -1
- package/dist/gc/garbageCollection.js.map +1 -1
- package/dist/gc/gcConfigs.d.ts +1 -1
- package/dist/gc/gcConfigs.d.ts.map +1 -1
- package/dist/gc/gcConfigs.js.map +1 -1
- package/dist/gc/gcDefinitions.d.ts +1 -1
- package/dist/gc/gcDefinitions.d.ts.map +1 -1
- package/dist/gc/gcDefinitions.js.map +1 -1
- package/dist/gc/gcHelpers.d.ts.map +1 -1
- package/dist/gc/gcHelpers.js.map +1 -1
- package/dist/gc/gcSummaryStateTracker.d.ts +1 -1
- package/dist/gc/gcSummaryStateTracker.d.ts.map +1 -1
- package/dist/gc/gcSummaryStateTracker.js.map +1 -1
- package/dist/gc/gcTelemetry.d.ts +1 -1
- package/dist/gc/gcTelemetry.d.ts.map +1 -1
- package/dist/gc/gcTelemetry.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/messageTypes.d.ts +11 -5
- package/dist/messageTypes.d.ts.map +1 -1
- package/dist/messageTypes.js +4 -0
- package/dist/messageTypes.js.map +1 -1
- package/dist/opLifecycle/definitions.d.ts +1 -19
- package/dist/opLifecycle/definitions.d.ts.map +1 -1
- package/dist/opLifecycle/definitions.js.map +1 -1
- package/dist/opLifecycle/index.d.ts +3 -3
- package/dist/opLifecycle/index.d.ts.map +1 -1
- package/dist/opLifecycle/index.js +3 -1
- package/dist/opLifecycle/index.js.map +1 -1
- package/dist/opLifecycle/opCompressor.d.ts.map +1 -1
- package/dist/opLifecycle/opCompressor.js +2 -3
- package/dist/opLifecycle/opCompressor.js.map +1 -1
- package/dist/opLifecycle/opDecompressor.d.ts +15 -4
- package/dist/opLifecycle/opDecompressor.d.ts.map +1 -1
- package/dist/opLifecycle/opDecompressor.js +60 -61
- package/dist/opLifecycle/opDecompressor.js.map +1 -1
- package/dist/opLifecycle/opGroupingManager.d.ts +2 -1
- package/dist/opLifecycle/opGroupingManager.d.ts.map +1 -1
- package/dist/opLifecycle/opGroupingManager.js +9 -11
- package/dist/opLifecycle/opGroupingManager.js.map +1 -1
- package/dist/opLifecycle/opSplitter.d.ts +11 -3
- package/dist/opLifecycle/opSplitter.d.ts.map +1 -1
- package/dist/opLifecycle/opSplitter.js +48 -38
- package/dist/opLifecycle/opSplitter.js.map +1 -1
- package/dist/opLifecycle/outbox.d.ts.map +1 -1
- package/dist/opLifecycle/outbox.js +18 -17
- package/dist/opLifecycle/outbox.js.map +1 -1
- package/dist/opLifecycle/remoteMessageProcessor.d.ts +8 -0
- package/dist/opLifecycle/remoteMessageProcessor.d.ts.map +1 -1
- package/dist/opLifecycle/remoteMessageProcessor.js +36 -32
- package/dist/opLifecycle/remoteMessageProcessor.js.map +1 -1
- package/dist/packageVersion.d.ts +1 -1
- package/dist/packageVersion.js +1 -1
- package/dist/packageVersion.js.map +1 -1
- package/dist/pendingStateManager.d.ts +1 -1
- package/dist/pendingStateManager.d.ts.map +1 -1
- package/dist/pendingStateManager.js.map +1 -1
- package/dist/scheduleManager.d.ts +1 -1
- package/dist/scheduleManager.d.ts.map +1 -1
- package/dist/scheduleManager.js +6 -2
- package/dist/scheduleManager.js.map +1 -1
- package/dist/summary/documentSchema.d.ts +178 -0
- package/dist/summary/documentSchema.d.ts.map +1 -0
- package/dist/summary/documentSchema.js +345 -0
- package/dist/summary/documentSchema.js.map +1 -0
- package/dist/summary/index.d.ts +2 -1
- package/dist/summary/index.d.ts.map +1 -1
- package/dist/summary/index.js +4 -1
- package/dist/summary/index.js.map +1 -1
- package/dist/summary/orderedClientElection.d.ts +2 -2
- package/dist/summary/orderedClientElection.d.ts.map +1 -1
- package/dist/summary/orderedClientElection.js +7 -2
- package/dist/summary/orderedClientElection.js.map +1 -1
- package/dist/summary/runWhileConnectedCoordinator.d.ts +1 -1
- package/dist/summary/runWhileConnectedCoordinator.d.ts.map +1 -1
- package/dist/summary/runWhileConnectedCoordinator.js.map +1 -1
- package/dist/summary/runningSummarizer.d.ts +2 -2
- package/dist/summary/runningSummarizer.d.ts.map +1 -1
- package/dist/summary/runningSummarizer.js +2 -2
- package/dist/summary/runningSummarizer.js.map +1 -1
- package/dist/summary/summarizer.d.ts +2 -2
- package/dist/summary/summarizer.d.ts.map +1 -1
- package/dist/summary/summarizer.js +2 -2
- package/dist/summary/summarizer.js.map +1 -1
- package/dist/summary/summarizerClientElection.d.ts +2 -2
- package/dist/summary/summarizerClientElection.d.ts.map +1 -1
- package/dist/summary/summarizerClientElection.js.map +1 -1
- package/dist/summary/summarizerHeuristics.d.ts +1 -1
- package/dist/summary/summarizerHeuristics.d.ts.map +1 -1
- package/dist/summary/summarizerHeuristics.js.map +1 -1
- package/dist/summary/summarizerNode/summarizerNode.d.ts +2 -2
- package/dist/summary/summarizerNode/summarizerNode.d.ts.map +1 -1
- package/dist/summary/summarizerNode/summarizerNode.js +3 -3
- package/dist/summary/summarizerNode/summarizerNode.js.map +1 -1
- package/dist/summary/summarizerNode/summarizerNodeUtils.d.ts +1 -1
- package/dist/summary/summarizerNode/summarizerNodeUtils.d.ts.map +1 -1
- package/dist/summary/summarizerNode/summarizerNodeUtils.js.map +1 -1
- package/dist/summary/summarizerNode/summarizerNodeWithGc.d.ts +1 -1
- package/dist/summary/summarizerNode/summarizerNodeWithGc.d.ts.map +1 -1
- package/dist/summary/summarizerNode/summarizerNodeWithGc.js +1 -1
- package/dist/summary/summarizerNode/summarizerNodeWithGc.js.map +1 -1
- package/dist/summary/summarizerTypes.d.ts +3 -3
- package/dist/summary/summarizerTypes.d.ts.map +1 -1
- package/dist/summary/summarizerTypes.js.map +1 -1
- package/dist/summary/summaryCollection.d.ts +2 -2
- package/dist/summary/summaryCollection.d.ts.map +1 -1
- package/dist/summary/summaryCollection.js +1 -1
- package/dist/summary/summaryCollection.js.map +1 -1
- package/dist/summary/summaryFormat.d.ts +5 -16
- package/dist/summary/summaryFormat.d.ts.map +1 -1
- package/dist/summary/summaryFormat.js.map +1 -1
- package/dist/summary/summaryGenerator.d.ts +2 -2
- package/dist/summary/summaryGenerator.d.ts.map +1 -1
- package/dist/summary/summaryGenerator.js +2 -2
- package/dist/summary/summaryGenerator.js.map +1 -1
- package/dist/summary/summaryManager.d.ts +1 -1
- package/dist/summary/summaryManager.d.ts.map +1 -1
- package/dist/summary/summaryManager.js +2 -2
- package/dist/summary/summaryManager.js.map +1 -1
- package/lib/batchTracker.d.ts +1 -1
- package/lib/batchTracker.d.ts.map +1 -1
- package/lib/batchTracker.js +2 -2
- package/lib/batchTracker.js.map +1 -1
- package/lib/blobManager.d.ts +3 -3
- package/lib/blobManager.d.ts.map +1 -1
- package/lib/blobManager.js +5 -5
- package/lib/blobManager.js.map +1 -1
- package/lib/channelCollection.d.ts +6 -5
- package/lib/channelCollection.d.ts.map +1 -1
- package/lib/channelCollection.js +59 -21
- package/lib/channelCollection.js.map +1 -1
- package/lib/connectionTelemetry.d.ts +2 -2
- package/lib/connectionTelemetry.d.ts.map +1 -1
- package/lib/connectionTelemetry.js +3 -3
- package/lib/connectionTelemetry.js.map +1 -1
- package/lib/container-runtime-alpha.d.ts +205 -12
- package/lib/container-runtime-beta.d.ts +16 -3
- package/lib/container-runtime-public.d.ts +16 -3
- package/lib/container-runtime-untrimmed.d.ts +207 -26
- package/lib/containerHandleContext.d.ts.map +1 -1
- package/lib/containerHandleContext.js.map +1 -1
- package/lib/containerRuntime.d.ts +32 -26
- package/lib/containerRuntime.d.ts.map +1 -1
- package/lib/containerRuntime.js +197 -95
- package/lib/containerRuntime.js.map +1 -1
- package/lib/dataStore.d.ts +1 -1
- package/lib/dataStore.d.ts.map +1 -1
- package/lib/dataStore.js +2 -2
- package/lib/dataStore.js.map +1 -1
- package/lib/dataStoreContext.d.ts +4 -4
- package/lib/dataStoreContext.d.ts.map +1 -1
- package/lib/dataStoreContext.js +3 -3
- package/lib/dataStoreContext.js.map +1 -1
- package/lib/dataStoreContexts.d.ts.map +1 -1
- package/lib/dataStoreContexts.js.map +1 -1
- package/lib/dataStoreRegistry.d.ts +4 -0
- package/lib/dataStoreRegistry.d.ts.map +1 -1
- package/lib/dataStoreRegistry.js.map +1 -1
- package/lib/deltaScheduler.d.ts +1 -1
- package/lib/deltaScheduler.d.ts.map +1 -1
- package/lib/deltaScheduler.js +1 -1
- package/lib/deltaScheduler.js.map +1 -1
- package/lib/gc/garbageCollection.d.ts +1 -1
- package/lib/gc/garbageCollection.d.ts.map +1 -1
- package/lib/gc/garbageCollection.js +3 -3
- package/lib/gc/garbageCollection.js.map +1 -1
- package/lib/gc/gcConfigs.d.ts +1 -1
- package/lib/gc/gcConfigs.d.ts.map +1 -1
- package/lib/gc/gcConfigs.js +1 -1
- package/lib/gc/gcConfigs.js.map +1 -1
- package/lib/gc/gcDefinitions.d.ts +1 -1
- package/lib/gc/gcDefinitions.d.ts.map +1 -1
- package/lib/gc/gcDefinitions.js.map +1 -1
- package/lib/gc/gcHelpers.d.ts.map +1 -1
- package/lib/gc/gcHelpers.js.map +1 -1
- package/lib/gc/gcSummaryStateTracker.d.ts +1 -1
- package/lib/gc/gcSummaryStateTracker.d.ts.map +1 -1
- package/lib/gc/gcSummaryStateTracker.js +1 -1
- package/lib/gc/gcSummaryStateTracker.js.map +1 -1
- package/lib/gc/gcTelemetry.d.ts +1 -1
- package/lib/gc/gcTelemetry.d.ts.map +1 -1
- package/lib/gc/gcTelemetry.js +1 -1
- package/lib/gc/gcTelemetry.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/messageTypes.d.ts +11 -5
- package/lib/messageTypes.d.ts.map +1 -1
- package/lib/messageTypes.js +4 -0
- package/lib/messageTypes.js.map +1 -1
- package/lib/opLifecycle/definitions.d.ts +1 -19
- package/lib/opLifecycle/definitions.d.ts.map +1 -1
- package/lib/opLifecycle/definitions.js.map +1 -1
- package/lib/opLifecycle/index.d.ts +3 -3
- package/lib/opLifecycle/index.d.ts.map +1 -1
- package/lib/opLifecycle/index.js +2 -2
- package/lib/opLifecycle/index.js.map +1 -1
- package/lib/opLifecycle/opCompressor.d.ts.map +1 -1
- package/lib/opLifecycle/opCompressor.js +2 -3
- package/lib/opLifecycle/opCompressor.js.map +1 -1
- package/lib/opLifecycle/opDecompressor.d.ts +15 -4
- package/lib/opLifecycle/opDecompressor.d.ts.map +1 -1
- package/lib/opLifecycle/opDecompressor.js +60 -61
- package/lib/opLifecycle/opDecompressor.js.map +1 -1
- package/lib/opLifecycle/opGroupingManager.d.ts +2 -1
- package/lib/opLifecycle/opGroupingManager.d.ts.map +1 -1
- package/lib/opLifecycle/opGroupingManager.js +7 -10
- package/lib/opLifecycle/opGroupingManager.js.map +1 -1
- package/lib/opLifecycle/opSplitter.d.ts +11 -3
- package/lib/opLifecycle/opSplitter.d.ts.map +1 -1
- package/lib/opLifecycle/opSplitter.js +46 -37
- package/lib/opLifecycle/opSplitter.js.map +1 -1
- package/lib/opLifecycle/outbox.d.ts.map +1 -1
- package/lib/opLifecycle/outbox.js +18 -17
- package/lib/opLifecycle/outbox.js.map +1 -1
- package/lib/opLifecycle/remoteMessageProcessor.d.ts +8 -0
- package/lib/opLifecycle/remoteMessageProcessor.d.ts.map +1 -1
- package/lib/opLifecycle/remoteMessageProcessor.js +36 -32
- package/lib/opLifecycle/remoteMessageProcessor.js.map +1 -1
- package/lib/packageVersion.d.ts +1 -1
- package/lib/packageVersion.js +1 -1
- package/lib/packageVersion.js.map +1 -1
- package/lib/pendingStateManager.d.ts +1 -1
- package/lib/pendingStateManager.d.ts.map +1 -1
- package/lib/pendingStateManager.js.map +1 -1
- package/lib/scheduleManager.d.ts +1 -1
- package/lib/scheduleManager.d.ts.map +1 -1
- package/lib/scheduleManager.js +6 -2
- package/lib/scheduleManager.js.map +1 -1
- package/lib/summary/documentSchema.d.ts +178 -0
- package/lib/summary/documentSchema.d.ts.map +1 -0
- package/lib/summary/documentSchema.js +341 -0
- package/lib/summary/documentSchema.js.map +1 -0
- package/lib/summary/index.d.ts +2 -1
- package/lib/summary/index.d.ts.map +1 -1
- package/lib/summary/index.js +1 -0
- package/lib/summary/index.js.map +1 -1
- package/lib/summary/orderedClientElection.d.ts +2 -2
- package/lib/summary/orderedClientElection.d.ts.map +1 -1
- package/lib/summary/orderedClientElection.js +7 -2
- package/lib/summary/orderedClientElection.js.map +1 -1
- package/lib/summary/runWhileConnectedCoordinator.d.ts +1 -1
- package/lib/summary/runWhileConnectedCoordinator.d.ts.map +1 -1
- package/lib/summary/runWhileConnectedCoordinator.js.map +1 -1
- package/lib/summary/runningSummarizer.d.ts +2 -2
- package/lib/summary/runningSummarizer.d.ts.map +1 -1
- package/lib/summary/runningSummarizer.js +3 -3
- package/lib/summary/runningSummarizer.js.map +1 -1
- package/lib/summary/summarizer.d.ts +2 -2
- package/lib/summary/summarizer.d.ts.map +1 -1
- package/lib/summary/summarizer.js +3 -3
- package/lib/summary/summarizer.js.map +1 -1
- package/lib/summary/summarizerClientElection.d.ts +2 -2
- package/lib/summary/summarizerClientElection.d.ts.map +1 -1
- package/lib/summary/summarizerClientElection.js.map +1 -1
- package/lib/summary/summarizerHeuristics.d.ts +1 -1
- package/lib/summary/summarizerHeuristics.d.ts.map +1 -1
- package/lib/summary/summarizerHeuristics.js.map +1 -1
- package/lib/summary/summarizerNode/summarizerNode.d.ts +2 -2
- package/lib/summary/summarizerNode/summarizerNode.d.ts.map +1 -1
- package/lib/summary/summarizerNode/summarizerNode.js +4 -4
- package/lib/summary/summarizerNode/summarizerNode.js.map +1 -1
- package/lib/summary/summarizerNode/summarizerNodeUtils.d.ts +1 -1
- package/lib/summary/summarizerNode/summarizerNodeUtils.d.ts.map +1 -1
- package/lib/summary/summarizerNode/summarizerNodeUtils.js.map +1 -1
- package/lib/summary/summarizerNode/summarizerNodeWithGc.d.ts +1 -1
- package/lib/summary/summarizerNode/summarizerNodeWithGc.d.ts.map +1 -1
- package/lib/summary/summarizerNode/summarizerNodeWithGc.js +1 -1
- package/lib/summary/summarizerNode/summarizerNodeWithGc.js.map +1 -1
- package/lib/summary/summarizerTypes.d.ts +3 -3
- package/lib/summary/summarizerTypes.d.ts.map +1 -1
- package/lib/summary/summarizerTypes.js.map +1 -1
- package/lib/summary/summaryCollection.d.ts +2 -2
- package/lib/summary/summaryCollection.d.ts.map +1 -1
- package/lib/summary/summaryCollection.js +1 -1
- package/lib/summary/summaryCollection.js.map +1 -1
- package/lib/summary/summaryFormat.d.ts +5 -16
- package/lib/summary/summaryFormat.d.ts.map +1 -1
- package/lib/summary/summaryFormat.js +1 -1
- package/lib/summary/summaryFormat.js.map +1 -1
- package/lib/summary/summaryGenerator.d.ts +2 -2
- package/lib/summary/summaryGenerator.d.ts.map +1 -1
- package/lib/summary/summaryGenerator.js +3 -3
- package/lib/summary/summaryGenerator.js.map +1 -1
- package/lib/summary/summaryManager.d.ts +1 -1
- package/lib/summary/summaryManager.d.ts.map +1 -1
- package/lib/summary/summaryManager.js +2 -2
- package/lib/summary/summaryManager.js.map +1 -1
- package/lib/test/blobManager.spec.js +3 -3
- package/lib/test/blobManager.spec.js.map +1 -1
- package/lib/test/containerRuntime.spec.js +6 -4
- package/lib/test/containerRuntime.spec.js.map +1 -1
- package/lib/test/dataStoreContext.spec.js +4 -4
- package/lib/test/dataStoreContext.spec.js.map +1 -1
- package/lib/test/dataStoreCreation.spec.js +1 -1
- package/lib/test/dataStoreCreation.spec.js.map +1 -1
- package/lib/test/dataStoreRegistry.spec.js.map +1 -1
- package/lib/test/documentSchema.spec.js +282 -0
- package/lib/test/documentSchema.spec.js.map +1 -0
- package/lib/test/fuzz/fuzzUtils.js +11 -7
- package/lib/test/fuzz/fuzzUtils.js.map +1 -1
- package/lib/test/fuzz/summarizer.fuzz.spec.js +9 -7
- package/lib/test/fuzz/summarizer.fuzz.spec.js.map +1 -1
- package/lib/test/fuzz/summarizerFuzzMocks.js +43 -25
- package/lib/test/fuzz/summarizerFuzzMocks.js.map +1 -1
- package/lib/test/fuzz/summarizerFuzzSuite.js +7 -4
- package/lib/test/fuzz/summarizerFuzzSuite.js.map +1 -1
- package/lib/test/gc/garbageCollection.spec.js +5 -5
- package/lib/test/gc/garbageCollection.spec.js.map +1 -1
- package/lib/test/gc/gcConfigs.spec.js +2 -2
- package/lib/test/gc/gcConfigs.spec.js.map +1 -1
- package/lib/test/gc/gcHelpers.spec.js.map +1 -1
- package/lib/test/gc/gcStats.spec.js +2 -2
- package/lib/test/gc/gcStats.spec.js.map +1 -1
- package/lib/test/gc/gcSummaryStateTracker.spec.js +1 -1
- package/lib/test/gc/gcSummaryStateTracker.spec.js.map +1 -1
- package/lib/test/gc/gcTelemetry.spec.js +3 -3
- package/lib/test/gc/gcTelemetry.spec.js.map +1 -1
- package/lib/test/gc/gcUnreferencedStateTracker.spec.js +1 -1
- package/lib/test/gc/gcUnreferencedStateTracker.spec.js.map +1 -1
- package/lib/test/getPendingBlobs.spec.js +1 -1
- package/lib/test/getPendingBlobs.spec.js.map +1 -1
- package/lib/test/hardwareStats.spec.js +1 -1
- package/lib/test/hardwareStats.spec.js.map +1 -1
- package/lib/test/opLifecycle/OpGroupingManager.spec.js +95 -118
- package/lib/test/opLifecycle/OpGroupingManager.spec.js.map +1 -1
- package/lib/test/opLifecycle/batchManager.spec.js +1 -1
- package/lib/test/opLifecycle/batchManager.spec.js.map +1 -1
- package/lib/test/opLifecycle/opCompressor.spec.js +0 -1
- package/lib/test/opLifecycle/opCompressor.spec.js.map +1 -1
- package/lib/test/opLifecycle/opDecompressor.spec.js +60 -55
- package/lib/test/opLifecycle/opDecompressor.spec.js.map +1 -1
- package/lib/test/opLifecycle/opSplitter.spec.js +56 -41
- package/lib/test/opLifecycle/opSplitter.spec.js.map +1 -1
- package/lib/test/opLifecycle/outbox.spec.js +118 -10
- package/lib/test/opLifecycle/outbox.spec.js.map +1 -1
- package/lib/test/opLifecycle/remoteMessageProcessor.spec.js +115 -91
- package/lib/test/opLifecycle/remoteMessageProcessor.spec.js.map +1 -1
- package/lib/test/pendingStateManager.spec.js +1 -1
- package/lib/test/pendingStateManager.spec.js.map +1 -1
- package/lib/test/scheduleManager.spec.js +1 -1
- package/lib/test/scheduleManager.spec.js.map +1 -1
- package/lib/test/summarizerNode.spec.js +1 -1
- package/lib/test/summarizerNode.spec.js.map +1 -1
- package/lib/test/summarizerNodeWithGc.spec.js +1 -1
- package/lib/test/summarizerNodeWithGc.spec.js.map +1 -1
- package/lib/test/summary/runningSummarizer.spec.js +4 -4
- package/lib/test/summary/runningSummarizer.spec.js.map +1 -1
- package/lib/test/summary/summarizer.spec.js.map +1 -1
- package/lib/test/summary/summarizerClientElection.spec.js +2 -2
- package/lib/test/summary/summarizerClientElection.spec.js.map +1 -1
- package/lib/test/summary/summarizerHeuristics.spec.js +1 -1
- package/lib/test/summary/summarizerHeuristics.spec.js.map +1 -1
- package/lib/test/summary/summaryCollection.spec.js +1 -1
- package/lib/test/summary/summaryCollection.spec.js.map +1 -1
- package/lib/test/summary/summaryManager.spec.js +3 -3
- package/lib/test/summary/summaryManager.spec.js.map +1 -1
- package/lib/test/throttler.spec.js +1 -1
- package/lib/test/throttler.spec.js.map +1 -1
- package/lib/test/types/validateContainerRuntimePrevious.generated.js +6 -4
- package/lib/test/types/validateContainerRuntimePrevious.generated.js.map +1 -1
- package/package.json +35 -21
- package/src/batchTracker.ts +3 -3
- package/src/blobManager.ts +15 -15
- package/src/channelCollection.ts +90 -44
- package/src/connectionTelemetry.ts +10 -10
- package/src/containerHandleContext.ts +1 -1
- package/src/containerRuntime.ts +375 -213
- package/src/dataStore.ts +2 -2
- package/src/dataStoreContext.ts +19 -19
- package/src/dataStoreContexts.ts +2 -2
- package/src/dataStoreRegistry.ts +2 -1
- package/src/deltaScheduler.ts +1 -1
- package/src/gc/garbageCollection.ts +12 -12
- package/src/gc/gcConfigs.ts +11 -11
- package/src/gc/gcDefinitions.ts +2 -2
- package/src/gc/gcHelpers.ts +2 -2
- package/src/gc/gcSummaryStateTracker.ts +4 -4
- package/src/gc/gcTelemetry.ts +6 -6
- package/src/index.ts +8 -1
- package/src/messageTypes.ts +18 -5
- package/src/opLifecycle/README.md +89 -0
- package/src/opLifecycle/definitions.ts +1 -20
- package/src/opLifecycle/index.ts +3 -9
- package/src/opLifecycle/opCompressor.ts +4 -5
- package/src/opLifecycle/opDecompressor.ts +83 -100
- package/src/opLifecycle/opGroupingManager.ts +9 -12
- package/src/opLifecycle/opSplitter.ts +73 -47
- package/src/opLifecycle/outbox.ts +26 -37
- package/src/opLifecycle/remoteMessageProcessor.ts +41 -55
- package/src/packageVersion.ts +1 -1
- package/src/pendingStateManager.ts +2 -2
- package/src/scheduleManager.ts +8 -7
- package/src/summary/documentSchema.ts +553 -0
- package/src/summary/index.ts +10 -1
- package/src/summary/orderedClientElection.ts +7 -5
- package/src/summary/runWhileConnectedCoordinator.ts +1 -1
- package/src/summary/runningSummarizer.ts +19 -19
- package/src/summary/summarizer.ts +14 -14
- package/src/summary/summarizerClientElection.ts +2 -2
- package/src/summary/summarizerHeuristics.ts +2 -2
- package/src/summary/summarizerNode/summarizerNode.ts +15 -15
- package/src/summary/summarizerNode/summarizerNodeUtils.ts +1 -1
- package/src/summary/summarizerNode/summarizerNodeWithGc.ts +4 -4
- package/src/summary/summarizerTypes.ts +3 -3
- package/src/summary/summaryCollection.ts +3 -3
- package/src/summary/summaryFormat.ts +8 -19
- package/src/summary/summaryGenerator.ts +10 -10
- package/src/summary/summaryManager.ts +4 -4
package/lib/containerRuntime.js
CHANGED
|
@@ -1,29 +1,33 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
1
|
+
/*!
|
|
2
|
+
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
*/
|
|
3
5
|
import { Trace, TypedEventEmitter } from "@fluid-internal/client-utils";
|
|
4
|
-
import {
|
|
6
|
+
import { AttachState, LoaderHeader, } from "@fluidframework/container-definitions";
|
|
7
|
+
import { assert, Deferred, LazyPromise, PromiseCache, delay } from "@fluidframework/core-utils";
|
|
5
8
|
import { DriverHeader, FetchSource, } from "@fluidframework/driver-definitions";
|
|
6
9
|
import { readAndParse } from "@fluidframework/driver-utils";
|
|
7
10
|
import { MessageType, SummaryType, } from "@fluidframework/protocol-definitions";
|
|
8
|
-
import { FlushMode, FlushModeExperimental,
|
|
9
|
-
import {
|
|
11
|
+
import { FlushMode, FlushModeExperimental, channelsTreeName, gcTreeKey, } from "@fluidframework/runtime-definitions";
|
|
12
|
+
import { GCDataBuilder, RequestParser, TelemetryContext, addBlobToSummary, addSummarizeResultToSummary, calculateStats, create404Response, exceptionToResponse, responseToException, seqFromTree, } from "@fluidframework/runtime-utils";
|
|
13
|
+
import { DataCorruptionError, DataProcessingError, GenericError, LoggingError, PerformanceEvent, TaggedLoggerAdapter, UsageError, createChildLogger, createChildMonitoringContext, createSampledLogger, loggerToMonitoringContext, raiseConnectedEvent, wrapError, } from "@fluidframework/telemetry-utils";
|
|
10
14
|
import { v4 as uuid } from "uuid";
|
|
11
|
-
import {
|
|
12
|
-
import { FluidDataStoreRegistry } from "./dataStoreRegistry.js";
|
|
13
|
-
import { ReportOpPerfTelemetry } from "./connectionTelemetry.js";
|
|
14
|
-
import { PendingStateManager, } from "./pendingStateManager.js";
|
|
15
|
-
import { pkgVersion } from "./packageVersion.js";
|
|
15
|
+
import { BindBatchTracker } from "./batchTracker.js";
|
|
16
16
|
import { BlobManager } from "./blobManager.js";
|
|
17
17
|
import { ChannelCollection, getSummaryForDatastores, wrapContext } from "./channelCollection.js";
|
|
18
|
-
import {
|
|
19
|
-
import {
|
|
20
|
-
import { GarbageCollector, GCNodeType, gcGenerationOptionName, } from "./gc/index.js";
|
|
18
|
+
import { ReportOpPerfTelemetry } from "./connectionTelemetry.js";
|
|
19
|
+
import { ContainerFluidHandleContext } from "./containerHandleContext.js";
|
|
21
20
|
import { channelToDataStore } from "./dataStore.js";
|
|
22
|
-
import {
|
|
23
|
-
import { ScheduleManager } from "./scheduleManager.js";
|
|
24
|
-
import { OpCompressor, OpDecompressor, Outbox, OpSplitter, RemoteMessageProcessor, OpGroupingManager, getLongStack, } from "./opLifecycle/index.js";
|
|
21
|
+
import { FluidDataStoreRegistry } from "./dataStoreRegistry.js";
|
|
25
22
|
import { DeltaManagerSummarizerProxy } from "./deltaManagerSummarizerProxy.js";
|
|
23
|
+
import { GCNodeType, GarbageCollector, gcGenerationOptionName, } from "./gc/index.js";
|
|
26
24
|
import { ContainerMessageType, } from "./messageTypes.js";
|
|
25
|
+
import { OpCompressor, OpDecompressor, OpGroupingManager, OpSplitter, Outbox, RemoteMessageProcessor, getLongStack, } from "./opLifecycle/index.js";
|
|
26
|
+
import { pkgVersion } from "./packageVersion.js";
|
|
27
|
+
import { PendingStateManager, } from "./pendingStateManager.js";
|
|
28
|
+
import { ScheduleManager } from "./scheduleManager.js";
|
|
29
|
+
import { DocumentsSchemaController, OrderedClientCollection, OrderedClientElection, RetriableSummaryError, RunWhileConnectedCoordinator, Summarizer, SummarizerClientElection, SummaryCollection, SummaryManager, aliasBlobName, blobsTreeName, chunksBlobName, createRootSummarizerNodeWithGC, electedSummarizerBlobName, extractSummaryMetadataMessage, idCompressorBlobName, metadataBlobName, rootHasIsolatedChannels, summarizerClientType, wrapSummaryInChannelsTree, } from "./summary/index.js";
|
|
30
|
+
import { Throttler, formExponentialFn } from "./throttler.js";
|
|
27
31
|
/**
|
|
28
32
|
* Utility to implement compat behaviors given an unknown message type
|
|
29
33
|
* The parameters are typed to support compile-time enforcement of handling all known types/behaviors
|
|
@@ -78,6 +82,11 @@ export var CompressionAlgorithms;
|
|
|
78
82
|
(function (CompressionAlgorithms) {
|
|
79
83
|
CompressionAlgorithms["lz4"] = "lz4";
|
|
80
84
|
})(CompressionAlgorithms || (CompressionAlgorithms = {}));
|
|
85
|
+
/** @alpha */
|
|
86
|
+
export const disabledCompressionConfig = {
|
|
87
|
+
minimumBatchSizeInBytes: Infinity,
|
|
88
|
+
compressionAlgorithm: CompressionAlgorithms.lz4,
|
|
89
|
+
};
|
|
81
90
|
const maxConsecutiveReconnectsKey = "Fluid.ContainerRuntime.MaxConsecutiveReconnects";
|
|
82
91
|
const defaultFlushMode = FlushMode.TurnBased;
|
|
83
92
|
// The actual limit is 1Mb (socket.io and Kafka limits)
|
|
@@ -101,26 +110,12 @@ export const defaultPendingOpsRetryDelayMs = 1000;
|
|
|
101
110
|
* This delay's goal is to prevent tight restart loops
|
|
102
111
|
*/
|
|
103
112
|
const defaultCloseSummarizerDelayMs = 5000; // 5 seconds
|
|
104
|
-
/**
|
|
105
|
-
* @deprecated use ContainerRuntimeMessageType instead
|
|
106
|
-
* @internal
|
|
107
|
-
*/
|
|
108
|
-
export var RuntimeMessage;
|
|
109
|
-
(function (RuntimeMessage) {
|
|
110
|
-
RuntimeMessage["FluidDataStoreOp"] = "component";
|
|
111
|
-
RuntimeMessage["Attach"] = "attach";
|
|
112
|
-
RuntimeMessage["ChunkedOp"] = "chunkedOp";
|
|
113
|
-
RuntimeMessage["BlobAttach"] = "blobAttach";
|
|
114
|
-
RuntimeMessage["Rejoin"] = "rejoin";
|
|
115
|
-
RuntimeMessage["Alias"] = "alias";
|
|
116
|
-
RuntimeMessage["Operation"] = "op";
|
|
117
|
-
})(RuntimeMessage || (RuntimeMessage = {}));
|
|
118
113
|
/**
|
|
119
114
|
* @deprecated please use version in driver-utils
|
|
120
115
|
* @internal
|
|
121
116
|
*/
|
|
122
117
|
export function isRuntimeMessage(message) {
|
|
123
|
-
return Object.values(
|
|
118
|
+
return Object.values(ContainerMessageType).includes(message.type);
|
|
124
119
|
}
|
|
125
120
|
/**
|
|
126
121
|
* Legacy ID for the built-in AgentScheduler. To minimize disruption while removing it, retaining this as a
|
|
@@ -194,6 +189,17 @@ async function createSummarizer(loader, url) {
|
|
|
194
189
|
}
|
|
195
190
|
return fluidObject.ISummarizer;
|
|
196
191
|
}
|
|
192
|
+
/**
|
|
193
|
+
* Extract last message from the snapshot metadata.
|
|
194
|
+
* Uses legacy property if not using explicit schema control, otherwise uses the new property.
|
|
195
|
+
* This allows new runtime to make documents not openable for old runtimes, one explicit document schema control is enabled.
|
|
196
|
+
* Please see addMetadataToSummary() as well
|
|
197
|
+
*/
|
|
198
|
+
function lastMessageFromMetadata(metadata) {
|
|
199
|
+
return metadata?.documentSchema?.runtime?.explicitSchemaControl
|
|
200
|
+
? metadata?.lastMessage
|
|
201
|
+
: metadata?.message;
|
|
202
|
+
}
|
|
197
203
|
/**
|
|
198
204
|
* Represents the runtime of the container. Contains helper functions/state of the container.
|
|
199
205
|
* It will define the store level mappings.
|
|
@@ -231,7 +237,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
231
237
|
},
|
|
232
238
|
});
|
|
233
239
|
const mc = loggerToMonitoringContext(logger);
|
|
234
|
-
const { summaryOptions = {}, gcOptions = {}, loadSequenceNumberVerification = "close", flushMode = defaultFlushMode, compressionOptions = defaultCompressionConfig, maxBatchSizeInBytes = defaultMaxBatchSizeInBytes, enableRuntimeIdCompressor
|
|
240
|
+
const { summaryOptions = {}, gcOptions = {}, loadSequenceNumberVerification = "close", flushMode = defaultFlushMode, compressionOptions = defaultCompressionConfig, maxBatchSizeInBytes = defaultMaxBatchSizeInBytes, enableRuntimeIdCompressor, chunkSizeInBytes = defaultChunkSizeInBytes, enableOpReentryCheck = false, enableGroupedBatching = false, explicitSchemaControl = false, } = runtimeOptions;
|
|
235
241
|
const registry = new FluidDataStoreRegistry(registryEntries);
|
|
236
242
|
const tryFetchBlob = async (blobName) => {
|
|
237
243
|
const blobId = context.baseSnapshot?.blobs[blobName];
|
|
@@ -256,14 +262,21 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
256
262
|
assert(context.storage !== undefined, 0x256 /* "storage undefined in attached container" */);
|
|
257
263
|
return readAndParse(context.storage, id);
|
|
258
264
|
});
|
|
265
|
+
const messageAtLastSummary = lastMessageFromMetadata(metadata);
|
|
259
266
|
// Verify summary runtime sequence number matches protocol sequence number.
|
|
260
|
-
const runtimeSequenceNumber =
|
|
267
|
+
const runtimeSequenceNumber = messageAtLastSummary?.sequenceNumber;
|
|
261
268
|
// When we load with pending state, we reuse an old snapshot so we don't expect these numbers to match
|
|
262
269
|
if (!context.pendingLocalState && runtimeSequenceNumber !== undefined) {
|
|
263
270
|
const protocolSequenceNumber = context.deltaManager.initialSequenceNumber;
|
|
264
271
|
// Unless bypass is explicitly set, then take action when sequence numbers mismatch.
|
|
265
272
|
if (loadSequenceNumberVerification !== "bypass" &&
|
|
266
273
|
runtimeSequenceNumber !== protocolSequenceNumber) {
|
|
274
|
+
// Message to OCEs:
|
|
275
|
+
// You can hit this error with runtimeSequenceNumber === -1 in < 2.0 RC3 builds.
|
|
276
|
+
// This would indicate that explicit schema control is enabled in current (2.0 RC3+) builds and it
|
|
277
|
+
// results in addMetadataToSummary() creating a poison pill for older runtimes in the form of a -1 sequence number.
|
|
278
|
+
// Older runtimes do not understand new schema, and thus could corrupt document if they proceed, thus we are using
|
|
279
|
+
// this poison pill to prevent them from proceeding.
|
|
267
280
|
// "Load from summary, runtime metadata sequenceNumber !== initialSequenceNumber"
|
|
268
281
|
const error = new DataCorruptionError(
|
|
269
282
|
// pre-0.58 error message: SummaryMetadataMismatch
|
|
@@ -277,7 +290,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
277
290
|
}
|
|
278
291
|
}
|
|
279
292
|
// Enabling the IdCompressor is a one-way operation and we only want to
|
|
280
|
-
// allow new containers to turn it on
|
|
293
|
+
// allow new containers to turn it on.
|
|
281
294
|
let idCompressorMode;
|
|
282
295
|
if (existing) {
|
|
283
296
|
// This setting has to be sticky for correctness:
|
|
@@ -286,20 +299,20 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
286
299
|
// 2) if it's ON, then all sessions should load compressor right away
|
|
287
300
|
// 3) Same logic applies for "delayed" mode
|
|
288
301
|
// Maybe in the future we will need to enabled (and figure how to do it safely) "delayed" -> "on" change.
|
|
289
|
-
// We could do "off" -> "on"
|
|
290
|
-
// this will allow clients to eventually to disregard "off" setting (when it's safe so) and start
|
|
302
|
+
// We could do "off" -> "on" transition too, if all clients start loading compressor (but not using it initially) and
|
|
303
|
+
// do so for a while - this will allow clients to eventually to disregard "off" setting (when it's safe so) and start
|
|
304
|
+
// using compressor in future sessions.
|
|
291
305
|
// Everyting is possible, but it needs to be designed and executed carefully, when such need arises.
|
|
292
|
-
idCompressorMode = metadata?.
|
|
306
|
+
idCompressorMode = metadata?.documentSchema?.runtime
|
|
307
|
+
?.idCompressorMode;
|
|
293
308
|
}
|
|
294
309
|
else {
|
|
295
|
-
|
|
296
|
-
const enabled = mc.config.getBoolean("Fluid.ContainerRuntime.IdCompressorEnabled");
|
|
297
|
-
switch (enabled) {
|
|
310
|
+
switch (mc.config.getBoolean("Fluid.ContainerRuntime.IdCompressorEnabled")) {
|
|
298
311
|
case true:
|
|
299
312
|
idCompressorMode = "on";
|
|
300
313
|
break;
|
|
301
314
|
case false:
|
|
302
|
-
idCompressorMode =
|
|
315
|
+
idCompressorMode = undefined;
|
|
303
316
|
break;
|
|
304
317
|
default:
|
|
305
318
|
idCompressorMode = enableRuntimeIdCompressor;
|
|
@@ -332,6 +345,24 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
332
345
|
return createIdCompressor(compressorLogger);
|
|
333
346
|
}
|
|
334
347
|
};
|
|
348
|
+
const disableGroupedBatching = mc.config.getBoolean("Fluid.ContainerRuntime.DisableGroupedBatching");
|
|
349
|
+
const disableCompression = mc.config.getBoolean("Fluid.ContainerRuntime.CompressionDisabled");
|
|
350
|
+
const compressionLz4 = disableCompression !== true &&
|
|
351
|
+
compressionOptions.minimumBatchSizeInBytes !== Infinity &&
|
|
352
|
+
compressionOptions.compressionAlgorithm === "lz4";
|
|
353
|
+
const opGroupingEnabled = disableGroupedBatching !== true && enableGroupedBatching;
|
|
354
|
+
const documentSchemaController = new DocumentsSchemaController(existing, metadata?.documentSchema, {
|
|
355
|
+
explicitSchemaControl,
|
|
356
|
+
compressionLz4,
|
|
357
|
+
idCompressorMode,
|
|
358
|
+
opGroupingEnabled,
|
|
359
|
+
}, (schema) => {
|
|
360
|
+
runtime.onSchemaChange(schema);
|
|
361
|
+
});
|
|
362
|
+
const featureGatesForTelemetry = {
|
|
363
|
+
disableGroupedBatching,
|
|
364
|
+
disableCompression,
|
|
365
|
+
};
|
|
335
366
|
const runtime = new containerRuntimeCtor(context, registry, metadata, electedSummarizerData, chunks ?? [], aliases ?? [], {
|
|
336
367
|
summaryOptions,
|
|
337
368
|
gcOptions,
|
|
@@ -340,10 +371,12 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
340
371
|
compressionOptions,
|
|
341
372
|
maxBatchSizeInBytes,
|
|
342
373
|
chunkSizeInBytes,
|
|
343
|
-
|
|
374
|
+
// Requires<> drops undefined from IdCompressorType
|
|
375
|
+
enableRuntimeIdCompressor: enableRuntimeIdCompressor,
|
|
344
376
|
enableOpReentryCheck,
|
|
345
377
|
enableGroupedBatching,
|
|
346
|
-
|
|
378
|
+
explicitSchemaControl,
|
|
379
|
+
}, containerScope, logger, existing, blobManagerSnapshot, context.storage, createIdCompressorFn, documentSchemaController, featureGatesForTelemetry, provideEntryPoint, requestHandler, undefined);
|
|
347
380
|
// Apply stashed ops with a reference sequence number equal to the sequence number of the snapshot,
|
|
348
381
|
// or zero. This must be done before Container replays saved ops.
|
|
349
382
|
await runtime.pendingStateManager.applyStashedOpsAt(runtimeSequenceNumber ?? 0);
|
|
@@ -372,6 +405,12 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
372
405
|
get attachState() {
|
|
373
406
|
return this._getAttachState();
|
|
374
407
|
}
|
|
408
|
+
get documentSchema() {
|
|
409
|
+
return this.documentsSchemaController.sessionSchema.runtime;
|
|
410
|
+
}
|
|
411
|
+
get idCompressorMode() {
|
|
412
|
+
return this.documentSchema.idCompressorMode;
|
|
413
|
+
}
|
|
375
414
|
/**
|
|
376
415
|
* See IContainerRuntimeBase.idCompressor() for details.
|
|
377
416
|
*/
|
|
@@ -452,7 +491,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
452
491
|
return this.garbageCollector.throwOnTombstoneUsage;
|
|
453
492
|
}
|
|
454
493
|
/***/
|
|
455
|
-
constructor(context, registry, metadata, electedSummarizerData, chunks, dataStoreAliasMap, runtimeOptions, containerScope, logger, existing, blobManagerSnapshot, _storage, createIdCompressor,
|
|
494
|
+
constructor(context, registry, metadata, electedSummarizerData, chunks, dataStoreAliasMap, runtimeOptions, containerScope, logger, existing, blobManagerSnapshot, _storage, createIdCompressor, documentsSchemaController, featureGatesForTelemetry, provideEntryPoint, requestHandler, summaryConfiguration = {
|
|
456
495
|
// the defaults
|
|
457
496
|
...DefaultSummaryConfiguration,
|
|
458
497
|
// the runtime configuration overrides
|
|
@@ -466,18 +505,13 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
466
505
|
this.logger = logger;
|
|
467
506
|
this._storage = _storage;
|
|
468
507
|
this.createIdCompressor = createIdCompressor;
|
|
469
|
-
this.
|
|
508
|
+
this.documentsSchemaController = documentsSchemaController;
|
|
470
509
|
this.requestHandler = requestHandler;
|
|
471
510
|
this.summaryConfiguration = summaryConfiguration;
|
|
472
511
|
this.imminentClosure = false;
|
|
473
512
|
// We accumulate Id compressor Ops while Id compressor is not loaded yet (only for "delayed" mode)
|
|
474
513
|
// Once it loads, it will process all such ops and we will stop accumulating further ops - ops will be processes as they come in.
|
|
475
514
|
this.pendingIdCompressorOps = [];
|
|
476
|
-
/**
|
|
477
|
-
* True if we have ID compressor loading in-flight (async operation). Useful only for
|
|
478
|
-
* this.idCompressorMode === "delayed" mode
|
|
479
|
-
*/
|
|
480
|
-
this.compressorLoadInitiated = false;
|
|
481
515
|
this.defaultMaxConsecutiveReconnects = 7;
|
|
482
516
|
this._orderSequentiallyCalls = 0;
|
|
483
517
|
this.flushTaskExists = false;
|
|
@@ -507,6 +541,20 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
507
541
|
expiry: { policy: "absolute", durationMs: 60000 },
|
|
508
542
|
});
|
|
509
543
|
const { options, clientDetails, connected, baseSnapshot, submitFn, submitBatchFn, submitSummaryFn, submitSignalFn, disposeFn, closeFn, deltaManager, quorum, audience, loader, pendingLocalState, supportedFeatures, } = context;
|
|
544
|
+
this.mc = createChildMonitoringContext({
|
|
545
|
+
logger: this.logger,
|
|
546
|
+
namespace: "ContainerRuntime",
|
|
547
|
+
});
|
|
548
|
+
// If we support multiple algorithms in the future, then we would need to manage it here carefully.
|
|
549
|
+
// We can use runtimeOptions.compressionOptions.compressionAlgorithm, but only if it's in the schema list!
|
|
550
|
+
// If it's not in the list, then we will need to either use no compression, or fallback to some other (supported by format)
|
|
551
|
+
// compression.
|
|
552
|
+
const compressionOptions = {
|
|
553
|
+
minimumBatchSizeInBytes: this.documentSchema.compressionLz4
|
|
554
|
+
? runtimeOptions.compressionOptions.minimumBatchSizeInBytes
|
|
555
|
+
: Number.POSITIVE_INFINITY,
|
|
556
|
+
compressionAlgorithm: CompressionAlgorithms.lz4,
|
|
557
|
+
};
|
|
510
558
|
this.innerDeltaManager = deltaManager;
|
|
511
559
|
this.deltaManager = new DeltaManagerSummarizerProxy(this.innerDeltaManager);
|
|
512
560
|
// Here we could wrap/intercept on these functions to block/modify outgoing messages if needed.
|
|
@@ -540,10 +588,6 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
540
588
|
this.disposeFn = disposeFn ?? closeFn;
|
|
541
589
|
// In cases of summarizer, we want to dispose instead since consumer doesn't interact with this container
|
|
542
590
|
this.closeFn = this.isSummarizerClient ? this.disposeFn : closeFn;
|
|
543
|
-
this.mc = createChildMonitoringContext({
|
|
544
|
-
logger: this.logger,
|
|
545
|
-
namespace: "ContainerRuntime",
|
|
546
|
-
});
|
|
547
591
|
let loadSummaryNumber;
|
|
548
592
|
// Get the container creation metadata. For new container, we initialize these. For existing containers,
|
|
549
593
|
// get the values from the metadata blob.
|
|
@@ -564,7 +608,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
564
608
|
loadSummaryNumber = 0;
|
|
565
609
|
}
|
|
566
610
|
this.nextSummaryNumber = loadSummaryNumber + 1;
|
|
567
|
-
this.messageAtLastSummary = metadata
|
|
611
|
+
this.messageAtLastSummary = lastMessageFromMetadata(metadata);
|
|
568
612
|
// Note that we only need to pull the *initial* connected state from the context.
|
|
569
613
|
// Later updates come through calls to setConnectionState.
|
|
570
614
|
this._connected = connected;
|
|
@@ -681,18 +725,14 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
681
725
|
clientId: () => this.clientId,
|
|
682
726
|
close: this.closeFn,
|
|
683
727
|
connected: () => this.connected,
|
|
684
|
-
reSubmit:
|
|
728
|
+
reSubmit: (message) => {
|
|
729
|
+
this.reSubmit(message);
|
|
730
|
+
this.flush();
|
|
731
|
+
},
|
|
685
732
|
reSubmitBatch: this.reSubmitBatch.bind(this),
|
|
686
733
|
isActiveConnection: () => this.innerDeltaManager.active,
|
|
687
734
|
isAttached: () => this.attachState !== AttachState.Detached,
|
|
688
735
|
}, pendingRuntimeState?.pending, this.logger);
|
|
689
|
-
const disableCompression = this.mc.config.getBoolean("Fluid.ContainerRuntime.CompressionDisabled");
|
|
690
|
-
const compressionOptions = disableCompression === true
|
|
691
|
-
? {
|
|
692
|
-
minimumBatchSizeInBytes: Number.POSITIVE_INFINITY,
|
|
693
|
-
compressionAlgorithm: CompressionAlgorithms.lz4,
|
|
694
|
-
}
|
|
695
|
-
: runtimeOptions.compressionOptions;
|
|
696
736
|
const disablePartialFlush = this.mc.config.getBoolean("Fluid.ContainerRuntime.DisablePartialFlush");
|
|
697
737
|
const legacySendBatchFn = makeLegacySendBatchFn(this.submitFn, this.innerDeltaManager);
|
|
698
738
|
this.outbox = new Outbox({
|
|
@@ -797,10 +837,10 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
797
837
|
disableIsolatedChannels: metadata?.disableIsolatedChannels,
|
|
798
838
|
gcVersion: metadata?.gcFeature,
|
|
799
839
|
options: JSON.stringify(runtimeOptions),
|
|
800
|
-
idCompressorModeMetadata: metadata?.idCompressorMode,
|
|
840
|
+
idCompressorModeMetadata: metadata?.documentSchema?.runtime?.idCompressorMode,
|
|
801
841
|
idCompressorMode: this.idCompressorMode,
|
|
802
842
|
featureGates: JSON.stringify({
|
|
803
|
-
|
|
843
|
+
...featureGatesForTelemetry,
|
|
804
844
|
disableOpReentryCheck,
|
|
805
845
|
disableChunking,
|
|
806
846
|
disableAttachReorder: this.disableAttachReorder,
|
|
@@ -823,6 +863,20 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
823
863
|
// saved state, i.e. all the ops marked by Loader layer sa savedOp === true.
|
|
824
864
|
this.skipSavedCompressorOps = pendingRuntimeState?.pendingIdCompressorState !== undefined;
|
|
825
865
|
}
|
|
866
|
+
onSchemaChange(schema) {
|
|
867
|
+
// Most of the settings will be picked up only by new sessions (i.e. after reload).
|
|
868
|
+
// We can make it better in the future (i.e. start to use op compression right away), but for simplicity
|
|
869
|
+
// this is not done.
|
|
870
|
+
// But ID compressor is special. It's possible, that in future, we will remove "stickiness" of ID compressor setting
|
|
871
|
+
// and will allow to start using it. If that were to happen, we want to ensure that we do not break eventual consistency
|
|
872
|
+
// promises. To do so, we need to initialize id compressor right away.
|
|
873
|
+
// As it's implemented right now (with async initialization), this will only work for "off" -> "delayed" transitions.
|
|
874
|
+
// Anything else is too risky, and requires ability to initialize ID compressor synchronously!
|
|
875
|
+
if (schema.runtime.idCompressorMode !== undefined) {
|
|
876
|
+
// eslint-disable-next-line @typescript-eslint/no-floating-promises
|
|
877
|
+
this.loadIdCompressor();
|
|
878
|
+
}
|
|
879
|
+
}
|
|
826
880
|
getCreateChildSummarizerNodeFn(id, createParam) {
|
|
827
881
|
return (summarizeInternal, getGCDataFn) => this.summarizerNode.createChild(summarizeInternal, id, createParam, undefined, getGCDataFn);
|
|
828
882
|
}
|
|
@@ -834,7 +888,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
834
888
|
assert(false, 0x8eb /* should not be called */);
|
|
835
889
|
}
|
|
836
890
|
setChannelDirty(address) {
|
|
837
|
-
assert(false,
|
|
891
|
+
assert(false, 0x909 /* should not be called */);
|
|
838
892
|
}
|
|
839
893
|
/**
|
|
840
894
|
* Initializes the state from the base snapshot this container runtime loaded from.
|
|
@@ -1040,18 +1094,30 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1040
1094
|
}
|
|
1041
1095
|
/** Adds the container's metadata to the given summary tree. */
|
|
1042
1096
|
addMetadataToSummary(summaryTree) {
|
|
1097
|
+
// The last message processed at the time of summary. If there are no new messages, use the message from the
|
|
1098
|
+
// last summary.
|
|
1099
|
+
const message = extractSummaryMetadataMessage(this.deltaManager.lastMessage) ??
|
|
1100
|
+
this.messageAtLastSummary;
|
|
1101
|
+
const documentSchema = this.documentsSchemaController.summarizeDocumentSchema(this.deltaManager.lastSequenceNumber);
|
|
1102
|
+
// Is document schema explicit control on?
|
|
1103
|
+
const explitiSchemaControl = documentSchema?.runtime.explicitSchemaControl;
|
|
1043
1104
|
const metadata = {
|
|
1044
1105
|
...this.createContainerMetadata,
|
|
1045
1106
|
// Increment the summary number for the next summary that will be generated.
|
|
1046
1107
|
summaryNumber: this.nextSummaryNumber++,
|
|
1047
1108
|
summaryFormatVersion: 1,
|
|
1048
1109
|
...this.garbageCollector.getMetadata(),
|
|
1049
|
-
// The last message processed at the time of summary. If there are no new messages, use the message from the
|
|
1050
|
-
// last summary.
|
|
1051
|
-
message: extractSummaryMetadataMessage(this.deltaManager.lastMessage) ??
|
|
1052
|
-
this.messageAtLastSummary,
|
|
1053
1110
|
telemetryDocumentId: this.telemetryDocumentId,
|
|
1054
|
-
|
|
1111
|
+
// If explicit document schema control is not on, use legacy way to supply last message (using 'message' property).
|
|
1112
|
+
// Otherwise use new 'lastMessage' property, but also put content into the 'message' property that cases old
|
|
1113
|
+
// runtimes (that preceed document schema control capabilities) to close container on load due to mismatch in
|
|
1114
|
+
// last message's sequence number.
|
|
1115
|
+
// See also lastMessageFromMetadata()
|
|
1116
|
+
message: explitiSchemaControl
|
|
1117
|
+
? { sequenceNumber: -1 }
|
|
1118
|
+
: message,
|
|
1119
|
+
lastMessage: explitiSchemaControl ? message : undefined,
|
|
1120
|
+
documentSchema,
|
|
1055
1121
|
};
|
|
1056
1122
|
addBlobToSummary(summaryTree, metadataBlobName, JSON.stringify(metadata));
|
|
1057
1123
|
}
|
|
@@ -1112,14 +1178,8 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1112
1178
|
}
|
|
1113
1179
|
return this.consecutiveReconnects < this.maxConsecutiveReconnects;
|
|
1114
1180
|
}
|
|
1115
|
-
resetReconnectCount(
|
|
1116
|
-
|
|
1117
|
-
// in their own batches before the originating batch is sent.
|
|
1118
|
-
// Therefore, receiving them while attempting to send the originating batch
|
|
1119
|
-
// does not mean that the container is making any progress.
|
|
1120
|
-
if (message?.type !== ContainerMessageType.ChunkedOp) {
|
|
1121
|
-
this.consecutiveReconnects = 0;
|
|
1122
|
-
}
|
|
1181
|
+
resetReconnectCount() {
|
|
1182
|
+
this.consecutiveReconnects = 0;
|
|
1123
1183
|
}
|
|
1124
1184
|
replayPendingStates() {
|
|
1125
1185
|
// We need to be able to send ops to replay states
|
|
@@ -1168,7 +1228,9 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1168
1228
|
case ContainerMessageType.Alias:
|
|
1169
1229
|
return this.channelCollection.applyStashedOp(opContents);
|
|
1170
1230
|
case ContainerMessageType.IdAllocation:
|
|
1171
|
-
assert(this.idCompressorMode !==
|
|
1231
|
+
assert(this.idCompressorMode !== undefined, 0x8f1 /* ID compressor should be in use */);
|
|
1232
|
+
return;
|
|
1233
|
+
case ContainerMessageType.DocumentSchemaChange:
|
|
1172
1234
|
return;
|
|
1173
1235
|
case ContainerMessageType.BlobAttach:
|
|
1174
1236
|
return;
|
|
@@ -1199,10 +1261,11 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1199
1261
|
}
|
|
1200
1262
|
}
|
|
1201
1263
|
}
|
|
1202
|
-
|
|
1203
|
-
if (
|
|
1204
|
-
this.
|
|
1205
|
-
this.
|
|
1264
|
+
async loadIdCompressor() {
|
|
1265
|
+
if (this._idCompressor === undefined &&
|
|
1266
|
+
this.idCompressorMode !== undefined &&
|
|
1267
|
+
this._loadIdCompressor === undefined) {
|
|
1268
|
+
this._loadIdCompressor = this.createIdCompressor()
|
|
1206
1269
|
.then((compressor) => {
|
|
1207
1270
|
this._idCompressor = compressor;
|
|
1208
1271
|
for (const range of this.pendingIdCompressorOps) {
|
|
@@ -1212,8 +1275,16 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1212
1275
|
})
|
|
1213
1276
|
.catch((error) => {
|
|
1214
1277
|
this.logger.sendErrorEvent({ eventName: "IdCompressorDelayedLoad" }, error);
|
|
1278
|
+
throw error;
|
|
1215
1279
|
});
|
|
1216
1280
|
}
|
|
1281
|
+
return this._loadIdCompressor;
|
|
1282
|
+
}
|
|
1283
|
+
setConnectionState(connected, clientId) {
|
|
1284
|
+
if (connected && this.idCompressorMode === "delayed") {
|
|
1285
|
+
// eslint-disable-next-line @typescript-eslint/no-floating-promises
|
|
1286
|
+
this.loadIdCompressor();
|
|
1287
|
+
}
|
|
1217
1288
|
if (connected === false && this.delayConnectClientId !== undefined) {
|
|
1218
1289
|
this.delayConnectClientId = undefined;
|
|
1219
1290
|
this.mc.logger.sendTelemetryEvent({
|
|
@@ -1222,6 +1293,9 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1222
1293
|
// Don't propagate "disconnected" event because we didn't propagate the previous "connected" event
|
|
1223
1294
|
return;
|
|
1224
1295
|
}
|
|
1296
|
+
if (!connected) {
|
|
1297
|
+
this.documentsSchemaController.onDisconnect();
|
|
1298
|
+
}
|
|
1225
1299
|
// If there are stashed blobs in the pending state, we need to delay
|
|
1226
1300
|
// propagation of the "connected" event until we have uploaded them to
|
|
1227
1301
|
// ensure we don't submit ops referencing a blob that has not been uploaded
|
|
@@ -1324,10 +1398,13 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1324
1398
|
this.scheduleManager.beforeOpProcessing(message);
|
|
1325
1399
|
this._processedClientSequenceNumber = message.clientSequenceNumber;
|
|
1326
1400
|
try {
|
|
1401
|
+
// See commit that added this assert for more details.
|
|
1402
|
+
// These calls should be made for all but chunked ops:
|
|
1403
|
+
// 1) this.pendingStateManager.processPendingLocalMessage() below
|
|
1404
|
+
// 2) this.resetReconnectCount() below
|
|
1405
|
+
assert(message.type !== ContainerMessageType.ChunkedOp, "we should never get here with chunked ops");
|
|
1327
1406
|
let localOpMetadata;
|
|
1328
|
-
if (local &&
|
|
1329
|
-
messageWithContext.modernRuntimeMessage &&
|
|
1330
|
-
message.type !== ContainerMessageType.ChunkedOp) {
|
|
1407
|
+
if (local && messageWithContext.modernRuntimeMessage) {
|
|
1331
1408
|
localOpMetadata = this.pendingStateManager.processPendingLocalMessage(messageWithContext.message);
|
|
1332
1409
|
}
|
|
1333
1410
|
// If there are no more pending messages after processing a local message,
|
|
@@ -1342,7 +1419,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1342
1419
|
// If we have processed a local op, this means that the container is
|
|
1343
1420
|
// making progress and we can reset the counter for how many times
|
|
1344
1421
|
// we have consecutively replayed the pending states
|
|
1345
|
-
this.resetReconnectCount(
|
|
1422
|
+
this.resetReconnectCount();
|
|
1346
1423
|
}
|
|
1347
1424
|
}
|
|
1348
1425
|
catch (e) {
|
|
@@ -1388,8 +1465,14 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1388
1465
|
this.garbageCollector.processMessage(messageWithContext.message, local);
|
|
1389
1466
|
break;
|
|
1390
1467
|
case ContainerMessageType.ChunkedOp:
|
|
1468
|
+
// From observability POV, we should not exppse the rest of the system (including "op" events on object) to these messages.
|
|
1469
|
+
// Also resetReconnectCount() would be wrong - see comment that was there before this change was made.
|
|
1470
|
+
assert(false, "should not even get here");
|
|
1391
1471
|
case ContainerMessageType.Rejoin:
|
|
1392
1472
|
break;
|
|
1473
|
+
case ContainerMessageType.DocumentSchemaChange:
|
|
1474
|
+
this.documentsSchemaController.processDocumentSchemaOp(messageWithContext.message.contents, messageWithContext.local, messageWithContext.message.sequenceNumber);
|
|
1475
|
+
break;
|
|
1393
1476
|
default: {
|
|
1394
1477
|
// If we didn't necessarily expect a runtime message type, then no worries - just return
|
|
1395
1478
|
// e.g. this case applies to system ops, or legacy ops that would have fallen into the above cases anyway.
|
|
@@ -1619,6 +1702,8 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1619
1702
|
}
|
|
1620
1703
|
break;
|
|
1621
1704
|
}
|
|
1705
|
+
case ContainerMessageType.IdAllocation:
|
|
1706
|
+
case ContainerMessageType.DocumentSchemaChange:
|
|
1622
1707
|
case ContainerMessageType.GC: {
|
|
1623
1708
|
return false;
|
|
1624
1709
|
}
|
|
@@ -1694,6 +1779,8 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
1694
1779
|
// Wrap data store summaries in .channels subtree.
|
|
1695
1780
|
wrapSummaryInChannelsTree(summarizeResult);
|
|
1696
1781
|
const pathPartsForChildren = [channelsTreeName];
|
|
1782
|
+
// Ensure that ID compressor had a chance to load, if we are using delayed mode.
|
|
1783
|
+
await this.loadIdCompressor();
|
|
1697
1784
|
this.addContainerStateToSummary(summarizeResult, fullTree, trackState, telemetryContext);
|
|
1698
1785
|
return {
|
|
1699
1786
|
...summarizeResult,
|
|
@@ -2236,19 +2323,18 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
2236
2323
|
const idAllocationBatchMessage = {
|
|
2237
2324
|
contents: JSON.stringify(idAllocationMessage),
|
|
2238
2325
|
referenceSequenceNumber: this.deltaManager.lastSequenceNumber,
|
|
2239
|
-
metadata: undefined,
|
|
2240
|
-
localOpMetadata: undefined,
|
|
2241
|
-
type: ContainerMessageType.IdAllocation,
|
|
2242
2326
|
};
|
|
2243
2327
|
this.outbox.submitIdAllocation(idAllocationBatchMessage);
|
|
2244
2328
|
}
|
|
2245
2329
|
}
|
|
2246
2330
|
}
|
|
2247
|
-
submit(containerRuntimeMessage, localOpMetadata = undefined, metadata
|
|
2331
|
+
submit(containerRuntimeMessage, localOpMetadata = undefined, metadata) {
|
|
2248
2332
|
this.verifyNotClosed();
|
|
2249
2333
|
this.verifyCanSubmitOps();
|
|
2250
2334
|
// There should be no ops in detached container state!
|
|
2251
2335
|
assert(this.attachState !== AttachState.Detached, 0x132 /* "sending ops in detached container" */);
|
|
2336
|
+
assert(metadata === undefined ||
|
|
2337
|
+
containerRuntimeMessage.type === ContainerMessageType.BlobAttach, "metadata");
|
|
2252
2338
|
const serializedContent = JSON.stringify(containerRuntimeMessage);
|
|
2253
2339
|
// Note that the real (non-proxy) delta manager is used here to get the readonly info. This is because
|
|
2254
2340
|
// container runtime's ability to submit ops depend on the actual readonly state of the delta manager.
|
|
@@ -2261,7 +2347,6 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
2261
2347
|
const type = containerRuntimeMessage.type;
|
|
2262
2348
|
const message = {
|
|
2263
2349
|
contents: serializedContent,
|
|
2264
|
-
type,
|
|
2265
2350
|
metadata,
|
|
2266
2351
|
localOpMetadata,
|
|
2267
2352
|
referenceSequenceNumber: this.deltaManager.lastSequenceNumber,
|
|
@@ -2276,6 +2361,19 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
2276
2361
|
}
|
|
2277
2362
|
else {
|
|
2278
2363
|
this.submitIdAllocationOpIfNeeded();
|
|
2364
|
+
// Allow document schema controller to send a message if it needs to propose change in document schema.
|
|
2365
|
+
// If it needs to send a message, it will call provided callback with payload of such message and rely
|
|
2366
|
+
// on this callback to do actual sending.
|
|
2367
|
+
this.documentsSchemaController.onMessageSent((contents) => {
|
|
2368
|
+
const msg = {
|
|
2369
|
+
type: ContainerMessageType.DocumentSchemaChange,
|
|
2370
|
+
contents,
|
|
2371
|
+
};
|
|
2372
|
+
this.outbox.submit({
|
|
2373
|
+
contents: JSON.stringify(msg),
|
|
2374
|
+
referenceSequenceNumber: this.deltaManager.lastSequenceNumber,
|
|
2375
|
+
});
|
|
2376
|
+
});
|
|
2279
2377
|
// If this is attach message for new data store, and we are in a batch, send this op out of order
|
|
2280
2378
|
// Is it safe:
|
|
2281
2379
|
// Yes, this should be safe reordering. Newly created data stores are not visible through API surface.
|
|
@@ -2447,6 +2545,11 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
2447
2545
|
case ContainerMessageType.GC:
|
|
2448
2546
|
this.submit(message);
|
|
2449
2547
|
break;
|
|
2548
|
+
case ContainerMessageType.DocumentSchemaChange:
|
|
2549
|
+
// There is no need to resend this message. Document schema controller will properly resend it again (if needed)
|
|
2550
|
+
// on a first occasion (any ops sent after reconnect). There is a good chance, though, that it will not want to
|
|
2551
|
+
// send any ops, as some other client already changed schema.
|
|
2552
|
+
break;
|
|
2450
2553
|
default: {
|
|
2451
2554
|
// This case should be very rare - it would imply an op was stashed from a
|
|
2452
2555
|
// future version of runtime code and now is being applied on an older version.
|
|
@@ -2649,8 +2752,7 @@ export class ContainerRuntime extends TypedEventEmitter {
|
|
|
2649
2752
|
}
|
|
2650
2753
|
}
|
|
2651
2754
|
get groupedBatchingEnabled() {
|
|
2652
|
-
|
|
2653
|
-
return killSwitch !== true && this.runtimeOptions.enableGroupedBatching;
|
|
2755
|
+
return this.documentSchema.opGroupingEnabled === true;
|
|
2654
2756
|
}
|
|
2655
2757
|
}
|
|
2656
2758
|
//# sourceMappingURL=containerRuntime.js.map
|