@fluidframework/test-utils 2.31.1 → 2.33.0-333010
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 +4 -0
- package/dist/index.d.ts +2 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -1
- package/dist/index.js.map +1 -1
- package/dist/packageVersion.d.ts +1 -1
- package/dist/packageVersion.d.ts.map +1 -1
- package/dist/packageVersion.js +1 -1
- package/dist/packageVersion.js.map +1 -1
- package/dist/testFluidObject.d.ts +23 -10
- package/dist/testFluidObject.d.ts.map +1 -1
- package/dist/testFluidObject.js +22 -19
- package/dist/testFluidObject.js.map +1 -1
- package/dist/testFluidObjectInternal.d.ts +50 -0
- package/dist/testFluidObjectInternal.d.ts.map +1 -0
- package/dist/testFluidObjectInternal.js +78 -0
- package/dist/testFluidObjectInternal.js.map +1 -0
- package/lib/index.d.ts +2 -1
- package/lib/index.d.ts.map +1 -1
- package/lib/index.js +1 -0
- package/lib/index.js.map +1 -1
- package/lib/packageVersion.d.ts +1 -1
- package/lib/packageVersion.d.ts.map +1 -1
- package/lib/packageVersion.js +1 -1
- package/lib/packageVersion.js.map +1 -1
- package/lib/testFluidObject.d.ts +23 -10
- package/lib/testFluidObject.d.ts.map +1 -1
- package/lib/testFluidObject.js +22 -19
- package/lib/testFluidObject.js.map +1 -1
- package/lib/testFluidObjectInternal.d.ts +50 -0
- package/lib/testFluidObjectInternal.d.ts.map +1 -0
- package/lib/testFluidObjectInternal.js +74 -0
- package/lib/testFluidObjectInternal.js.map +1 -0
- package/package.json +24 -23
- package/src/index.ts +3 -0
- package/src/packageVersion.ts +1 -1
- package/src/testFluidObject.ts +61 -28
- package/src/testFluidObjectInternal.ts +110 -0
package/src/testFluidObject.ts
CHANGED
|
@@ -3,7 +3,12 @@
|
|
|
3
3
|
* Licensed under the MIT License.
|
|
4
4
|
*/
|
|
5
5
|
|
|
6
|
-
import {
|
|
6
|
+
import {
|
|
7
|
+
IFluidHandle,
|
|
8
|
+
IRequest,
|
|
9
|
+
IResponse,
|
|
10
|
+
type IFluidLoadable,
|
|
11
|
+
} from "@fluidframework/core-interfaces";
|
|
7
12
|
import { assert } from "@fluidframework/core-utils/internal";
|
|
8
13
|
import {
|
|
9
14
|
FluidDataStoreRuntime,
|
|
@@ -21,13 +26,18 @@ import {
|
|
|
21
26
|
IFluidDataStoreFactory,
|
|
22
27
|
} from "@fluidframework/runtime-definitions/internal";
|
|
23
28
|
import { create404Response } from "@fluidframework/runtime-utils/internal";
|
|
29
|
+
import type { ISharedObject } from "@fluidframework/shared-object-base/internal";
|
|
24
30
|
|
|
25
31
|
import { ITestFluidObject } from "./interfaces.js";
|
|
26
32
|
|
|
27
33
|
/**
|
|
28
|
-
* A test Fluid object that will create a shared object for each key-value pair in the
|
|
34
|
+
* A test Fluid object that will create a shared object for each key-value pair in the initialSharedObjectsFactories passed to load.
|
|
29
35
|
* The shared objects can be retrieved by passing the key of the entry to getSharedObject.
|
|
30
36
|
* It exposes the IFluidDataStoreContext and IFluidDataStoreRuntime.
|
|
37
|
+
* @privateRemarks
|
|
38
|
+
* TODO:
|
|
39
|
+
* Usage of this outside this repo (via ITestFluidObject) should probably be phased out.
|
|
40
|
+
* Once thats done, ITestFluidObject can be made internal and this class can be replaced with the simplified TestFluidObjectInternal.
|
|
31
41
|
* @internal
|
|
32
42
|
*/
|
|
33
43
|
export class TestFluidObject implements ITestFluidObject {
|
|
@@ -39,28 +49,28 @@ export class TestFluidObject implements ITestFluidObject {
|
|
|
39
49
|
return this;
|
|
40
50
|
}
|
|
41
51
|
|
|
42
|
-
public
|
|
43
|
-
return this.innerHandle;
|
|
44
|
-
}
|
|
52
|
+
public readonly handle: IFluidHandle<this>;
|
|
45
53
|
|
|
46
54
|
public root!: ISharedMap;
|
|
47
|
-
private readonly innerHandle: IFluidHandle<this>;
|
|
48
55
|
private initializationPromise: Promise<void> | undefined;
|
|
49
56
|
|
|
50
57
|
/**
|
|
51
58
|
* Creates a new TestFluidObject.
|
|
52
59
|
* @param runtime - The data store runtime.
|
|
53
60
|
* @param context - The data store context.
|
|
54
|
-
* @param
|
|
61
|
+
* @param initialSharedObjectsFactories - A list of id to IChannelFactory mapping. For each item in the list,
|
|
55
62
|
* a shared object is created which can be retrieved by calling getSharedObject() with the id;
|
|
56
63
|
*/
|
|
57
64
|
constructor(
|
|
58
65
|
public readonly runtime: IFluidDataStoreRuntime,
|
|
59
66
|
public readonly channel: IFluidDataStoreChannel,
|
|
60
67
|
public readonly context: IFluidDataStoreContext,
|
|
61
|
-
private readonly
|
|
68
|
+
private readonly initialSharedObjectsFactories: ReadonlyMap<
|
|
69
|
+
string,
|
|
70
|
+
IChannelFactory<ISharedObject>
|
|
71
|
+
>,
|
|
62
72
|
) {
|
|
63
|
-
this.
|
|
73
|
+
this.handle = new FluidObjectHandle(this, "", runtime.objectsRoutingContext);
|
|
64
74
|
}
|
|
65
75
|
|
|
66
76
|
/**
|
|
@@ -68,15 +78,15 @@ export class TestFluidObject implements ITestFluidObject {
|
|
|
68
78
|
* @param id - The id of the shared object to retrieve.
|
|
69
79
|
*/
|
|
70
80
|
public async getSharedObject<T = any>(id: string): Promise<T> {
|
|
71
|
-
if (this.
|
|
81
|
+
if (this.initialSharedObjectsFactories === undefined) {
|
|
72
82
|
throw new Error("Shared objects were not provided during creation.");
|
|
73
83
|
}
|
|
74
84
|
|
|
75
|
-
if (this.
|
|
85
|
+
if (this.initialSharedObjectsFactories.has(id)) {
|
|
76
86
|
const handle = this.root.get<IFluidHandle<T>>(id);
|
|
77
87
|
if (handle === undefined) {
|
|
78
88
|
throw new Error(
|
|
79
|
-
`Shared object with id '${id}' is in
|
|
89
|
+
`Shared object with id '${id}' is in initialSharedObjectsFactories but not found under root.`,
|
|
80
90
|
);
|
|
81
91
|
}
|
|
82
92
|
return handle.get();
|
|
@@ -96,10 +106,12 @@ export class TestFluidObject implements ITestFluidObject {
|
|
|
96
106
|
if (!existing) {
|
|
97
107
|
this.root = SharedMap.create(this.runtime, "root");
|
|
98
108
|
|
|
99
|
-
this.
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
109
|
+
this.initialSharedObjectsFactories.forEach(
|
|
110
|
+
(sharedObjectFactory: IChannelFactory, key: string) => {
|
|
111
|
+
const sharedObject = this.runtime.createChannel(key, sharedObjectFactory.type);
|
|
112
|
+
this.root.set(key, sharedObject.handle);
|
|
113
|
+
},
|
|
114
|
+
);
|
|
103
115
|
|
|
104
116
|
this.root.bindToContext();
|
|
105
117
|
}
|
|
@@ -118,6 +130,20 @@ export class TestFluidObject implements ITestFluidObject {
|
|
|
118
130
|
*/
|
|
119
131
|
export type ChannelFactoryRegistry = Iterable<[string | undefined, IChannelFactory]>;
|
|
120
132
|
|
|
133
|
+
/**
|
|
134
|
+
* Kind of test data object which {@link TestFluidObjectFactory} can create.
|
|
135
|
+
* @internal
|
|
136
|
+
*/
|
|
137
|
+
export type TestDataObjectKind = new (
|
|
138
|
+
runtime: IFluidDataStoreRuntime,
|
|
139
|
+
channel: IFluidDataStoreChannel,
|
|
140
|
+
context: IFluidDataStoreContext,
|
|
141
|
+
initialSharedObjectsFactories: ReadonlyMap<string, IChannelFactory<ISharedObject>>,
|
|
142
|
+
) => IFluidLoadable & {
|
|
143
|
+
request(request: IRequest): Promise<IResponse>;
|
|
144
|
+
initialize(existing: boolean): Promise<void>;
|
|
145
|
+
};
|
|
146
|
+
|
|
121
147
|
/**
|
|
122
148
|
* Creates a factory for a TestFluidObject with the given object factory entries. It creates a data store runtime
|
|
123
149
|
* with the object factories in the entry list. All the entries with an id other than undefined are passed to the
|
|
@@ -156,13 +182,14 @@ export class TestFluidObjectFactory implements IFluidDataStoreFactory {
|
|
|
156
182
|
|
|
157
183
|
/**
|
|
158
184
|
* Creates a new TestFluidObjectFactory.
|
|
159
|
-
* @param
|
|
185
|
+
* @param initialSharedObjectsFactories - A list of id to IChannelFactory mapping. It creates a data store runtime with each
|
|
160
186
|
* IChannelFactory. Entries with string ids are passed to the Fluid object so that it can create a shared object
|
|
161
187
|
* for it.
|
|
162
188
|
*/
|
|
163
189
|
constructor(
|
|
164
|
-
private readonly
|
|
190
|
+
private readonly initialSharedObjectsFactories: ChannelFactoryRegistry,
|
|
165
191
|
public readonly type = "TestFluidObjectFactory",
|
|
192
|
+
private readonly dataObjectKind: TestDataObjectKind = TestFluidObject,
|
|
166
193
|
) {}
|
|
167
194
|
|
|
168
195
|
public async instantiateDataStore(
|
|
@@ -176,16 +203,17 @@ export class TestFluidObjectFactory implements IFluidDataStoreFactory {
|
|
|
176
203
|
dataTypes.set(sharedMapFactory.type, sharedMapFactory);
|
|
177
204
|
|
|
178
205
|
// Add the object factories to the list to be sent to data store runtime.
|
|
179
|
-
for (const [, factory] of this.
|
|
206
|
+
for (const [, factory] of this.initialSharedObjectsFactories) {
|
|
180
207
|
dataTypes.set(factory.type, factory);
|
|
181
208
|
}
|
|
182
209
|
|
|
183
210
|
// Create a map from the factory entries with entries that don't have the id as undefined. This will be
|
|
184
211
|
// passed to the Fluid object.
|
|
185
|
-
const factoryEntriesMapForObject = new Map<string, IChannelFactory
|
|
186
|
-
for (const [id, factory] of this.
|
|
212
|
+
const factoryEntriesMapForObject = new Map<string, IChannelFactory<ISharedObject>>();
|
|
213
|
+
for (const [id, factory] of this.initialSharedObjectsFactories) {
|
|
187
214
|
if (id !== undefined) {
|
|
188
|
-
|
|
215
|
+
// Here we assume the factory produces an ISharedObject.
|
|
216
|
+
factoryEntriesMapForObject.set(id, factory as IChannelFactory<ISharedObject>);
|
|
189
217
|
}
|
|
190
218
|
}
|
|
191
219
|
|
|
@@ -194,19 +222,24 @@ export class TestFluidObjectFactory implements IFluidDataStoreFactory {
|
|
|
194
222
|
// The provideEntryPoint callback below always returns TestFluidObject.
|
|
195
223
|
const dataObject = await rt.entryPoint.get();
|
|
196
224
|
assert(
|
|
197
|
-
dataObject instanceof
|
|
225
|
+
dataObject instanceof this.dataObjectKind,
|
|
198
226
|
"entryPoint should have been initialized by now",
|
|
199
227
|
);
|
|
200
228
|
return dataObject.request(request);
|
|
201
229
|
},
|
|
202
230
|
);
|
|
203
231
|
|
|
204
|
-
const runtime = new runtimeClass(
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
232
|
+
const runtime: FluidDataStoreRuntime = new runtimeClass(
|
|
233
|
+
context,
|
|
234
|
+
dataTypes,
|
|
235
|
+
existing,
|
|
236
|
+
async () => {
|
|
237
|
+
await instance.initialize(true);
|
|
238
|
+
return instance;
|
|
239
|
+
},
|
|
240
|
+
);
|
|
208
241
|
|
|
209
|
-
const instance
|
|
242
|
+
const instance = new this.dataObjectKind(
|
|
210
243
|
runtime, // runtime
|
|
211
244
|
runtime, // channel
|
|
212
245
|
context,
|
|
@@ -0,0 +1,110 @@
|
|
|
1
|
+
/*!
|
|
2
|
+
* Copyright (c) Microsoft Corporation and contributors. All rights reserved.
|
|
3
|
+
* Licensed under the MIT License.
|
|
4
|
+
*/
|
|
5
|
+
|
|
6
|
+
import {
|
|
7
|
+
IFluidHandle,
|
|
8
|
+
IRequest,
|
|
9
|
+
IResponse,
|
|
10
|
+
type IFluidLoadable,
|
|
11
|
+
} from "@fluidframework/core-interfaces";
|
|
12
|
+
import { fail } from "@fluidframework/core-utils/internal";
|
|
13
|
+
import { FluidObjectHandle } from "@fluidframework/datastore/internal";
|
|
14
|
+
import {
|
|
15
|
+
IChannelFactory,
|
|
16
|
+
IFluidDataStoreRuntime,
|
|
17
|
+
type IChannel,
|
|
18
|
+
} from "@fluidframework/datastore-definitions/internal";
|
|
19
|
+
import {
|
|
20
|
+
IFluidDataStoreChannel,
|
|
21
|
+
IFluidDataStoreContext,
|
|
22
|
+
} from "@fluidframework/runtime-definitions/internal";
|
|
23
|
+
import { create404Response } from "@fluidframework/runtime-utils/internal";
|
|
24
|
+
import type {
|
|
25
|
+
ISharedObject,
|
|
26
|
+
SharedObjectKind,
|
|
27
|
+
} from "@fluidframework/shared-object-base/internal";
|
|
28
|
+
|
|
29
|
+
/**
|
|
30
|
+
* A test Fluid object that will create a shared object for each key-value pair in the factoryEntries passed to load.
|
|
31
|
+
* The shared objects can be retrieved by passing the key of the entry to {@link TestFluidObjectInternal.getInitialSharedObject}.
|
|
32
|
+
* It exposes the IFluidDataStoreContext and IFluidDataStoreRuntime.
|
|
33
|
+
* @remarks
|
|
34
|
+
* This is a simplified (does not use SharedMap) alternative to {@link TestFluidObject} which does not implement the external facing {@link ITestFluidObject} interface.
|
|
35
|
+
* @internal
|
|
36
|
+
*/
|
|
37
|
+
export class TestFluidObjectInternal implements IFluidLoadable {
|
|
38
|
+
public get IFluidLoadable() {
|
|
39
|
+
return this;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
public readonly handle: IFluidHandle<this>;
|
|
43
|
+
private initializationPromise: Promise<void> | undefined;
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Creates a new TestFluidObjectInternal.
|
|
47
|
+
* @param runtime - The data store runtime.
|
|
48
|
+
* @param context - The data store context.
|
|
49
|
+
* @param factoryEntries - A list of id to IChannelFactory mapping. For each item in the list,
|
|
50
|
+
* a shared object is created which can be retrieved by calling {@link TestFluidObjectInternal.getInitialSharedObject} with the id;
|
|
51
|
+
* @param initialSharedObjectsFactories - A collection of ids (which can be passed to {@link TestFluidObjectInternal.getInitialSharedObject})
|
|
52
|
+
* and the corresponding factories to use to create the shared objects during initialization.
|
|
53
|
+
*/
|
|
54
|
+
constructor(
|
|
55
|
+
public readonly runtime: IFluidDataStoreRuntime,
|
|
56
|
+
public readonly channel: IFluidDataStoreChannel,
|
|
57
|
+
public readonly context: IFluidDataStoreContext,
|
|
58
|
+
private readonly initialSharedObjectsFactories: ReadonlyMap<
|
|
59
|
+
string,
|
|
60
|
+
IChannelFactory<ISharedObject>
|
|
61
|
+
>,
|
|
62
|
+
) {
|
|
63
|
+
this.handle = new FluidObjectHandle(this, "", runtime.objectsRoutingContext);
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* Retrieves the shared object with the given id:
|
|
68
|
+
* this id must have been a key included in the initialSharedObjectsFactories map passed to the constructor.
|
|
69
|
+
* @param id - The id of the shared object to retrieve.
|
|
70
|
+
*/
|
|
71
|
+
public async getInitialSharedObject(id: string): Promise<IChannel> {
|
|
72
|
+
return (await this.runtime.getChannel(id)) ?? fail("Shared object not found");
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* Retrieves a shared object with the given id.
|
|
77
|
+
* @param kind - The kind of object to retrieve.
|
|
78
|
+
* @param id - The id of the shared object to retrieve.
|
|
79
|
+
*/
|
|
80
|
+
public async getInitialSharedObjectTyped<T>(
|
|
81
|
+
kind: SharedObjectKind<T>,
|
|
82
|
+
id: string,
|
|
83
|
+
): Promise<IChannel & T> {
|
|
84
|
+
const result = (await this.runtime.getChannel(id)) ?? fail("Shared object not found");
|
|
85
|
+
if (kind.is(result)) {
|
|
86
|
+
return result;
|
|
87
|
+
}
|
|
88
|
+
return fail("Wrong kind of shared object");
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
public async request(request: IRequest): Promise<IResponse> {
|
|
92
|
+
return request.url === "" || request.url === "/" || request.url.startsWith("/?")
|
|
93
|
+
? { mimeType: "fluid/object", status: 200, value: this }
|
|
94
|
+
: create404Response(request);
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
public async initialize(existing: boolean) {
|
|
98
|
+
const doInitialization = async () => {
|
|
99
|
+
if (!existing) {
|
|
100
|
+
for (const [key, sharedObjectFactory] of this.initialSharedObjectsFactories) {
|
|
101
|
+
const channel = this.runtime.createChannel(key, sharedObjectFactory.type);
|
|
102
|
+
(channel as ISharedObject).bindToContext();
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
};
|
|
106
|
+
|
|
107
|
+
this.initializationPromise ??= doInitialization();
|
|
108
|
+
return this.initializationPromise;
|
|
109
|
+
}
|
|
110
|
+
}
|