@fluidframework/container-runtime 2.0.0-internal.6.4.0 → 2.0.0-internal.7.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +111 -0
- package/api-extractor.json +13 -1
- package/api-report/container-runtime.api.md +799 -0
- package/dist/blobManager.d.ts +1 -1
- package/dist/blobManager.d.ts.map +1 -1
- package/dist/blobManager.js +7 -7
- package/dist/blobManager.js.map +1 -1
- package/dist/connectionTelemetry.d.ts.map +1 -1
- package/dist/connectionTelemetry.js +75 -42
- package/dist/connectionTelemetry.js.map +1 -1
- package/dist/container-runtime-alpha.d.ts +1554 -0
- package/dist/container-runtime-beta.d.ts +1554 -0
- package/dist/container-runtime-public.d.ts +1554 -0
- package/dist/container-runtime.d.ts +1611 -0
- package/dist/containerHandleContext.js +3 -3
- package/dist/containerHandleContext.js.map +1 -1
- package/dist/containerRuntime.d.ts +28 -24
- package/dist/containerRuntime.d.ts.map +1 -1
- package/dist/containerRuntime.js +277 -256
- package/dist/containerRuntime.js.map +1 -1
- package/dist/dataStore.js +9 -9
- package/dist/dataStore.js.map +1 -1
- package/dist/dataStoreContext.d.ts +1 -3
- package/dist/dataStoreContext.d.ts.map +1 -1
- package/dist/dataStoreContext.js +54 -58
- package/dist/dataStoreContext.js.map +1 -1
- package/dist/dataStoreRegistry.js +3 -3
- package/dist/dataStoreRegistry.js.map +1 -1
- package/dist/deltaManagerProxyBase.js +4 -4
- package/dist/deltaManagerProxyBase.js.map +1 -1
- package/dist/deltaManagerSummarizerProxy.js +6 -6
- package/dist/deltaManagerSummarizerProxy.js.map +1 -1
- package/dist/deltaScheduler.js.map +1 -1
- package/dist/error.d.ts.map +1 -1
- package/dist/error.js.map +1 -1
- package/dist/gc/garbageCollection.js +13 -13
- package/dist/gc/garbageCollection.js.map +1 -1
- package/dist/gc/gcDefinitions.d.ts +4 -15
- package/dist/gc/gcDefinitions.d.ts.map +1 -1
- package/dist/gc/gcDefinitions.js.map +1 -1
- package/dist/gc/gcTelemetry.d.ts +1 -1
- package/dist/gc/gcTelemetry.d.ts.map +1 -1
- package/dist/gc/gcUnreferencedStateTracker.js +3 -3
- package/dist/gc/gcUnreferencedStateTracker.js.map +1 -1
- package/dist/id-compressor/appendOnlySortedMap.js.map +1 -1
- package/dist/id-compressor/idCompressor.js.map +1 -1
- package/dist/id-compressor/identifiers.d.ts +3 -3
- package/dist/id-compressor/identifiers.d.ts.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +2 -1
- package/dist/index.js.map +1 -1
- package/dist/messageTypes.d.ts +17 -17
- package/dist/messageTypes.d.ts.map +1 -1
- package/dist/messageTypes.js +1 -1
- package/dist/messageTypes.js.map +1 -1
- package/dist/opLifecycle/batchManager.js +6 -6
- package/dist/opLifecycle/batchManager.js.map +1 -1
- package/dist/opLifecycle/definitions.d.ts +2 -2
- package/dist/opLifecycle/definitions.d.ts.map +1 -1
- package/dist/opLifecycle/outbox.d.ts.map +1 -1
- package/dist/opLifecycle/outbox.js +7 -2
- package/dist/opLifecycle/outbox.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 +3 -19
- package/dist/pendingStateManager.d.ts.map +1 -1
- package/dist/pendingStateManager.js +23 -40
- package/dist/pendingStateManager.js.map +1 -1
- package/dist/scheduleManager.js +6 -2
- package/dist/scheduleManager.js.map +1 -1
- package/dist/summary/orderedClientElection.d.ts +3 -3
- package/dist/summary/orderedClientElection.d.ts.map +1 -1
- package/dist/summary/orderedClientElection.js +54 -54
- package/dist/summary/orderedClientElection.js.map +1 -1
- package/dist/summary/runWhileConnectedCoordinator.js +6 -6
- package/dist/summary/runWhileConnectedCoordinator.js.map +1 -1
- package/dist/summary/runningSummarizer.js +37 -37
- package/dist/summary/runningSummarizer.js.map +1 -1
- package/dist/summary/summarizer.d.ts +1 -0
- package/dist/summary/summarizer.d.ts.map +1 -1
- package/dist/summary/summarizer.js +17 -8
- package/dist/summary/summarizer.js.map +1 -1
- package/dist/summary/summarizerClientElection.js +6 -6
- package/dist/summary/summarizerClientElection.js.map +1 -1
- package/dist/summary/summarizerHeuristics.js +9 -9
- package/dist/summary/summarizerHeuristics.js.map +1 -1
- package/dist/summary/summarizerNode/summarizerNode.js +7 -7
- 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 +3 -3
- package/dist/summary/summarizerNode/summarizerNodeUtils.js.map +1 -1
- package/dist/summary/summarizerNode/summarizerNodeWithGc.d.ts +2 -2
- package/dist/summary/summarizerNode/summarizerNodeWithGc.d.ts.map +1 -1
- package/dist/summary/summarizerTypes.d.ts +12 -12
- package/dist/summary/summarizerTypes.d.ts.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 +22 -21
- package/dist/summary/summaryCollection.js.map +1 -1
- package/dist/summary/summaryFormat.d.ts +5 -5
- package/dist/summary/summaryFormat.d.ts.map +1 -1
- package/dist/summary/summaryGenerator.d.ts +3 -3
- package/dist/summary/summaryGenerator.d.ts.map +1 -1
- package/dist/summary/summaryGenerator.js.map +1 -1
- package/dist/summary/summaryManager.d.ts +2 -2
- package/dist/summary/summaryManager.d.ts.map +1 -1
- package/dist/summary/summaryManager.js +10 -10
- package/dist/summary/summaryManager.js.map +1 -1
- package/dist/throttler.js +16 -16
- package/dist/throttler.js.map +1 -1
- package/dist/tsdoc-metadata.json +1 -1
- package/lib/blobManager.d.ts +1 -1
- package/lib/blobManager.d.ts.map +1 -1
- package/lib/blobManager.js +7 -7
- package/lib/blobManager.js.map +1 -1
- package/lib/connectionTelemetry.d.ts.map +1 -1
- package/lib/connectionTelemetry.js +76 -43
- package/lib/connectionTelemetry.js.map +1 -1
- package/lib/containerHandleContext.js +3 -3
- package/lib/containerHandleContext.js.map +1 -1
- package/lib/containerRuntime.d.ts +28 -24
- package/lib/containerRuntime.d.ts.map +1 -1
- package/lib/containerRuntime.js +268 -252
- package/lib/containerRuntime.js.map +1 -1
- package/lib/dataStore.js +9 -9
- package/lib/dataStore.js.map +1 -1
- package/lib/dataStoreContext.d.ts +1 -3
- package/lib/dataStoreContext.d.ts.map +1 -1
- package/lib/dataStoreContext.js +54 -58
- package/lib/dataStoreContext.js.map +1 -1
- package/lib/dataStoreRegistry.js +3 -3
- package/lib/dataStoreRegistry.js.map +1 -1
- package/lib/deltaManagerProxyBase.js +4 -4
- package/lib/deltaManagerProxyBase.js.map +1 -1
- package/lib/deltaManagerSummarizerProxy.js +6 -6
- package/lib/deltaManagerSummarizerProxy.js.map +1 -1
- package/lib/deltaScheduler.js.map +1 -1
- package/lib/error.d.ts.map +1 -1
- package/lib/error.js.map +1 -1
- package/lib/gc/garbageCollection.js +13 -13
- package/lib/gc/garbageCollection.js.map +1 -1
- package/lib/gc/gcDefinitions.d.ts +4 -15
- package/lib/gc/gcDefinitions.d.ts.map +1 -1
- package/lib/gc/gcDefinitions.js.map +1 -1
- package/lib/gc/gcTelemetry.d.ts +1 -1
- package/lib/gc/gcTelemetry.d.ts.map +1 -1
- package/lib/gc/gcUnreferencedStateTracker.js +3 -3
- package/lib/gc/gcUnreferencedStateTracker.js.map +1 -1
- package/lib/id-compressor/appendOnlySortedMap.js.map +1 -1
- package/lib/id-compressor/idCompressor.js.map +1 -1
- package/lib/id-compressor/identifiers.d.ts +3 -3
- package/lib/id-compressor/identifiers.d.ts.map +1 -1
- package/lib/index.d.ts +1 -1
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -1
- package/lib/index.js.map +1 -1
- package/lib/messageTypes.d.ts +17 -17
- package/lib/messageTypes.d.ts.map +1 -1
- package/lib/opLifecycle/batchManager.js +6 -6
- package/lib/opLifecycle/batchManager.js.map +1 -1
- package/lib/opLifecycle/definitions.d.ts +2 -2
- package/lib/opLifecycle/definitions.d.ts.map +1 -1
- package/lib/opLifecycle/outbox.d.ts.map +1 -1
- package/lib/opLifecycle/outbox.js +7 -2
- package/lib/opLifecycle/outbox.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 +3 -19
- package/lib/pendingStateManager.d.ts.map +1 -1
- package/lib/pendingStateManager.js +23 -40
- package/lib/pendingStateManager.js.map +1 -1
- package/lib/scheduleManager.js +6 -2
- package/lib/scheduleManager.js.map +1 -1
- package/lib/summary/orderedClientElection.d.ts +3 -3
- package/lib/summary/orderedClientElection.d.ts.map +1 -1
- package/lib/summary/orderedClientElection.js +54 -54
- package/lib/summary/orderedClientElection.js.map +1 -1
- package/lib/summary/runWhileConnectedCoordinator.js +6 -6
- package/lib/summary/runWhileConnectedCoordinator.js.map +1 -1
- package/lib/summary/runningSummarizer.js +37 -37
- package/lib/summary/runningSummarizer.js.map +1 -1
- package/lib/summary/summarizer.d.ts +1 -0
- package/lib/summary/summarizer.d.ts.map +1 -1
- package/lib/summary/summarizer.js +18 -9
- package/lib/summary/summarizer.js.map +1 -1
- package/lib/summary/summarizerClientElection.js +6 -6
- package/lib/summary/summarizerClientElection.js.map +1 -1
- package/lib/summary/summarizerHeuristics.js +9 -9
- package/lib/summary/summarizerHeuristics.js.map +1 -1
- package/lib/summary/summarizerNode/summarizerNode.js +7 -7
- 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 +3 -3
- package/lib/summary/summarizerNode/summarizerNodeUtils.js.map +1 -1
- package/lib/summary/summarizerNode/summarizerNodeWithGc.d.ts +2 -2
- package/lib/summary/summarizerNode/summarizerNodeWithGc.d.ts.map +1 -1
- package/lib/summary/summarizerTypes.d.ts +12 -12
- package/lib/summary/summarizerTypes.d.ts.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 +22 -21
- package/lib/summary/summaryCollection.js.map +1 -1
- package/lib/summary/summaryFormat.d.ts +5 -5
- package/lib/summary/summaryFormat.d.ts.map +1 -1
- package/lib/summary/summaryGenerator.d.ts +3 -3
- package/lib/summary/summaryGenerator.d.ts.map +1 -1
- package/lib/summary/summaryGenerator.js.map +1 -1
- package/lib/summary/summaryManager.d.ts +2 -2
- package/lib/summary/summaryManager.d.ts.map +1 -1
- package/lib/summary/summaryManager.js +9 -9
- package/lib/summary/summaryManager.js.map +1 -1
- package/lib/throttler.js +16 -16
- package/lib/throttler.js.map +1 -1
- package/package.json +27 -27
- package/src/blobManager.ts +1 -1
- package/src/connectionTelemetry.ts +97 -52
- package/src/containerRuntime.ts +96 -73
- package/src/dataStore.ts +1 -1
- package/src/dataStoreContext.ts +1 -6
- package/src/error.ts +4 -1
- package/src/gc/gcDefinitions.ts +3 -15
- package/src/gc/gcEarlyAdoption.md +1 -1
- package/src/index.ts +1 -0
- package/src/opLifecycle/README.md +53 -28
- package/src/opLifecycle/outbox.ts +3 -0
- package/src/packageVersion.ts +1 -1
- package/src/pendingStateManager.ts +8 -46
- package/src/scheduleManager.ts +2 -0
- package/src/summary/summarizer.ts +20 -7
- package/src/summary/summaryCollection.ts +1 -0
- package/src/summary/summaryGenerator.ts +3 -3
- package/src/summary/summaryManager.ts +2 -2
|
@@ -4,8 +4,11 @@
|
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
6
|
import {
|
|
7
|
+
IEventSampler,
|
|
8
|
+
ISampledTelemetryLogger,
|
|
7
9
|
ITelemetryLoggerExt,
|
|
8
10
|
createChildLogger,
|
|
11
|
+
createSampledLogger,
|
|
9
12
|
formatTick,
|
|
10
13
|
} from "@fluidframework/telemetry-utils";
|
|
11
14
|
import { IDeltaManager } from "@fluidframework/container-definitions";
|
|
@@ -53,7 +56,6 @@ interface IOpPerfTimings {
|
|
|
53
56
|
}
|
|
54
57
|
|
|
55
58
|
class OpPerfTelemetry {
|
|
56
|
-
private pongCount: number = 0;
|
|
57
59
|
private pingLatency: number | undefined;
|
|
58
60
|
|
|
59
61
|
// Collab window tracking. This is timestamp of %1000 message.
|
|
@@ -61,11 +63,14 @@ class OpPerfTelemetry {
|
|
|
61
63
|
private msnTrackingTimestamp: number = 0;
|
|
62
64
|
// To track round trip time for every %500 client message.
|
|
63
65
|
private clientSequenceNumberForLatencyStatistics: number | undefined;
|
|
64
|
-
|
|
65
|
-
private opProcessingTimes: Partial<IOpPerfTimings> = {};
|
|
66
|
-
|
|
67
66
|
// Performance Data to be reported for ops round trips and processing.
|
|
68
|
-
private
|
|
67
|
+
private readonly latencyStatistics = new Map<
|
|
68
|
+
number,
|
|
69
|
+
{
|
|
70
|
+
opProcessingTimes: Partial<IOpPerfTimings>;
|
|
71
|
+
opPerfData: Partial<IOpPerfTelemetryProperties>;
|
|
72
|
+
}
|
|
73
|
+
>();
|
|
69
74
|
|
|
70
75
|
private firstConnection = true;
|
|
71
76
|
private connectionOpSeqNumber: number | undefined;
|
|
@@ -75,6 +80,12 @@ class OpPerfTelemetry {
|
|
|
75
80
|
|
|
76
81
|
private readonly logger: ITelemetryLoggerExt;
|
|
77
82
|
|
|
83
|
+
private static readonly OP_LATENCY_SAMPLE_RATE = 500;
|
|
84
|
+
private readonly opLatencyLogger: ISampledTelemetryLogger;
|
|
85
|
+
|
|
86
|
+
private static readonly DELTA_LATENCY_SAMPLE_RATE = 100;
|
|
87
|
+
private readonly deltaLatencyLogger: ISampledTelemetryLogger;
|
|
88
|
+
|
|
78
89
|
public constructor(
|
|
79
90
|
private clientId: string | undefined,
|
|
80
91
|
private readonly deltaManager: IDeltaManager<ISequencedDocumentMessage, IDocumentMessage>,
|
|
@@ -82,6 +93,28 @@ class OpPerfTelemetry {
|
|
|
82
93
|
) {
|
|
83
94
|
this.logger = createChildLogger({ logger, namespace: "OpPerf" });
|
|
84
95
|
|
|
96
|
+
const deltaLatencyEventSampler: IEventSampler = (() => {
|
|
97
|
+
let eventCount = -1;
|
|
98
|
+
return {
|
|
99
|
+
sample: () => {
|
|
100
|
+
eventCount++;
|
|
101
|
+
const shouldSample =
|
|
102
|
+
eventCount % OpPerfTelemetry.DELTA_LATENCY_SAMPLE_RATE === 0;
|
|
103
|
+
if (shouldSample) {
|
|
104
|
+
eventCount = 0;
|
|
105
|
+
}
|
|
106
|
+
return shouldSample;
|
|
107
|
+
},
|
|
108
|
+
};
|
|
109
|
+
})();
|
|
110
|
+
|
|
111
|
+
this.deltaLatencyLogger = createSampledLogger(logger, deltaLatencyEventSampler);
|
|
112
|
+
|
|
113
|
+
// The SampledLogger here is used get access to the isSamplingDisabled property dervied from
|
|
114
|
+
// telemetry config properties. The actual sampling logic for op messages happens outside this SampledLogger
|
|
115
|
+
// due to complexity of the different asynchronus scenarios of the op message lifecycle.
|
|
116
|
+
this.opLatencyLogger = createSampledLogger(logger);
|
|
117
|
+
|
|
85
118
|
this.deltaManager.on("pong", (latency) => this.recordPingTime(latency));
|
|
86
119
|
this.deltaManager.on("submitOp", (message) => this.beforeOpSubmit(message));
|
|
87
120
|
|
|
@@ -103,42 +136,47 @@ class OpPerfTelemetry {
|
|
|
103
136
|
this.deltaManager.on("disconnect", () => {
|
|
104
137
|
this.sequenceNumberForMsnTracking = undefined;
|
|
105
138
|
this.clientSequenceNumberForLatencyStatistics = undefined;
|
|
106
|
-
this.opProcessingTimes = {};
|
|
107
|
-
this.opPerfData = {};
|
|
108
139
|
this.connectionOpSeqNumber = undefined;
|
|
109
140
|
this.firstConnection = false;
|
|
110
|
-
this.
|
|
141
|
+
this.latencyStatistics.clear();
|
|
111
142
|
});
|
|
112
143
|
|
|
113
144
|
this.deltaManager.outbound.on("push", (messages) => {
|
|
114
145
|
for (const msg of messages) {
|
|
115
146
|
if (
|
|
116
147
|
msg.type === MessageType.Operation &&
|
|
117
|
-
this.
|
|
148
|
+
(this.opLatencyLogger.isSamplingDisabled ||
|
|
149
|
+
this.clientSequenceNumberForLatencyStatistics === msg.clientSequenceNumber)
|
|
118
150
|
) {
|
|
151
|
+
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
|
|
152
|
+
const latencyStats = this.latencyStatistics.get(msg.clientSequenceNumber)!;
|
|
153
|
+
assert(
|
|
154
|
+
latencyStats !== undefined,
|
|
155
|
+
0x7c2 /* Latency stats for op should exist */,
|
|
156
|
+
);
|
|
119
157
|
assert(
|
|
120
|
-
|
|
158
|
+
latencyStats.opProcessingTimes.outboundPushEventTime === undefined,
|
|
121
159
|
0x2c8 /* "outboundPushEventTime should be undefined" */,
|
|
122
160
|
);
|
|
123
161
|
assert(
|
|
124
|
-
|
|
162
|
+
latencyStats.opPerfData.durationNetwork === undefined,
|
|
125
163
|
0x2c9 /* "durationNetwork should be undefined" */,
|
|
126
164
|
);
|
|
127
|
-
|
|
165
|
+
latencyStats.opProcessingTimes.outboundPushEventTime = Date.now();
|
|
128
166
|
|
|
129
167
|
assert(
|
|
130
|
-
|
|
168
|
+
latencyStats.opPerfData.durationOutboundBatching === undefined,
|
|
131
169
|
0x2ca /* "durationOutboundBatching should be undefined" */,
|
|
132
170
|
);
|
|
133
171
|
|
|
134
172
|
assert(
|
|
135
|
-
|
|
173
|
+
latencyStats.opProcessingTimes.submitOpEventTime !== undefined,
|
|
136
174
|
0x2cb /* "submitOpEventTime should be undefined" */,
|
|
137
175
|
);
|
|
138
176
|
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
177
|
+
latencyStats.opPerfData.durationOutboundBatching =
|
|
178
|
+
latencyStats.opProcessingTimes.outboundPushEventTime -
|
|
179
|
+
latencyStats.opProcessingTimes.submitOpEventTime;
|
|
142
180
|
}
|
|
143
181
|
}
|
|
144
182
|
});
|
|
@@ -147,15 +185,20 @@ class OpPerfTelemetry {
|
|
|
147
185
|
if (
|
|
148
186
|
this.clientId === message.clientId &&
|
|
149
187
|
message.type === MessageType.Operation &&
|
|
150
|
-
this.
|
|
151
|
-
|
|
188
|
+
(this.opLatencyLogger.isSamplingDisabled ||
|
|
189
|
+
this.clientSequenceNumberForLatencyStatistics === message.clientSequenceNumber)
|
|
152
190
|
) {
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
191
|
+
// We do an explicit check for undefined right after this
|
|
192
|
+
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
|
|
193
|
+
const latencyStats = this.latencyStatistics.get(message.clientSequenceNumber)!;
|
|
194
|
+
assert(latencyStats !== undefined, 0x7c3 /* Latency stats for op should exist */);
|
|
195
|
+
if (latencyStats.opProcessingTimes.outboundPushEventTime !== undefined) {
|
|
196
|
+
latencyStats.opProcessingTimes.inboundPushEventTime = Date.now();
|
|
197
|
+
latencyStats.opPerfData.durationNetwork =
|
|
198
|
+
latencyStats.opProcessingTimes.inboundPushEventTime -
|
|
199
|
+
latencyStats.opProcessingTimes.outboundPushEventTime;
|
|
200
|
+
latencyStats.opPerfData.lengthInboundQueue = this.deltaManager.inbound.length;
|
|
201
|
+
}
|
|
159
202
|
}
|
|
160
203
|
});
|
|
161
204
|
|
|
@@ -201,32 +244,33 @@ class OpPerfTelemetry {
|
|
|
201
244
|
});
|
|
202
245
|
}
|
|
203
246
|
|
|
204
|
-
// logging one in every
|
|
205
|
-
if (this.
|
|
206
|
-
this.
|
|
247
|
+
// logging one in every DELTA_LATENCY_SAMPLE_RATE pongs, including the first time, if it is a "write" client.
|
|
248
|
+
if (this.deltaManager.active) {
|
|
249
|
+
this.deltaLatencyLogger.sendPerformanceEvent({
|
|
207
250
|
eventName: "DeltaLatency",
|
|
208
251
|
duration: latency,
|
|
209
252
|
});
|
|
210
253
|
}
|
|
211
|
-
this.pongCount++;
|
|
212
254
|
}
|
|
213
255
|
|
|
214
256
|
private beforeOpSubmit(message: IDocumentMessage) {
|
|
215
257
|
// start with first client op and measure latency every 500 client ops
|
|
216
258
|
if (
|
|
217
|
-
this.
|
|
218
|
-
|
|
259
|
+
this.opLatencyLogger.isSamplingDisabled ||
|
|
260
|
+
(this.clientSequenceNumberForLatencyStatistics === undefined &&
|
|
261
|
+
message.clientSequenceNumber % OpPerfTelemetry.OP_LATENCY_SAMPLE_RATE === 1)
|
|
219
262
|
) {
|
|
220
263
|
assert(
|
|
221
|
-
this.
|
|
222
|
-
|
|
223
|
-
);
|
|
224
|
-
assert(
|
|
225
|
-
this.opPerfData.durationNetwork === undefined,
|
|
226
|
-
0x2cd /* "durationNetwork should be undefined" */,
|
|
264
|
+
this.latencyStatistics.get(message.clientSequenceNumber) === undefined,
|
|
265
|
+
0x7c4 /* Existing op perf data for client sequence number */,
|
|
227
266
|
);
|
|
228
|
-
this.opProcessingTimes.submitOpEventTime = Date.now();
|
|
229
267
|
this.clientSequenceNumberForLatencyStatistics = message.clientSequenceNumber;
|
|
268
|
+
this.latencyStatistics.set(message.clientSequenceNumber, {
|
|
269
|
+
opProcessingTimes: {
|
|
270
|
+
submitOpEventTime: Date.now(),
|
|
271
|
+
},
|
|
272
|
+
opPerfData: {},
|
|
273
|
+
});
|
|
230
274
|
}
|
|
231
275
|
}
|
|
232
276
|
|
|
@@ -261,20 +305,23 @@ class OpPerfTelemetry {
|
|
|
261
305
|
|
|
262
306
|
if (
|
|
263
307
|
this.clientId === message.clientId &&
|
|
264
|
-
this.
|
|
308
|
+
(this.opLatencyLogger.isSamplingDisabled ||
|
|
309
|
+
this.clientSequenceNumberForLatencyStatistics === message.clientSequenceNumber)
|
|
265
310
|
) {
|
|
311
|
+
// We do an explicit check for undefined right after this
|
|
312
|
+
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
|
|
313
|
+
const latencyData = this.latencyStatistics.get(message.clientSequenceNumber)!;
|
|
314
|
+
assert(latencyData !== undefined, 0x7c5 /* Undefined latency statistics for op */);
|
|
266
315
|
assert(
|
|
267
|
-
|
|
268
|
-
0x120 /* "Undefined latency statistics (op send time)" */,
|
|
316
|
+
latencyData.opProcessingTimes.submitOpEventTime !== undefined,
|
|
317
|
+
0x120 /* "Undefined latency statistics for op (op send time)" */,
|
|
269
318
|
);
|
|
270
319
|
const currentTime = Date.now();
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
|
|
274
|
-
currentTime - this.opProcessingTimes.inboundPushEventTime;
|
|
320
|
+
if (latencyData.opProcessingTimes.inboundPushEventTime !== undefined) {
|
|
321
|
+
latencyData.opPerfData.durationInboundToProcessing =
|
|
322
|
+
currentTime - latencyData.opProcessingTimes.inboundPushEventTime;
|
|
275
323
|
}
|
|
276
|
-
|
|
277
|
-
const duration = currentTime - this.opProcessingTimes.submitOpEventTime;
|
|
324
|
+
const duration = currentTime - latencyData.opProcessingTimes.submitOpEventTime;
|
|
278
325
|
|
|
279
326
|
// One of the core expectations for Fluid service is to be fast.
|
|
280
327
|
// When it's not the case, we want to learn about it and be able to investigate, so
|
|
@@ -284,8 +331,7 @@ class OpPerfTelemetry {
|
|
|
284
331
|
// The threshold could be adjusted, but ideally it stays workload-agnostic, as service
|
|
285
332
|
// performance impacts all workloads relying on service.
|
|
286
333
|
const category = duration > latencyThreshold ? "error" : "performance";
|
|
287
|
-
|
|
288
|
-
this.logger.sendPerformanceEvent({
|
|
334
|
+
this.opLatencyLogger.sendPerformanceEvent({
|
|
289
335
|
eventName: "OpRoundtripTime",
|
|
290
336
|
sequenceNumber,
|
|
291
337
|
referenceSequenceNumber: message.referenceSequenceNumber,
|
|
@@ -294,11 +340,10 @@ class OpPerfTelemetry {
|
|
|
294
340
|
pingLatency: this.pingLatency,
|
|
295
341
|
msnDistance:
|
|
296
342
|
this.deltaManager.lastSequenceNumber - this.deltaManager.minimumSequenceNumber,
|
|
297
|
-
...
|
|
343
|
+
...latencyData.opPerfData,
|
|
298
344
|
});
|
|
299
345
|
this.clientSequenceNumberForLatencyStatistics = undefined;
|
|
300
|
-
this.
|
|
301
|
-
this.opProcessingTimes = {};
|
|
346
|
+
this.latencyStatistics.delete(message.clientSequenceNumber);
|
|
302
347
|
}
|
|
303
348
|
}
|
|
304
349
|
}
|
package/src/containerRuntime.ts
CHANGED
|
@@ -8,9 +8,11 @@ import {
|
|
|
8
8
|
FluidObject,
|
|
9
9
|
IFluidHandle,
|
|
10
10
|
IFluidHandleContext,
|
|
11
|
+
// eslint-disable-next-line import/no-deprecated
|
|
11
12
|
IFluidRouter,
|
|
12
13
|
IRequest,
|
|
13
14
|
IResponse,
|
|
15
|
+
IProvideFluidHandleContext,
|
|
14
16
|
} from "@fluidframework/core-interfaces";
|
|
15
17
|
import {
|
|
16
18
|
IAudience,
|
|
@@ -21,6 +23,7 @@ import {
|
|
|
21
23
|
ICriticalContainerError,
|
|
22
24
|
AttachState,
|
|
23
25
|
ILoaderOptions,
|
|
26
|
+
ILoader,
|
|
24
27
|
LoaderHeader,
|
|
25
28
|
} from "@fluidframework/container-definitions";
|
|
26
29
|
import {
|
|
@@ -97,11 +100,11 @@ import {
|
|
|
97
100
|
create404Response,
|
|
98
101
|
exceptionToResponse,
|
|
99
102
|
GCDataBuilder,
|
|
100
|
-
requestFluidObject,
|
|
101
103
|
seqFromTree,
|
|
102
104
|
calculateStats,
|
|
103
105
|
TelemetryContext,
|
|
104
106
|
ReadAndParseBlob,
|
|
107
|
+
responseToException,
|
|
105
108
|
} from "@fluidframework/runtime-utils";
|
|
106
109
|
import { v4 as uuid } from "uuid";
|
|
107
110
|
import { ContainerFluidHandleContext } from "./containerHandleContext";
|
|
@@ -141,7 +144,6 @@ import {
|
|
|
141
144
|
IConnectableRuntime,
|
|
142
145
|
IGeneratedSummaryStats,
|
|
143
146
|
ISubmitSummaryOptions,
|
|
144
|
-
ISummarizer,
|
|
145
147
|
ISummarizerInternalsProvider,
|
|
146
148
|
ISummarizerRuntime,
|
|
147
149
|
IRefreshSummaryAckOptions,
|
|
@@ -154,6 +156,7 @@ import {
|
|
|
154
156
|
EnqueueSummarizeResult,
|
|
155
157
|
ISummarizerEvents,
|
|
156
158
|
IBaseSummarizeResult,
|
|
159
|
+
ISummarizer,
|
|
157
160
|
} from "./summary";
|
|
158
161
|
import { formExponentialFn, Throttler } from "./throttler";
|
|
159
162
|
import {
|
|
@@ -352,16 +355,17 @@ export interface ISummaryRuntimeOptions {
|
|
|
352
355
|
|
|
353
356
|
/**
|
|
354
357
|
* Options for op compression.
|
|
355
|
-
* @experimental - Not ready for use
|
|
356
358
|
*/
|
|
357
359
|
export interface ICompressionRuntimeOptions {
|
|
358
360
|
/**
|
|
359
|
-
* The
|
|
361
|
+
* The value the batch's content size must exceed for the batch to be compressed.
|
|
362
|
+
* By default the value is 600 * 1024 = 614400 bytes. If the value is set to `Infinity`, compression will be disabled.
|
|
360
363
|
*/
|
|
361
364
|
readonly minimumBatchSizeInBytes: number;
|
|
362
365
|
|
|
363
366
|
/**
|
|
364
367
|
* The compression algorithm that will be used to compress the op.
|
|
368
|
+
* By default the value is `lz4` which is the only compression algorithm currently supported.
|
|
365
369
|
*/
|
|
366
370
|
readonly compressionAlgorithm: CompressionAlgorithms;
|
|
367
371
|
}
|
|
@@ -389,8 +393,7 @@ export interface IContainerRuntimeOptions {
|
|
|
389
393
|
*/
|
|
390
394
|
readonly flushMode?: FlushMode;
|
|
391
395
|
/**
|
|
392
|
-
* Enables the runtime to compress ops.
|
|
393
|
-
* @experimental Not ready for use.
|
|
396
|
+
* Enables the runtime to compress ops. See {@link ICompressionRuntimeOptions}.
|
|
394
397
|
*/
|
|
395
398
|
readonly compressionOptions?: ICompressionRuntimeOptions;
|
|
396
399
|
/**
|
|
@@ -407,12 +410,15 @@ export interface IContainerRuntimeOptions {
|
|
|
407
410
|
/**
|
|
408
411
|
* If the op payload needs to be chunked in order to work around the maximum size of the batch, this value represents
|
|
409
412
|
* how large the individual chunks will be. This is only supported when compression is enabled. If after compression, the
|
|
410
|
-
* batch size exceeds this value, it will be chunked into smaller ops of this size.
|
|
413
|
+
* batch content size exceeds this value, it will be chunked into smaller ops of this exact size.
|
|
411
414
|
*
|
|
412
|
-
*
|
|
413
|
-
*
|
|
415
|
+
* This value is a trade-off between having many small chunks vs fewer larger chunks and by default, the runtime is configured to use
|
|
416
|
+
* 200 * 1024 = 204800 bytes. This default value ensures that no compressed payload's content is able to exceed {@link IContainerRuntimeOptions.maxBatchSizeInBytes}
|
|
417
|
+
* regardless of the overhead of an individual op.
|
|
414
418
|
*
|
|
415
|
-
* @
|
|
419
|
+
* Any value of `chunkSizeInBytes` exceeding {@link IContainerRuntimeOptions.maxBatchSizeInBytes} will disable this feature, therefore if a compressed batch's content
|
|
420
|
+
* size exceeds {@link IContainerRuntimeOptions.maxBatchSizeInBytes} after compression, the container will close with an instance of `GenericError` with
|
|
421
|
+
* the `BatchTooLarge` message.
|
|
416
422
|
*/
|
|
417
423
|
readonly chunkSizeInBytes?: number;
|
|
418
424
|
|
|
@@ -626,13 +632,65 @@ type MessageWithContext =
|
|
|
626
632
|
local: boolean;
|
|
627
633
|
};
|
|
628
634
|
|
|
635
|
+
const summarizerRequestUrl = "_summarizer";
|
|
636
|
+
|
|
637
|
+
/**
|
|
638
|
+
* Create and retrieve the summmarizer
|
|
639
|
+
*/
|
|
640
|
+
async function createSummarizer(loader: ILoader, url: string): Promise<ISummarizer> {
|
|
641
|
+
const request: IRequest = {
|
|
642
|
+
headers: {
|
|
643
|
+
[LoaderHeader.cache]: false,
|
|
644
|
+
[LoaderHeader.clientDetails]: {
|
|
645
|
+
capabilities: { interactive: false },
|
|
646
|
+
type: summarizerClientType,
|
|
647
|
+
},
|
|
648
|
+
[DriverHeader.summarizingClient]: true,
|
|
649
|
+
[LoaderHeader.reconnect]: false,
|
|
650
|
+
},
|
|
651
|
+
url,
|
|
652
|
+
};
|
|
653
|
+
|
|
654
|
+
const resolvedContainer = await loader.resolve(request);
|
|
655
|
+
let fluidObject: FluidObject<ISummarizer> | undefined;
|
|
656
|
+
|
|
657
|
+
// Older containers may not have the "getEntryPoint" API
|
|
658
|
+
// ! This check will need to stay until LTS of loader moves past 2.0.0-internal.7.0.0
|
|
659
|
+
if (resolvedContainer.getEntryPoint !== undefined) {
|
|
660
|
+
fluidObject = await resolvedContainer.getEntryPoint();
|
|
661
|
+
} else {
|
|
662
|
+
const response = await resolvedContainer.request({ url: `/${summarizerRequestUrl}` });
|
|
663
|
+
if (response.status !== 200 || response.mimeType !== "fluid/object") {
|
|
664
|
+
throw responseToException(response, request);
|
|
665
|
+
}
|
|
666
|
+
fluidObject = response.value;
|
|
667
|
+
}
|
|
668
|
+
|
|
669
|
+
if (fluidObject?.ISummarizer === undefined) {
|
|
670
|
+
throw new UsageError("Fluid object does not implement ISummarizer");
|
|
671
|
+
}
|
|
672
|
+
return fluidObject.ISummarizer;
|
|
673
|
+
}
|
|
674
|
+
|
|
675
|
+
/**
|
|
676
|
+
* This function is not supported publicly and exists for e2e testing
|
|
677
|
+
*/
|
|
678
|
+
export async function TEST_requestSummarizer(loader: ILoader, url: string): Promise<ISummarizer> {
|
|
679
|
+
return createSummarizer(loader, url);
|
|
680
|
+
}
|
|
681
|
+
|
|
629
682
|
/**
|
|
630
683
|
* Represents the runtime of the container. Contains helper functions/state of the container.
|
|
631
684
|
* It will define the store level mappings.
|
|
632
685
|
*/
|
|
633
686
|
export class ContainerRuntime
|
|
634
687
|
extends TypedEventEmitter<IContainerRuntimeEvents & ISummarizerEvents>
|
|
635
|
-
implements
|
|
688
|
+
implements
|
|
689
|
+
IContainerRuntime,
|
|
690
|
+
IRuntime,
|
|
691
|
+
ISummarizerRuntime,
|
|
692
|
+
ISummarizerInternalsProvider,
|
|
693
|
+
IProvideFluidHandleContext
|
|
636
694
|
{
|
|
637
695
|
/**
|
|
638
696
|
* @deprecated - Will be removed in future major release. Migrate all usage of IFluidRouter to the "entryPoint" pattern. Refer to Removing-IFluidRouter.md
|
|
@@ -669,10 +727,15 @@ export class ContainerRuntime
|
|
|
669
727
|
context,
|
|
670
728
|
registryEntries,
|
|
671
729
|
existing: existingFlag,
|
|
672
|
-
requestHandler,
|
|
673
730
|
runtimeOptions,
|
|
674
731
|
containerScope,
|
|
675
732
|
containerRuntimeCtor,
|
|
733
|
+
requestHandler,
|
|
734
|
+
provideEntryPoint: () => {
|
|
735
|
+
throw new UsageError(
|
|
736
|
+
"ContainerRuntime.load is deprecated and should no longer be used",
|
|
737
|
+
);
|
|
738
|
+
},
|
|
676
739
|
});
|
|
677
740
|
}
|
|
678
741
|
|
|
@@ -688,7 +751,7 @@ export class ContainerRuntime
|
|
|
688
751
|
* - containerScope - runtime services provided with context
|
|
689
752
|
* - containerRuntimeCtor - Constructor to use to create the ContainerRuntime instance.
|
|
690
753
|
* This allows mixin classes to leverage this method to define their own async initializer.
|
|
691
|
-
* -
|
|
754
|
+
* - provideEntryPoint - Promise that resolves to an object which will act as entryPoint for the Container.
|
|
692
755
|
* This object should provide all the functionality that the Container is expected to provide to the loader layer.
|
|
693
756
|
*/
|
|
694
757
|
public static async loadRuntime(params: {
|
|
@@ -698,30 +761,21 @@ export class ContainerRuntime
|
|
|
698
761
|
runtimeOptions?: IContainerRuntimeOptions;
|
|
699
762
|
containerScope?: FluidObject;
|
|
700
763
|
containerRuntimeCtor?: typeof ContainerRuntime;
|
|
764
|
+
/** @deprecated Will be removed in future major release. Migrate all usage of IFluidRouter to the "entryPoint" pattern. Refer to Removing-IFluidRouter.md */
|
|
701
765
|
requestHandler?: (request: IRequest, runtime: IContainerRuntime) => Promise<IResponse>;
|
|
702
|
-
|
|
766
|
+
provideEntryPoint: (containerRuntime: IContainerRuntime) => Promise<FluidObject>;
|
|
703
767
|
}): Promise<ContainerRuntime> {
|
|
704
768
|
const {
|
|
705
769
|
context,
|
|
706
770
|
registryEntries,
|
|
707
771
|
existing,
|
|
708
772
|
requestHandler,
|
|
773
|
+
provideEntryPoint,
|
|
709
774
|
runtimeOptions = {},
|
|
710
775
|
containerScope = {},
|
|
711
776
|
containerRuntimeCtor = ContainerRuntime,
|
|
712
777
|
} = params;
|
|
713
778
|
|
|
714
|
-
const initializeEntryPoint =
|
|
715
|
-
params.initializeEntryPoint ??
|
|
716
|
-
(async (containerRuntime: IContainerRuntime) => ({
|
|
717
|
-
get IFluidRouter() {
|
|
718
|
-
return this;
|
|
719
|
-
},
|
|
720
|
-
async request(req) {
|
|
721
|
-
return containerRuntime.request(req);
|
|
722
|
-
},
|
|
723
|
-
}));
|
|
724
|
-
|
|
725
779
|
// If taggedLogger exists, use it. Otherwise, wrap the vanilla logger:
|
|
726
780
|
// back-compat: Remove the TaggedLoggerAdapter fallback once all the host are using loader > 0.45
|
|
727
781
|
const backCompatContext: IContainerContext | OldContainerContextWithLogger = context;
|
|
@@ -850,9 +904,9 @@ export class ContainerRuntime
|
|
|
850
904
|
blobManagerSnapshot,
|
|
851
905
|
context.storage,
|
|
852
906
|
idCompressor,
|
|
907
|
+
provideEntryPoint,
|
|
853
908
|
requestHandler,
|
|
854
909
|
undefined, // summaryConfiguration
|
|
855
|
-
initializeEntryPoint,
|
|
856
910
|
);
|
|
857
911
|
|
|
858
912
|
// Apply stashed ops with a reference sequence number equal to the sequence number of the snapshot,
|
|
@@ -878,17 +932,6 @@ export class ContainerRuntime
|
|
|
878
932
|
return this._storage;
|
|
879
933
|
}
|
|
880
934
|
|
|
881
|
-
/** @deprecated - The functionality is no longer exposed publicly */
|
|
882
|
-
public get reSubmitFn() {
|
|
883
|
-
return (
|
|
884
|
-
type: ContainerMessageType,
|
|
885
|
-
contents: any,
|
|
886
|
-
localOpMetadata: unknown,
|
|
887
|
-
opMetadata: Record<string, unknown> | undefined,
|
|
888
|
-
) => this.reSubmitCore({ type, contents }, localOpMetadata, opMetadata);
|
|
889
|
-
// Note: compatDetails is not included in this deprecated API
|
|
890
|
-
}
|
|
891
|
-
|
|
892
935
|
private readonly submitFn: (
|
|
893
936
|
type: MessageType,
|
|
894
937
|
contents: any,
|
|
@@ -1140,6 +1183,7 @@ export class ContainerRuntime
|
|
|
1140
1183
|
blobManagerSnapshot: IBlobManagerLoadInfo,
|
|
1141
1184
|
private readonly _storage: IDocumentStorageService,
|
|
1142
1185
|
idCompressor: (IIdCompressor & IIdCompressorCore) | undefined,
|
|
1186
|
+
provideEntryPoint: (containerRuntime: IContainerRuntime) => Promise<FluidObject>,
|
|
1143
1187
|
private readonly requestHandler?: (
|
|
1144
1188
|
request: IRequest,
|
|
1145
1189
|
runtime: IContainerRuntime,
|
|
@@ -1150,7 +1194,6 @@ export class ContainerRuntime
|
|
|
1150
1194
|
// the runtime configuration overrides
|
|
1151
1195
|
...runtimeOptions.summaryOptions?.summaryConfigOverrides,
|
|
1152
1196
|
},
|
|
1153
|
-
initializeEntryPoint?: (containerRuntime: IContainerRuntime) => Promise<FluidObject>,
|
|
1154
1197
|
) {
|
|
1155
1198
|
super();
|
|
1156
1199
|
|
|
@@ -1584,7 +1627,7 @@ export class ContainerRuntime
|
|
|
1584
1627
|
this, // IConnectedState
|
|
1585
1628
|
this.summaryCollection,
|
|
1586
1629
|
this.logger,
|
|
1587
|
-
this.
|
|
1630
|
+
this.formCreateSummarizerFn(loader),
|
|
1588
1631
|
new Throttler(
|
|
1589
1632
|
60 * 1000, // 60 sec delay window
|
|
1590
1633
|
30 * 1000, // 30 sec max delay
|
|
@@ -1642,7 +1685,7 @@ export class ContainerRuntime
|
|
|
1642
1685
|
);
|
|
1643
1686
|
return this._summarizer;
|
|
1644
1687
|
}
|
|
1645
|
-
return
|
|
1688
|
+
return provideEntryPoint(this);
|
|
1646
1689
|
});
|
|
1647
1690
|
}
|
|
1648
1691
|
|
|
@@ -1690,7 +1733,7 @@ export class ContainerRuntime
|
|
|
1690
1733
|
const parser = RequestParser.create(request);
|
|
1691
1734
|
const id = parser.pathParts[0];
|
|
1692
1735
|
|
|
1693
|
-
if (id ===
|
|
1736
|
+
if (id === summarizerRequestUrl && parser.pathParts.length === 1) {
|
|
1694
1737
|
if (this._summarizer !== undefined) {
|
|
1695
1738
|
return {
|
|
1696
1739
|
status: 200,
|
|
@@ -1701,6 +1744,7 @@ export class ContainerRuntime
|
|
|
1701
1744
|
return create404Response(request);
|
|
1702
1745
|
}
|
|
1703
1746
|
if (this.requestHandler !== undefined) {
|
|
1747
|
+
// eslint-disable-next-line @typescript-eslint/return-await -- Adding an await here causes test failures
|
|
1704
1748
|
return this.requestHandler(parser, this);
|
|
1705
1749
|
}
|
|
1706
1750
|
|
|
@@ -1720,6 +1764,7 @@ export class ContainerRuntime
|
|
|
1720
1764
|
const id = requestParser.pathParts[0];
|
|
1721
1765
|
|
|
1722
1766
|
if (id === "_channels") {
|
|
1767
|
+
// eslint-disable-next-line @typescript-eslint/return-await -- Adding an await here causes test failures
|
|
1723
1768
|
return this.resolveHandle(requestParser.createSubRequest(1));
|
|
1724
1769
|
}
|
|
1725
1770
|
|
|
@@ -1741,6 +1786,7 @@ export class ContainerRuntime
|
|
|
1741
1786
|
subRequest.url.startsWith("/"),
|
|
1742
1787
|
0x126 /* "Expected createSubRequest url to include a leading slash" */,
|
|
1743
1788
|
);
|
|
1789
|
+
// eslint-disable-next-line @typescript-eslint/return-await -- Adding an await here causes test failures
|
|
1744
1790
|
return dataStore.request(subRequest);
|
|
1745
1791
|
}
|
|
1746
1792
|
|
|
@@ -1753,10 +1799,10 @@ export class ContainerRuntime
|
|
|
1753
1799
|
/**
|
|
1754
1800
|
* {@inheritDoc @fluidframework/container-definitions#IRuntime.getEntryPoint}
|
|
1755
1801
|
*/
|
|
1756
|
-
public async getEntryPoint
|
|
1802
|
+
public async getEntryPoint(): Promise<FluidObject> {
|
|
1757
1803
|
return this.entryPoint;
|
|
1758
1804
|
}
|
|
1759
|
-
private readonly entryPoint: LazyPromise<FluidObject
|
|
1805
|
+
private readonly entryPoint: LazyPromise<FluidObject>;
|
|
1760
1806
|
|
|
1761
1807
|
private internalId(maybeAlias: string): string {
|
|
1762
1808
|
return this.dataStores.aliases.get(maybeAlias) ?? maybeAlias;
|
|
@@ -2338,6 +2384,7 @@ export class ContainerRuntime
|
|
|
2338
2384
|
* @param wait - True if you want to wait for it.
|
|
2339
2385
|
* @deprecated - Use getAliasedDataStoreEntryPoint instead to get an aliased data store's entry point.
|
|
2340
2386
|
*/
|
|
2387
|
+
// eslint-disable-next-line import/no-deprecated
|
|
2341
2388
|
public async getRootDataStore(id: string, wait = true): Promise<IFluidRouter> {
|
|
2342
2389
|
return this.getRootDataStoreChannel(id, wait);
|
|
2343
2390
|
}
|
|
@@ -2526,7 +2573,7 @@ export class ContainerRuntime
|
|
|
2526
2573
|
return false;
|
|
2527
2574
|
}
|
|
2528
2575
|
} else if (type === ContainerMessageType.FluidDataStoreOp) {
|
|
2529
|
-
const envelope = contents
|
|
2576
|
+
const envelope = contents;
|
|
2530
2577
|
if (envelope.address === agentSchedulerId) {
|
|
2531
2578
|
return false;
|
|
2532
2579
|
}
|
|
@@ -3664,7 +3711,7 @@ export class ContainerRuntime
|
|
|
3664
3711
|
case ContainerMessageType.FluidDataStoreOp:
|
|
3665
3712
|
// For operations, call rollbackDataStoreOp which will find the right store
|
|
3666
3713
|
// and trigger rollback on it.
|
|
3667
|
-
this.dataStores.rollbackDataStoreOp(contents
|
|
3714
|
+
this.dataStores.rollbackDataStoreOp(contents, localOpMetadata);
|
|
3668
3715
|
break;
|
|
3669
3716
|
default:
|
|
3670
3717
|
// Don't check message.compatDetails because this is for rolling back a local op so the type will be known
|
|
@@ -3911,35 +3958,11 @@ export class ContainerRuntime
|
|
|
3911
3958
|
}
|
|
3912
3959
|
|
|
3913
3960
|
/**
|
|
3914
|
-
*
|
|
3915
|
-
|
|
3916
|
-
|
|
3917
|
-
private formRequestSummarizerFn(loaderRouter: IFluidRouter) {
|
|
3961
|
+
* Forms a function that will create and retrieve a Summarizer.
|
|
3962
|
+
*/
|
|
3963
|
+
private formCreateSummarizerFn(loader: ILoader) {
|
|
3918
3964
|
return async () => {
|
|
3919
|
-
|
|
3920
|
-
headers: {
|
|
3921
|
-
[LoaderHeader.cache]: false,
|
|
3922
|
-
[LoaderHeader.clientDetails]: {
|
|
3923
|
-
capabilities: { interactive: false },
|
|
3924
|
-
type: summarizerClientType,
|
|
3925
|
-
},
|
|
3926
|
-
[DriverHeader.summarizingClient]: true,
|
|
3927
|
-
[LoaderHeader.reconnect]: false,
|
|
3928
|
-
},
|
|
3929
|
-
url: "/_summarizer",
|
|
3930
|
-
};
|
|
3931
|
-
|
|
3932
|
-
const fluidObject = await requestFluidObject<FluidObject<ISummarizer>>(
|
|
3933
|
-
loaderRouter,
|
|
3934
|
-
request,
|
|
3935
|
-
);
|
|
3936
|
-
const summarizer = fluidObject.ISummarizer;
|
|
3937
|
-
|
|
3938
|
-
if (!summarizer) {
|
|
3939
|
-
throw new UsageError("Fluid object does not implement ISummarizer");
|
|
3940
|
-
}
|
|
3941
|
-
|
|
3942
|
-
return summarizer;
|
|
3965
|
+
return createSummarizer(loader, `/${summarizerRequestUrl}`);
|
|
3943
3966
|
};
|
|
3944
3967
|
}
|
|
3945
3968
|
|
package/src/dataStore.ts
CHANGED
|
@@ -170,7 +170,7 @@ class DataStore implements IDataStore {
|
|
|
170
170
|
/**
|
|
171
171
|
* {@inheritDoc @fluidframework/runtime-definitions#IDataStore.entryPoint}
|
|
172
172
|
*/
|
|
173
|
-
get entryPoint(): IFluidHandle<FluidObject>
|
|
173
|
+
get entryPoint(): IFluidHandle<FluidObject> {
|
|
174
174
|
return this.fluidDataStoreChannel.entryPoint;
|
|
175
175
|
}
|
|
176
176
|
|