@fluidframework/presence 2.74.0-370705 → 2.80.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.
Files changed (69) hide show
  1. package/dist/alpha.d.ts +1 -0
  2. package/dist/beta.d.ts +1 -0
  3. package/dist/exposedInternalTypes.d.ts +1 -1
  4. package/dist/exposedInternalTypes.d.ts.map +1 -1
  5. package/dist/exposedInternalTypes.js.map +1 -1
  6. package/dist/index.d.ts +1 -1
  7. package/dist/index.d.ts.map +1 -1
  8. package/dist/index.js.map +1 -1
  9. package/dist/internalTypes.d.ts +6 -0
  10. package/dist/internalTypes.d.ts.map +1 -1
  11. package/dist/internalTypes.js.map +1 -1
  12. package/dist/latestMapValueManager.d.ts +33 -14
  13. package/dist/latestMapValueManager.d.ts.map +1 -1
  14. package/dist/latestMapValueManager.js +33 -16
  15. package/dist/latestMapValueManager.js.map +1 -1
  16. package/dist/legacy.alpha.d.ts +1 -0
  17. package/dist/packageVersion.d.ts +1 -1
  18. package/dist/packageVersion.d.ts.map +1 -1
  19. package/dist/packageVersion.js +1 -1
  20. package/dist/packageVersion.js.map +1 -1
  21. package/dist/presenceDatastoreManager.d.ts +7 -11
  22. package/dist/presenceDatastoreManager.d.ts.map +1 -1
  23. package/dist/presenceDatastoreManager.js +11 -62
  24. package/dist/presenceDatastoreManager.js.map +1 -1
  25. package/dist/presenceManager.d.ts.map +1 -1
  26. package/dist/presenceManager.js +68 -23
  27. package/dist/presenceManager.js.map +1 -1
  28. package/dist/stateDatastore.d.ts +2 -2
  29. package/dist/stateDatastore.d.ts.map +1 -1
  30. package/dist/stateDatastore.js.map +1 -1
  31. package/dist/systemWorkspace.d.ts +2 -1
  32. package/dist/systemWorkspace.d.ts.map +1 -1
  33. package/dist/systemWorkspace.js +95 -42
  34. package/dist/systemWorkspace.js.map +1 -1
  35. package/lib/alpha.d.ts +1 -0
  36. package/lib/beta.d.ts +1 -0
  37. package/lib/exposedInternalTypes.d.ts +1 -1
  38. package/lib/exposedInternalTypes.d.ts.map +1 -1
  39. package/lib/exposedInternalTypes.js.map +1 -1
  40. package/lib/index.d.ts +1 -1
  41. package/lib/index.d.ts.map +1 -1
  42. package/lib/index.js.map +1 -1
  43. package/lib/internalTypes.d.ts +6 -0
  44. package/lib/internalTypes.d.ts.map +1 -1
  45. package/lib/internalTypes.js.map +1 -1
  46. package/lib/latestMapValueManager.d.ts +33 -14
  47. package/lib/latestMapValueManager.d.ts.map +1 -1
  48. package/lib/latestMapValueManager.js +33 -16
  49. package/lib/latestMapValueManager.js.map +1 -1
  50. package/lib/legacy.alpha.d.ts +1 -0
  51. package/lib/packageVersion.d.ts +1 -1
  52. package/lib/packageVersion.d.ts.map +1 -1
  53. package/lib/packageVersion.js +1 -1
  54. package/lib/packageVersion.js.map +1 -1
  55. package/lib/presenceDatastoreManager.d.ts +7 -11
  56. package/lib/presenceDatastoreManager.d.ts.map +1 -1
  57. package/lib/presenceDatastoreManager.js +11 -62
  58. package/lib/presenceDatastoreManager.js.map +1 -1
  59. package/lib/presenceManager.d.ts.map +1 -1
  60. package/lib/presenceManager.js +64 -19
  61. package/lib/presenceManager.js.map +1 -1
  62. package/lib/stateDatastore.d.ts +2 -2
  63. package/lib/stateDatastore.d.ts.map +1 -1
  64. package/lib/stateDatastore.js.map +1 -1
  65. package/lib/systemWorkspace.d.ts +2 -1
  66. package/lib/systemWorkspace.d.ts.map +1 -1
  67. package/lib/systemWorkspace.js +95 -42
  68. package/lib/systemWorkspace.js.map +1 -1
  69. package/package.json +25 -24
@@ -1 +1 @@
1
- {"version":3,"file":"latestMapValueManager.js","sourceRoot":"","sources":["../src/latestMapValueManager.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { createEmitter } from \"@fluid-internal/client-utils\";\nimport type { Listenable } from \"@fluidframework/core-interfaces\";\nimport type { IEmitter } from \"@fluidframework/core-interfaces/internal\";\nimport type {\n\tDeepReadonly,\n\tJsonDeserialized,\n\tJsonSerializable,\n} from \"@fluidframework/core-interfaces/internal/exposedUtilityTypes\";\n\nimport type { BroadcastControls, BroadcastControlSettings } from \"./broadcastControls.js\";\nimport { OptionalBroadcastControl } from \"./broadcastControls.js\";\nimport type { InternalTypes } from \"./exposedInternalTypes.js\";\nimport type {\n\tPostUpdateAction,\n\tValidatableOptionalState,\n\tValueManager,\n} from \"./internalTypes.js\";\nimport {\n\tasDeeplyReadonly,\n\tasDeeplyReadonlyDeserializedJson,\n\tisValueRequiredState,\n\tobjectEntries,\n\tobjectKeys,\n\ttoOpaqueJson,\n} from \"./internalUtils.js\";\nimport { createValidatedGetter } from \"./latestValueTypes.js\";\nimport type {\n\tLatestClientData,\n\tLatestData,\n\tLatestMetadata,\n\tProxiedValueAccessor,\n\tRawValueAccessor,\n\tStateSchemaValidator,\n\tValueAccessor,\n} from \"./latestValueTypes.js\";\nimport type { AttendeeId, Attendee, Presence, SpecificAttendee } from \"./presence.js\";\nimport { datastoreFromHandle, type StateDatastore } from \"./stateDatastore.js\";\nimport { brandIVM } from \"./valueManager.js\";\n\n/**\n * Collection of validatable optional values in a \"map\" structure.\n *\n * @remarks\n * Validatable equivalent of {@link InternalTypes.MapValueState}.\n */\ninterface ValidatableMapValueState<T, Keys extends string | number> {\n\trev: number;\n\titems: {\n\t\t// Caution: any particular item may or may not exist\n\t\t// Typescript does not support absent keys without forcing type to also be undefined.\n\t\t// See https://github.com/microsoft/TypeScript/issues/42810.\n\t\t[name in Keys]: ValidatableOptionalState<T>;\n\t};\n}\n\n/**\n * Collection of latest known values for a specific {@link Attendee}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapClientData<\n\tT,\n\tKeys extends string | number,\n\tTValueAccessor extends ValueAccessor<T>,\n\tSpecificAttendeeId extends AttendeeId = AttendeeId,\n> {\n\t/**\n\t * Associated {@link Attendee}.\n\t */\n\tattendee: Attendee<SpecificAttendeeId>;\n\n\t/**\n\t * Map of items for the state.\n\t *\n\t * @privateRemarks This could be regular map currently as no Map is\n\t * stored internally and a new instance is created for every request.\n\t */\n\titems: ReadonlyMap<Keys, LatestData<T, TValueAccessor>>;\n}\n\n/**\n * State of a single item value, its key, and its metadata.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapItemUpdatedClientData<\n\tT,\n\tK extends string | number,\n\tTValueAccessor extends ValueAccessor<T>,\n> extends LatestClientData<T, TValueAccessor> {\n\t/**\n\t * Key of the updated item.\n\t */\n\tkey: K;\n}\n\n/**\n * Identifier and metadata for a removed item.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapItemRemovedClientData<K extends string | number> {\n\t/**\n\t * Associated {@link Attendee}.\n\t */\n\tattendee: Attendee;\n\t/**\n\t * Key of the removed item.\n\t */\n\tkey: K;\n\t/**\n\t * Metadata associated with the removal of the item.\n\t */\n\tmetadata: LatestMetadata;\n}\n\n/**\n * Events from {@link LatestMapRaw}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapEvents<\n\tT,\n\tK extends string | number,\n\tTRemoteValueAccessor extends ValueAccessor<T> = ProxiedValueAccessor<T>,\n> {\n\t/**\n\t * Raised when any item's value for remote client is updated.\n\t * @param updates - Map of one or more values updated.\n\t *\n\t * @remarks The event does not include item removals.\n\t *\n\t * @eventProperty\n\t */\n\tremoteUpdated: (updates: LatestMapClientData<T, K, TRemoteValueAccessor>) => void;\n\n\t/**\n\t * Raised when specific item's value of remote client is updated.\n\t * @param updatedItem - Updated item value.\n\t *\n\t * @eventProperty\n\t */\n\tremoteItemUpdated: (\n\t\tupdatedItem: LatestMapItemUpdatedClientData<T, K, TRemoteValueAccessor>,\n\t) => void;\n\n\t/**\n\t * Raised when specific item of remote client is removed.\n\t * @param removedItem - Removed item.\n\t *\n\t * @eventProperty\n\t */\n\tremoteItemRemoved: (removedItem: LatestMapItemRemovedClientData<K>) => void;\n\n\t/**\n\t * Raised when specific local item's value is updated.\n\t * @param updatedItem - Updated item value.\n\t *\n\t * @eventProperty\n\t */\n\tlocalItemUpdated: (updatedItem: {\n\t\tvalue: DeepReadonly<JsonSerializable<T>>;\n\t\tkey: K;\n\t}) => void;\n\n\t/**\n\t * Raised when specific local item is removed.\n\t * @param removedItem - Removed item.\n\t *\n\t * @eventProperty\n\t */\n\tlocalItemRemoved: (removedItem: {\n\t\tkey: K;\n\t}) => void;\n}\n\n/**\n * Events from {@link LatestMapRaw}.\n *\n * @sealed\n * @beta\n */\nexport type LatestMapRawEvents<T, K extends string | number> = LatestMapEvents<\n\tT,\n\tK,\n\tRawValueAccessor<T>\n>;\n\n/**\n * Map of local client's values. Modifications are transmitted to all other connected clients.\n *\n * @sealed\n * @beta\n */\nexport interface StateMap<K extends string | number, V> {\n\t/**\n\t * ${@link StateMap.delete}s all elements in the StateMap.\n\t * @remarks This is not yet implemented.\n\t */\n\tclear(): void;\n\n\t/**\n\t * Removes the element with the specified key from the StateMap, if it exists.\n\t *\n\t * @returns true if an element in the StateMap existed and has been removed, or false if\n\t * the element does not exist.\n\t * @remarks No entry is fully removed. Instead an undefined placeholder is locally and\n\t * transmitted to all other clients. For better performance limit the number of deleted\n\t * entries and reuse keys when possible.\n\t * @privateRemarks In the future we may add a mechanism to remove the placeholder, at least\n\t * from transmissions after sufficient time has passed.\n\t */\n\tdelete(key: K): boolean;\n\n\t/**\n\t * Executes a provided function once per each key/value pair in the StateMap, in arbitrary order.\n\t */\n\tforEach(\n\t\tcallbackfn: (\n\t\t\tvalue: DeepReadonly<JsonDeserialized<V>>,\n\t\t\tkey: K,\n\t\t\tmap: StateMap<K, V>,\n\t\t) => void,\n\t\tthisArg?: unknown,\n\t): void;\n\n\t/**\n\t * Returns the element with the specified key from the StateMap, if it exists.\n\t *\n\t * @returns Returns the element associated with the specified key. If no element is associated with the specified key, undefined is returned.\n\t */\n\tget(key: K): DeepReadonly<JsonDeserialized<V>> | undefined;\n\n\t/**\n\t * Checks if an element with the specified key exists in the StateMap.\n\t * @returns boolean indicating whether an element with the specified key exists or not.\n\t */\n\thas(key: K): boolean;\n\n\t/**\n\t * Adds a new element with a specified key and value to the StateMap. If an element with the same key already exists, the element will be updated.\n\t * The value will be transmitted to all other connected clients.\n\t *\n\t * @remarks Manager assumes ownership of the value and its references.\n\t * Make a deep clone before setting, if needed. No comparison is done to detect changes; all\n\t * sets are transmitted.\n\t */\n\tset(key: K, value: JsonSerializable<V>): this;\n\n\t/**\n\t * The number of elements in the StateMap.\n\t */\n\treadonly size: number;\n\n\t/**\n\t * Returns an iterable of entries in the map.\n\t */\n\t// [Symbol.iterator](): IterableIterator<[K, DeepReadonly<JsonDeserialized<V>>]>;\n\n\t/**\n\t * Returns an iterable of key, value pairs for every entry in the map.\n\t */\n\t// entries(): IterableIterator<[K, DeepReadonly<JsonDeserialized<V>>]>;\n\n\t/**\n\t * Returns an iterable of keys in the map.\n\t */\n\tkeys(): IterableIterator<K>;\n\n\t/**\n\t * Returns an iterable of values in the map.\n\t */\n\t// values(): IterableIterator<DeepReadonly<JsonDeserialized<V>>>;\n}\n\nclass ValueMapImpl<T, K extends string | number> implements StateMap<K, T> {\n\tprivate countDefined: number;\n\tpublic constructor(\n\t\tprivate readonly value: InternalTypes.MapValueState<T, K>,\n\t\tprivate readonly emitter: IEmitter<\n\t\t\tPick<LatestMapEvents<T, K, ValueAccessor<T>>, \"localItemUpdated\" | \"localItemRemoved\">\n\t\t>,\n\t\tprivate readonly localUpdate: (\n\t\t\tupdates: InternalTypes.MapValueState<\n\t\t\t\tT,\n\t\t\t\t// This should be `K`, but will only work if properties are optional.\n\t\t\t\tstring | number\n\t\t\t>,\n\t\t) => void,\n\t) {\n\t\t// All initial items are expected to be defined.\n\t\t// TODO assert all defined and/or update type.\n\t\tthis.countDefined = Object.keys(value.items).length;\n\t}\n\n\t/**\n\t * Note: caller must ensure key exists in this.value.items.\n\t */\n\tprivate updateItem(key: K, value: InternalTypes.ValueOptionalState<T>[\"value\"]): void {\n\t\tthis.value.rev += 1;\n\t\t// Caller is required to ensure key exists.\n\t\tconst item = this.value.items[key];\n\t\titem.rev += 1;\n\t\titem.timestamp = Date.now();\n\t\tif (value === undefined) {\n\t\t\tdelete item.value;\n\t\t} else {\n\t\t\titem.value = value;\n\t\t}\n\t\tconst update = { rev: this.value.rev, items: { [key]: item } };\n\t\tthis.localUpdate(update);\n\t}\n\n\tpublic clear(): void {\n\t\tthrow new Error(\"Method not implemented.\");\n\t}\n\tpublic delete(key: K): boolean {\n\t\tconst { items } = this.value;\n\t\tconst hasKey = items[key]?.value !== undefined;\n\t\tif (hasKey) {\n\t\t\tthis.countDefined -= 1;\n\t\t\tthis.updateItem(key, undefined);\n\t\t\tthis.emitter.emit(\"localItemRemoved\", { key });\n\t\t}\n\t\treturn hasKey;\n\t}\n\tpublic forEach(\n\t\tcallbackfn: (\n\t\t\tvalue: DeepReadonly<JsonDeserialized<T>>,\n\t\t\tkey: K,\n\t\t\tmap: StateMap<K, T>,\n\t\t) => void,\n\t\tthisArg?: unknown,\n\t): void {\n\t\tfor (const [key, item] of objectEntries(this.value.items)) {\n\t\t\tif (item.value !== undefined) {\n\t\t\t\tcallbackfn(asDeeplyReadonlyDeserializedJson(item.value), key, this);\n\t\t\t}\n\t\t}\n\t}\n\tpublic get(key: K): DeepReadonly<JsonDeserialized<T>> | undefined {\n\t\treturn asDeeplyReadonlyDeserializedJson(this.value.items[key]?.value);\n\t}\n\tpublic has(key: K): boolean {\n\t\treturn this.value.items[key]?.value !== undefined;\n\t}\n\tpublic set(key: K, inValue: JsonSerializable<T>): this {\n\t\tconst value = toOpaqueJson<T>(inValue);\n\t\tif (!(key in this.value.items)) {\n\t\t\tthis.countDefined += 1;\n\t\t\tthis.value.items[key] = { rev: 0, timestamp: 0, value };\n\t\t}\n\t\tthis.updateItem(key, value);\n\t\tthis.emitter.emit(\"localItemUpdated\", { key, value: asDeeplyReadonly(inValue) });\n\t\treturn this;\n\t}\n\tpublic get size(): number {\n\t\treturn this.countDefined;\n\t}\n\tpublic keys(): IterableIterator<K> {\n\t\tconst keys: K[] = [];\n\t\tfor (const [key, item] of objectEntries(this.value.items)) {\n\t\t\tif (item.value !== undefined) {\n\t\t\t\tkeys.push(key);\n\t\t\t}\n\t\t}\n\t\treturn keys[Symbol.iterator]();\n\t}\n}\n\n/**\n * State that provides a `Map` of latest known values from this client to\n * others and read access to their values.\n * Entries in the map may vary over time and by client, but all values are expected to\n * be of the same type, which may be a union type.\n *\n * @remarks Create using {@link StateFactory.latestMap} registered to {@link StatesWorkspace}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMap<\n\tT,\n\tKeys extends string | number = string | number,\n\tTRemoteAccessor extends ValueAccessor<T> = ProxiedValueAccessor<T>,\n> {\n\t/**\n\t * Containing {@link Presence}\n\t */\n\treadonly presence: Presence;\n\n\t/**\n\t * Events for LatestMap.\n\t */\n\treadonly events: Listenable<LatestMapEvents<T, Keys, TRemoteAccessor>>;\n\n\t/**\n\t * Controls for management of sending updates.\n\t */\n\treadonly controls: BroadcastControls;\n\n\t/**\n\t * Current value map for this client.\n\t */\n\treadonly local: StateMap<Keys, T>;\n\t/**\n\t * Iterable access to remote clients' map of values.\n\t */\n\tgetRemotes(): IterableIterator<LatestMapClientData<T, Keys, TRemoteAccessor>>;\n\t/**\n\t * Array of {@link Attendee}s that have provided states.\n\t */\n\tgetStateAttendees(): Attendee[];\n\t/**\n\t * Access to a specific client's map of values.\n\t */\n\tgetRemote(attendee: Attendee): ReadonlyMap<Keys, LatestData<T, TRemoteAccessor>>;\n}\n\n/**\n * State that provides a `Map` of latest known values from this client to\n * others and read access to their values.\n * Entries in the map may vary over time and by client, but all values are expected to\n * be of the same type, which may be a union type.\n *\n * @remarks Create using {@link StateFactory.latestMap} registered to {@link StatesWorkspace}.\n *\n * @sealed\n * @beta\n */\nexport type LatestMapRaw<T, Keys extends string | number = string | number> = LatestMap<\n\tT,\n\tKeys,\n\tRawValueAccessor<T>\n>;\n\nclass LatestMapValueManagerImpl<\n\tT,\n\tRegistrationKey extends string,\n\tKeys extends string | number = string | number,\n> implements\n\t\tLatestMapRaw<T, Keys>,\n\t\tLatestMap<T, Keys>,\n\t\tRequired<ValueManager<T, InternalTypes.MapValueState<T, Keys>>>\n{\n\tpublic readonly events = createEmitter<LatestMapEvents<T, Keys, ValueAccessor<T>>>();\n\tpublic readonly controls: OptionalBroadcastControl;\n\n\tpublic constructor(\n\t\tprivate readonly key: RegistrationKey,\n\t\tprivate readonly datastore: StateDatastore<\n\t\t\tRegistrationKey,\n\t\t\tInternalTypes.MapValueState<T, Keys>,\n\t\t\tValidatableMapValueState<T, Keys>\n\t\t>,\n\t\tpublic readonly value: InternalTypes.MapValueState<T, Keys>,\n\t\tcontrolSettings: BroadcastControlSettings | undefined,\n\t\tprivate readonly validator: StateSchemaValidator<T> | undefined,\n\t) {\n\t\tthis.controls = new OptionalBroadcastControl(controlSettings);\n\n\t\tthis.local = new ValueMapImpl<T, Keys>(\n\t\t\tvalue,\n\t\t\tthis.events,\n\t\t\t(updates: InternalTypes.MapValueState<T, Keys>) => {\n\t\t\t\tdatastore.localUpdate(key, updates, {\n\t\t\t\t\tallowableUpdateLatencyMs: this.controls.allowableUpdateLatencyMs,\n\t\t\t\t});\n\t\t\t},\n\t\t);\n\t}\n\n\tpublic get presence(): Presence {\n\t\treturn this.datastore.presence;\n\t}\n\n\tpublic readonly local: StateMap<Keys, T>;\n\n\tpublic *getRemotes(): IterableIterator<LatestMapClientData<T, Keys, ValueAccessor<T>>> {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tfor (const attendeeId of objectKeys(allKnownStates.states)) {\n\t\t\tif (attendeeId !== allKnownStates.self) {\n\t\t\t\tconst attendee = this.datastore.presence.attendees.getAttendee(attendeeId);\n\t\t\t\tconst items = this.getRemote(attendee);\n\t\t\t\tyield { attendee, items };\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic getStateAttendees(): Attendee[] {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\treturn objectKeys(allKnownStates.states)\n\t\t\t.filter((attendeeId) => attendeeId !== allKnownStates.self)\n\t\t\t.map((attendeeId) => this.datastore.presence.attendees.getAttendee(attendeeId));\n\t}\n\n\tpublic getRemote(attendee: Attendee): ReadonlyMap<Keys, LatestData<T, ValueAccessor<T>>> {\n\t\tconst validator = this.validator;\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tconst attendeeId = attendee.attendeeId;\n\t\tconst clientStateMap = allKnownStates.states[attendeeId];\n\t\tif (clientStateMap === undefined) {\n\t\t\tthrow new Error(\"No entry for attendee\");\n\t\t}\n\t\tconst items = new Map<Keys, LatestData<T, ValueAccessor<T>>>();\n\t\tfor (const [key, item] of objectEntries(clientStateMap.items)) {\n\t\t\tif (isValueRequiredState(item)) {\n\t\t\t\titems.set(key, {\n\t\t\t\t\tvalue: createValidatedGetter(item, validator),\n\t\t\t\t\tmetadata: { revision: item.rev, timestamp: item.timestamp },\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t\treturn items;\n\t}\n\n\tpublic update<SpecificAttendeeId extends AttendeeId>(\n\t\tattendee: SpecificAttendee<SpecificAttendeeId>,\n\t\t_received: number,\n\t\tvalue: InternalTypes.MapValueState<T, string | number>,\n\t): PostUpdateAction[] {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tconst attendeeId: SpecificAttendeeId = attendee.attendeeId;\n\t\tconst currentState = (allKnownStates.states[attendeeId] ??=\n\t\t\t// New attendee - prepare new attendee state directory\n\t\t\t{\n\t\t\t\trev: value.rev,\n\t\t\t\t// eslint-disable-next-line @typescript-eslint/consistent-type-assertions -- items entries can't be optional per https://github.com/microsoft/TypeScript/issues/42810; so forced cast\n\t\t\t\titems: {} as ValidatableMapValueState<T, Keys>[\"items\"],\n\t\t\t});\n\t\t// Accumulate individual update keys\n\t\tconst updatedItemKeys: Keys[] = [];\n\t\tfor (const [key, item] of objectEntries(value.items)) {\n\t\t\t// TODO: Key validation needs to be added here.\n\t\t\tconst validKey = key as Keys;\n\t\t\tif (!(key in currentState.items) || currentState.items[validKey].rev < item.rev) {\n\t\t\t\tupdatedItemKeys.push(validKey);\n\t\t\t}\n\t\t}\n\n\t\tif (updatedItemKeys.length === 0) {\n\t\t\treturn [];\n\t\t}\n\n\t\t// Store updates\n\t\tif (value.rev > currentState.rev) {\n\t\t\tcurrentState.rev = value.rev;\n\t\t}\n\t\tconst allUpdates = {\n\t\t\tattendee,\n\t\t\titems: new Map<Keys, LatestData<T, ValueAccessor<T>>>(),\n\t\t};\n\t\tconst postUpdateActions: PostUpdateAction[] = [];\n\t\tfor (const key of updatedItemKeys) {\n\t\t\tconst item = value.items[key];\n\t\t\tconst hadPriorValue = currentState.items[key]?.value;\n\t\t\tcurrentState.items[key] = item;\n\t\t\tconst metadata = {\n\t\t\t\trevision: item.rev,\n\t\t\t\ttimestamp: item.timestamp,\n\t\t\t};\n\t\t\tif (isValueRequiredState(item)) {\n\t\t\t\tconst updatedItem = {\n\t\t\t\t\tattendee,\n\t\t\t\t\tkey,\n\t\t\t\t\tvalue: createValidatedGetter(item, this.validator),\n\t\t\t\t\tmetadata,\n\t\t\t\t} satisfies LatestMapItemUpdatedClientData<T, Keys, ValueAccessor<T>>;\n\t\t\t\tpostUpdateActions.push(() => this.events.emit(\"remoteItemUpdated\", updatedItem));\n\t\t\t\tallUpdates.items.set(key, {\n\t\t\t\t\tvalue: updatedItem.value,\n\t\t\t\t\tmetadata,\n\t\t\t\t});\n\t\t\t} else if (hadPriorValue !== undefined) {\n\t\t\t\tpostUpdateActions.push(() =>\n\t\t\t\t\tthis.events.emit(\"remoteItemRemoved\", {\n\t\t\t\t\t\tattendee,\n\t\t\t\t\t\tkey,\n\t\t\t\t\t\tmetadata,\n\t\t\t\t\t}),\n\t\t\t\t);\n\t\t\t}\n\t\t}\n\t\tthis.datastore.update(this.key, attendeeId, currentState);\n\t\tpostUpdateActions.push(() => this.events.emit(\"remoteUpdated\", allUpdates));\n\t\treturn postUpdateActions;\n\t}\n}\n\n/**\n * Arguments that are passed to the {@link StateFactory.latestMap} function.\n *\n * @input\n * @beta\n */\nexport interface LatestMapArgumentsRaw<T, Keys extends string | number = string | number> {\n\t/**\n\t * The initial value of the local state.\n\t */\n\tlocal?: {\n\t\t[K in Keys]: JsonSerializable<T>;\n\t};\n\n\t/**\n\t * See {@link BroadcastControlSettings}.\n\t */\n\tsettings?: BroadcastControlSettings | undefined;\n}\n\n/**\n * Arguments that are passed to the {@link StateFactory.latestMap} function.\n *\n * @input\n * @beta\n */\nexport interface LatestMapArguments<T, Keys extends string | number = string | number>\n\textends LatestMapArgumentsRaw<T, Keys> {\n\t/**\n\t * An optional function that will be called at runtime to validate the presence data. A runtime validator is strongly\n\t * recommended. See {@link StateSchemaValidator}.\n\t */\n\tvalidator: StateSchemaValidator<T>;\n}\n\n// #region factory function overloads\n// Overloads should be ordered from most specific to least specific when combined.\n\n/**\n * Factory for creating a {@link LatestMap} or {@link LatestMapRaw} State object.\n *\n * @beta\n * @sealed\n */\nexport interface LatestMapFactory {\n\t/**\n\t * Factory for creating a {@link LatestMap} State object.\n\t *\n\t * @remarks\n\t * This overload is used when called with {@link LatestMapArguments}.\n\t * That is, if a validator function is provided.\n\t */\n\t<T, Keys extends string | number = string | number, RegistrationKey extends string = string>(\n\t\targs: LatestMapArguments<T, Keys>,\n\t): InternalTypes.ManagerFactory<\n\t\tRegistrationKey,\n\t\tInternalTypes.MapValueState<T, Keys>,\n\t\tLatestMap<T, Keys>\n\t>;\n\n\t/**\n\t * Factory for creating a {@link LatestMapRaw} State object.\n\t *\n\t * @remarks\n\t * This overload is used when called with {@link LatestMapArgumentsRaw}.\n\t * That is, if a validator function is _not_ provided.\n\t */\n\t<T, Keys extends string | number = string | number, RegistrationKey extends string = string>(\n\t\targs?: LatestMapArgumentsRaw<T, Keys>,\n\t): InternalTypes.ManagerFactory<\n\t\tRegistrationKey,\n\t\tInternalTypes.MapValueState<T, Keys>,\n\t\tLatestMapRaw<T, Keys>\n\t>;\n}\n\n// #endregion\n\n/**\n * Factory for creating a {@link LatestMap} or {@link LatestMapRaw} State object.\n */\nexport const latestMap: LatestMapFactory = <\n\tT,\n\tKeys extends string | number = string | number,\n\tRegistrationKey extends string = string,\n>(\n\targs?: Partial<LatestMapArguments<T, Keys>>,\n): InternalTypes.ManagerFactory<\n\tRegistrationKey,\n\tInternalTypes.MapValueState<T, Keys>,\n\tLatestMapRaw<T, Keys> & LatestMap<T, Keys>\n> => {\n\tconst settings = args?.settings;\n\tconst initialValues = args?.local;\n\tconst validator = args?.validator;\n\n\tconst timestamp = Date.now();\n\tconst value: InternalTypes.MapValueState<\n\t\tT,\n\t\t// This should be `Keys`, but will only work if properties are optional.\n\t\tstring | number\n\t> = { rev: 0, items: {} };\n\t// LatestMapRaw takes ownership of values within initialValues.\n\tif (initialValues !== undefined) {\n\t\tfor (const key of objectKeys(initialValues)) {\n\t\t\tvalue.items[key] = {\n\t\t\t\trev: 0,\n\t\t\t\ttimestamp,\n\t\t\t\tvalue: toOpaqueJson(initialValues[key]),\n\t\t\t};\n\t\t}\n\t}\n\tconst factory = (\n\t\tkey: RegistrationKey,\n\t\tdatastoreHandle: InternalTypes.StateDatastoreHandle<\n\t\t\tRegistrationKey,\n\t\t\tInternalTypes.MapValueState<T, Keys>\n\t\t>,\n\t): {\n\t\tinitialData: { value: typeof value; allowableUpdateLatencyMs: number | undefined };\n\t\tmanager: InternalTypes.StateValue<LatestMapRaw<T, Keys> & LatestMap<T, Keys>>;\n\t} => ({\n\t\tinitialData: { value, allowableUpdateLatencyMs: settings?.allowableUpdateLatencyMs },\n\t\tmanager: brandIVM<\n\t\t\tLatestMapValueManagerImpl<T, RegistrationKey, Keys>,\n\t\t\tT,\n\t\t\tInternalTypes.MapValueState<T, Keys>\n\t\t>(\n\t\t\tnew LatestMapValueManagerImpl(\n\t\t\t\tkey,\n\t\t\t\tdatastoreFromHandle(datastoreHandle),\n\t\t\t\tvalue,\n\t\t\t\tsettings,\n\t\t\t\tvalidator,\n\t\t\t),\n\t\t),\n\t});\n\treturn Object.assign(factory, { instanceBase: LatestMapValueManagerImpl });\n};\n"]}
1
+ {"version":3,"file":"latestMapValueManager.js","sourceRoot":"","sources":["../src/latestMapValueManager.ts"],"names":[],"mappings":"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","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n */\n\nimport { createEmitter } from \"@fluid-internal/client-utils\";\nimport type { Listenable } from \"@fluidframework/core-interfaces\";\nimport type { IEmitter } from \"@fluidframework/core-interfaces/internal\";\nimport type {\n\tDeepReadonly,\n\tJsonDeserialized,\n\tJsonSerializable,\n} from \"@fluidframework/core-interfaces/internal/exposedUtilityTypes\";\n\nimport type { BroadcastControls, BroadcastControlSettings } from \"./broadcastControls.js\";\nimport { OptionalBroadcastControl } from \"./broadcastControls.js\";\nimport type { InternalTypes } from \"./exposedInternalTypes.js\";\nimport type {\n\tPostUpdateAction,\n\tValidatableOptionalState,\n\tValueManager,\n} from \"./internalTypes.js\";\nimport {\n\tasDeeplyReadonly,\n\tasDeeplyReadonlyDeserializedJson,\n\tisValueRequiredState,\n\tobjectEntries,\n\tobjectKeys,\n\ttoOpaqueJson,\n} from \"./internalUtils.js\";\nimport { createValidatedGetter } from \"./latestValueTypes.js\";\nimport type {\n\tLatestClientData,\n\tLatestData,\n\tLatestMetadata,\n\tProxiedValueAccessor,\n\tRawValueAccessor,\n\tStateSchemaValidator,\n\tValueAccessor,\n} from \"./latestValueTypes.js\";\nimport type { AttendeeId, Attendee, Presence, SpecificAttendee } from \"./presence.js\";\nimport { datastoreFromHandle, type StateDatastore } from \"./stateDatastore.js\";\nimport { brandIVM } from \"./valueManager.js\";\n\n/**\n * A validator function that can optionally be provided to do runtime validation\n * of the custom key listed in a {@link LatestMap}.\n *\n * @param unvalidatedKey - The unknown key that should be validated.\n *\n * @returns True if the key is valid.\n *\n * @beta\n */\nexport type KeySchemaValidator<Keys extends string> = (\n\tunvalidatedKey: string,\n) => unvalidatedKey is Keys;\n\n/**\n * Collection of validatable optional values in a \"map\" structure.\n *\n * @remarks\n * Validatable equivalent of {@link InternalTypes.MapValueState}.\n */\ninterface ValidatableMapValueState<T> {\n\trev: number;\n\titems: {\n\t\t// Caution: any particular item may or may not exist\n\t\t// Typescript does not support absent keys without forcing type to also be undefined.\n\t\t// See https://github.com/microsoft/TypeScript/issues/42810.\n\t\t[name in string]: ValidatableOptionalState<T>;\n\t};\n}\n\n/**\n * Collection of latest known values for a specific {@link Attendee}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapClientData<\n\tT,\n\tKeys extends string,\n\tTValueAccessor extends ValueAccessor<T>,\n\tSpecificAttendeeId extends AttendeeId = AttendeeId,\n> {\n\t/**\n\t * Associated {@link Attendee}.\n\t */\n\tattendee: Attendee<SpecificAttendeeId>;\n\n\t/**\n\t * Map of items for the state.\n\t *\n\t * @privateRemarks This could be regular map currently as no Map is\n\t * stored internally and a new instance is created for every request.\n\t */\n\titems: ReadonlyMap<Keys, LatestData<T, TValueAccessor>>;\n}\n\n/**\n * State of a single item value, its key, and its metadata.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapItemUpdatedClientData<\n\tT,\n\tK extends string,\n\tTValueAccessor extends ValueAccessor<T>,\n> extends LatestClientData<T, TValueAccessor> {\n\t/**\n\t * Key of the updated item.\n\t */\n\tkey: K;\n}\n\n/**\n * Identifier and metadata for a removed item.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapItemRemovedClientData<K extends string> {\n\t/**\n\t * Associated {@link Attendee}.\n\t */\n\tattendee: Attendee;\n\t/**\n\t * Key of the removed item.\n\t */\n\tkey: K;\n\t/**\n\t * Metadata associated with the removal of the item.\n\t */\n\tmetadata: LatestMetadata;\n}\n\n/**\n * Events from {@link LatestMapRaw}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMapEvents<\n\tT,\n\tK extends string,\n\tTRemoteValueAccessor extends ValueAccessor<T> = ProxiedValueAccessor<T>,\n> {\n\t/**\n\t * Raised when any item's value for remote client is updated.\n\t * @param updates - Map of one or more values updated.\n\t *\n\t * @remarks The event does not include item removals.\n\t *\n\t * @eventProperty\n\t */\n\tremoteUpdated: (updates: LatestMapClientData<T, K, TRemoteValueAccessor>) => void;\n\n\t/**\n\t * Raised when specific item's value of remote client is updated.\n\t * @param updatedItem - Updated item value.\n\t *\n\t * @eventProperty\n\t */\n\tremoteItemUpdated: (\n\t\tupdatedItem: LatestMapItemUpdatedClientData<T, K, TRemoteValueAccessor>,\n\t) => void;\n\n\t/**\n\t * Raised when specific item of remote client is removed.\n\t * @param removedItem - Removed item.\n\t *\n\t * @eventProperty\n\t */\n\tremoteItemRemoved: (removedItem: LatestMapItemRemovedClientData<K>) => void;\n\n\t/**\n\t * Raised when specific local item's value is updated.\n\t * @param updatedItem - Updated item value.\n\t *\n\t * @eventProperty\n\t */\n\tlocalItemUpdated: (updatedItem: {\n\t\tvalue: DeepReadonly<JsonSerializable<T>>;\n\t\tkey: K;\n\t}) => void;\n\n\t/**\n\t * Raised when specific local item is removed.\n\t * @param removedItem - Removed item.\n\t *\n\t * @eventProperty\n\t */\n\tlocalItemRemoved: (removedItem: {\n\t\tkey: K;\n\t}) => void;\n}\n\n/**\n * Events from {@link LatestMapRaw}.\n *\n * @sealed\n * @beta\n */\nexport type LatestMapRawEvents<T, K extends string> = LatestMapEvents<\n\tT,\n\tK,\n\tRawValueAccessor<T>\n>;\n\n/**\n * Map of local client's values. Modifications are transmitted to all other connected clients.\n *\n * @sealed\n * @beta\n */\nexport interface StateMap<K extends string, V> {\n\t/**\n\t * ${@link StateMap.delete}s all elements in the StateMap.\n\t * @remarks This is not yet implemented.\n\t */\n\tclear(): void;\n\n\t/**\n\t * Removes the element with the specified key from the StateMap, if it exists.\n\t *\n\t * @returns true if an element in the StateMap existed and has been removed, or false if\n\t * the element does not exist.\n\t * @remarks No entry is fully removed. Instead an undefined placeholder is locally and\n\t * transmitted to all other clients. For better performance limit the number of deleted\n\t * entries and reuse keys when possible.\n\t * @privateRemarks In the future we may add a mechanism to remove the placeholder, at least\n\t * from transmissions after sufficient time has passed.\n\t */\n\tdelete(key: K): boolean;\n\n\t/**\n\t * Executes a provided function once per each key/value pair in the StateMap, in arbitrary order.\n\t */\n\tforEach(\n\t\tcallbackfn: (\n\t\t\tvalue: DeepReadonly<JsonDeserialized<V>>,\n\t\t\tkey: K,\n\t\t\tmap: StateMap<K, V>,\n\t\t) => void,\n\t\tthisArg?: unknown,\n\t): void;\n\n\t/**\n\t * Returns the element with the specified key from the StateMap, if it exists.\n\t *\n\t * @returns Returns the element associated with the specified key. If no element is associated with the specified key, undefined is returned.\n\t */\n\tget(key: K): DeepReadonly<JsonDeserialized<V>> | undefined;\n\n\t/**\n\t * Checks if an element with the specified key exists in the StateMap.\n\t * @returns boolean indicating whether an element with the specified key exists or not.\n\t */\n\thas(key: K): boolean;\n\n\t/**\n\t * Adds a new element with a specified key and value to the StateMap. If an element with the same key already exists, the element will be updated.\n\t * The value will be transmitted to all other connected clients.\n\t *\n\t * @remarks Manager assumes ownership of the value and its references.\n\t * Make a deep clone before setting, if needed. No comparison is done to detect changes; all\n\t * sets are transmitted.\n\t */\n\tset(key: K, value: JsonSerializable<V>): this;\n\n\t/**\n\t * The number of elements in the StateMap.\n\t */\n\treadonly size: number;\n\n\t/**\n\t * Returns an iterable of entries in the map.\n\t */\n\t// [Symbol.iterator](): IterableIterator<[K, DeepReadonly<JsonDeserialized<V>>]>;\n\n\t/**\n\t * Returns an iterable of key, value pairs for every entry in the map.\n\t */\n\t// entries(): IterableIterator<[K, DeepReadonly<JsonDeserialized<V>>]>;\n\n\t/**\n\t * Returns an iterable of keys in the map.\n\t */\n\tkeys(): IterableIterator<K>;\n\n\t/**\n\t * Returns an iterable of values in the map.\n\t */\n\t// values(): IterableIterator<DeepReadonly<JsonDeserialized<V>>>;\n}\n\nclass ValueMapImpl<T, K extends string> implements StateMap<K, T> {\n\tprivate countDefined: number;\n\tpublic constructor(\n\t\tprivate readonly value: InternalTypes.MapValueState<T, K>,\n\t\tprivate readonly emitter: IEmitter<\n\t\t\tPick<LatestMapEvents<T, K, ValueAccessor<T>>, \"localItemUpdated\" | \"localItemRemoved\">\n\t\t>,\n\t\tprivate readonly localUpdate: (\n\t\t\tupdates: InternalTypes.MapValueState<\n\t\t\t\tT,\n\t\t\t\t// This should be `K`, but will only work if properties are optional.\n\t\t\t\tstring\n\t\t\t>,\n\t\t) => void,\n\t) {\n\t\t// All initial items are expected to be defined.\n\t\t// TODO assert all defined and/or update type.\n\t\tthis.countDefined = Object.keys(value.items).length;\n\t}\n\n\t/**\n\t * Note: caller must ensure key exists in this.value.items.\n\t */\n\tprivate updateItem(key: K, value: InternalTypes.ValueOptionalState<T>[\"value\"]): void {\n\t\tthis.value.rev += 1;\n\t\t// Caller is required to ensure key exists.\n\t\tconst item = this.value.items[key];\n\t\titem.rev += 1;\n\t\titem.timestamp = Date.now();\n\t\tif (value === undefined) {\n\t\t\tdelete item.value;\n\t\t} else {\n\t\t\titem.value = value;\n\t\t}\n\t\tconst update = { rev: this.value.rev, items: { [key]: item } };\n\t\tthis.localUpdate(update);\n\t}\n\n\tpublic clear(): void {\n\t\tthrow new Error(\"Method not implemented.\");\n\t}\n\tpublic delete(key: K): boolean {\n\t\tconst { items } = this.value;\n\t\tconst hasKey = items[key]?.value !== undefined;\n\t\tif (hasKey) {\n\t\t\tthis.countDefined -= 1;\n\t\t\tthis.updateItem(key, undefined);\n\t\t\tthis.emitter.emit(\"localItemRemoved\", { key });\n\t\t}\n\t\treturn hasKey;\n\t}\n\tpublic forEach(\n\t\tcallbackfn: (\n\t\t\tvalue: DeepReadonly<JsonDeserialized<T>>,\n\t\t\tkey: K,\n\t\t\tmap: StateMap<K, T>,\n\t\t) => void,\n\t\tthisArg?: unknown,\n\t): void {\n\t\tfor (const [key, item] of objectEntries(this.value.items)) {\n\t\t\tif (item.value !== undefined) {\n\t\t\t\t// TODO: AB#55932: try fixing typing of objectEntries to avoid this cast\n\t\t\t\tcallbackfn(asDeeplyReadonlyDeserializedJson(item.value), key as unknown as K, this);\n\t\t\t}\n\t\t}\n\t}\n\tpublic get(key: K): DeepReadonly<JsonDeserialized<T>> | undefined {\n\t\treturn asDeeplyReadonlyDeserializedJson(this.value.items[key]?.value);\n\t}\n\tpublic has(key: K): boolean {\n\t\treturn this.value.items[key]?.value !== undefined;\n\t}\n\tpublic set(key: K, inValue: JsonSerializable<T>): this {\n\t\tconst value = toOpaqueJson<T>(inValue);\n\t\tif (!(key in this.value.items)) {\n\t\t\tthis.countDefined += 1;\n\t\t\tthis.value.items[key] = { rev: 0, timestamp: 0, value };\n\t\t}\n\t\tthis.updateItem(key, value);\n\t\tthis.emitter.emit(\"localItemUpdated\", { key, value: asDeeplyReadonly(inValue) });\n\t\treturn this;\n\t}\n\tpublic get size(): number {\n\t\treturn this.countDefined;\n\t}\n\tpublic keys(): IterableIterator<K> {\n\t\tconst keys: K[] = [];\n\t\tfor (const [key, item] of objectEntries(this.value.items)) {\n\t\t\tif (item.value !== undefined) {\n\t\t\t\t// TODO: AB#55932: try fixing typing of objectEntries to avoid this cast\n\t\t\t\tkeys.push(key as unknown as K);\n\t\t\t}\n\t\t}\n\t\treturn keys[Symbol.iterator]();\n\t}\n}\n\n/**\n * State that provides a `Map` of latest known values from this client to\n * others and read access to their values.\n * Entries in the map may vary over time and by client, but all values are expected to\n * be of the same type, which may be a union type.\n *\n * @remarks Create using {@link StateFactory.latestMap} registered to {@link StatesWorkspace}.\n *\n * @sealed\n * @beta\n */\nexport interface LatestMap<\n\tT,\n\tKeys extends string = string,\n\tTRemoteAccessor extends ValueAccessor<T> = ProxiedValueAccessor<T>,\n> {\n\t/**\n\t * Containing {@link Presence}\n\t */\n\treadonly presence: Presence;\n\n\t/**\n\t * Events for LatestMap.\n\t */\n\treadonly events: Listenable<LatestMapEvents<T, Keys, TRemoteAccessor>>;\n\n\t/**\n\t * Controls for management of sending updates.\n\t */\n\treadonly controls: BroadcastControls;\n\n\t/**\n\t * Current value map for this client.\n\t */\n\treadonly local: StateMap<Keys, T>;\n\t/**\n\t * Iterable access to remote clients' map of values.\n\t */\n\tgetRemotes(): IterableIterator<LatestMapClientData<T, Keys, TRemoteAccessor>>;\n\t/**\n\t * Array of {@link Attendee}s that have provided states.\n\t */\n\tgetStateAttendees(): Attendee[];\n\t/**\n\t * Access to a specific client's map of values.\n\t */\n\tgetRemote(attendee: Attendee): ReadonlyMap<Keys, LatestData<T, TRemoteAccessor>>;\n}\n\n/**\n * State that provides a `Map` of latest known values from this client to\n * others and read access to their values.\n * Entries in the map may vary over time and by client, but all values are expected to\n * be of the same type, which may be a union type.\n *\n * @remarks Create using {@link StateFactory.latestMap} registered to {@link StatesWorkspace}.\n *\n * @sealed\n * @beta\n */\nexport type LatestMapRaw<T, Keys extends string = string> = LatestMap<\n\tT,\n\tKeys,\n\tRawValueAccessor<T>\n>;\n\n/**\n * Simply returns true for all given string keys.\n */\nfunction anyKeyIsValid<Keys extends string>(unvalidatedKey: string): unvalidatedKey is Keys {\n\treturn true;\n}\n\nclass LatestMapValueManagerImpl<\n\tT,\n\tRegistrationKey extends string,\n\tKeys extends string = string,\n> implements\n\t\tLatestMapRaw<T, Keys>,\n\t\tLatestMap<T, Keys>,\n\t\tRequired<ValueManager<T, InternalTypes.MapValueState<T, Keys>>>\n{\n\tpublic readonly events = createEmitter<LatestMapEvents<T, Keys, ValueAccessor<T>>>();\n\tpublic readonly controls: OptionalBroadcastControl;\n\n\tpublic constructor(\n\t\tprivate readonly key: RegistrationKey,\n\t\tprivate readonly datastore: StateDatastore<\n\t\t\tRegistrationKey,\n\t\t\tInternalTypes.MapValueState<T, Keys>,\n\t\t\tValidatableMapValueState<T>\n\t\t>,\n\t\tpublic readonly value: InternalTypes.MapValueState<T, Keys>,\n\t\tcontrolSettings: BroadcastControlSettings | undefined,\n\t\tprivate readonly validator: StateSchemaValidator<T> | undefined,\n\t\tprivate readonly isValidKey: KeySchemaValidator<Keys>,\n\t) {\n\t\tthis.controls = new OptionalBroadcastControl(controlSettings);\n\n\t\tthis.local = new ValueMapImpl<T, Keys>(\n\t\t\tvalue,\n\t\t\tthis.events,\n\t\t\t(updates: InternalTypes.MapValueState<T, Keys>) => {\n\t\t\t\tdatastore.localUpdate(key, updates, {\n\t\t\t\t\tallowableUpdateLatencyMs: this.controls.allowableUpdateLatencyMs,\n\t\t\t\t});\n\t\t\t},\n\t\t);\n\t}\n\n\tpublic get presence(): Presence {\n\t\treturn this.datastore.presence;\n\t}\n\n\tpublic readonly local: StateMap<Keys, T>;\n\n\tpublic *getRemotes(): IterableIterator<LatestMapClientData<T, Keys, ValueAccessor<T>>> {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tfor (const attendeeId of objectKeys(allKnownStates.states)) {\n\t\t\tif (attendeeId !== allKnownStates.self) {\n\t\t\t\tconst attendee = this.datastore.presence.attendees.getAttendee(attendeeId);\n\t\t\t\tconst items = this.getRemote(attendee);\n\t\t\t\tyield { attendee, items };\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic getStateAttendees(): Attendee[] {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\treturn objectKeys(allKnownStates.states)\n\t\t\t.filter((attendeeId) => attendeeId !== allKnownStates.self)\n\t\t\t.map((attendeeId) => this.datastore.presence.attendees.getAttendee(attendeeId));\n\t}\n\n\tpublic getRemote(attendee: Attendee): ReadonlyMap<Keys, LatestData<T, ValueAccessor<T>>> {\n\t\tconst validator = this.validator;\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tconst attendeeId = attendee.attendeeId;\n\t\tconst clientStateMap = allKnownStates.states[attendeeId];\n\t\tif (clientStateMap === undefined) {\n\t\t\tthrow new Error(\"No entry for attendee\");\n\t\t}\n\t\tconst items = new Map<Keys, LatestData<T, ValueAccessor<T>>>();\n\t\tfor (const [key, item] of objectEntries(clientStateMap.items)) {\n\t\t\tif (this.isValidKey(key) && isValueRequiredState(item)) {\n\t\t\t\titems.set(key, {\n\t\t\t\t\tvalue: createValidatedGetter(item, validator),\n\t\t\t\t\tmetadata: { revision: item.rev, timestamp: item.timestamp },\n\t\t\t\t});\n\t\t\t}\n\t\t}\n\t\treturn items;\n\t}\n\n\tpublic update<SpecificAttendeeId extends AttendeeId>(\n\t\tattendee: SpecificAttendee<SpecificAttendeeId>,\n\t\t_received: number,\n\t\tvalue: InternalTypes.MapValueState<T, string>,\n\t): PostUpdateAction[] {\n\t\tconst allKnownStates = this.datastore.knownValues(this.key);\n\t\tconst attendeeId: SpecificAttendeeId = attendee.attendeeId;\n\t\tconst currentState = (allKnownStates.states[attendeeId] ??=\n\t\t\t// New attendee - prepare new attendee state directory\n\t\t\t{\n\t\t\t\trev: value.rev,\n\t\t\t\titems: {},\n\t\t\t});\n\t\t// Accumulate individual update keys\n\t\tconst updatedKeyItemPairs: [string, InternalTypes.ValueOptionalState<T>][] = [];\n\t\tfor (const [key, item] of objectEntries(value.items)) {\n\t\t\tconst currentItem = currentState.items[key];\n\t\t\tif (currentItem === undefined || currentItem.rev < item.rev) {\n\t\t\t\tupdatedKeyItemPairs.push([key, item]);\n\t\t\t}\n\t\t}\n\n\t\tif (updatedKeyItemPairs.length === 0) {\n\t\t\treturn [];\n\t\t}\n\n\t\t// Store updates\n\t\tif (value.rev > currentState.rev) {\n\t\t\tcurrentState.rev = value.rev;\n\t\t}\n\t\tconst allUpdates = {\n\t\t\tattendee,\n\t\t\titems: new Map<Keys, LatestData<T, ValueAccessor<T>>>(),\n\t\t};\n\t\tconst postUpdateActions: PostUpdateAction[] = [];\n\t\tfor (const [key, item] of updatedKeyItemPairs) {\n\t\t\tconst hadPriorValue = currentState.items[key]?.value;\n\t\t\tcurrentState.items[key] = item;\n\n\t\t\t// Prepare update events, but only for valid keys.\n\t\t\tif (!this.isValidKey(key)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tconst metadata = {\n\t\t\t\trevision: item.rev,\n\t\t\t\ttimestamp: item.timestamp,\n\t\t\t};\n\t\t\tif (isValueRequiredState(item)) {\n\t\t\t\tconst updatedItem = {\n\t\t\t\t\tattendee,\n\t\t\t\t\tkey,\n\t\t\t\t\tvalue: createValidatedGetter(item, this.validator),\n\t\t\t\t\tmetadata,\n\t\t\t\t} satisfies LatestMapItemUpdatedClientData<T, Keys, ValueAccessor<T>>;\n\t\t\t\tpostUpdateActions.push(() => this.events.emit(\"remoteItemUpdated\", updatedItem));\n\t\t\t\tallUpdates.items.set(key, {\n\t\t\t\t\tvalue: updatedItem.value,\n\t\t\t\t\tmetadata,\n\t\t\t\t});\n\t\t\t} else if (hadPriorValue !== undefined) {\n\t\t\t\tpostUpdateActions.push(() =>\n\t\t\t\t\tthis.events.emit(\"remoteItemRemoved\", {\n\t\t\t\t\t\tattendee,\n\t\t\t\t\t\tkey,\n\t\t\t\t\t\tmetadata,\n\t\t\t\t\t}),\n\t\t\t\t);\n\t\t\t}\n\t\t}\n\t\tthis.datastore.update(this.key, attendeeId, currentState);\n\t\t// Only emit remoteUpdated if there are any individual updates, which\n\t\t// accounts for the case where all updates were for invalid keys.\n\t\tif (postUpdateActions.length > 0) {\n\t\t\tpostUpdateActions.push(() => this.events.emit(\"remoteUpdated\", allUpdates));\n\t\t}\n\t\treturn postUpdateActions;\n\t}\n}\n\n/**\n * Arguments that are passed to the {@link StateFactory.latestMap} function.\n *\n * @input\n * @beta\n */\nexport interface LatestMapArgumentsRaw<T, Keys extends string = string> {\n\t/**\n\t * The initial value of the local state.\n\t */\n\tlocal?: {\n\t\t[K in Keys]: JsonSerializable<T>;\n\t};\n\n\t/**\n\t * See {@link BroadcastControlSettings}.\n\t */\n\tsettings?: BroadcastControlSettings | undefined;\n}\n\n/**\n * Arguments that are passed to the {@link StateFactory.latestMap} function.\n *\n * @input\n * @beta\n */\nexport interface LatestMapArguments<T, Keys extends string = string>\n\textends LatestMapArgumentsRaw<T, Keys> {\n\t/**\n\t * An optional function that will be called at runtime to validate data value\n\t * under a key. A runtime validator is strongly recommended.\n\t * @see {@link StateSchemaValidator}.\n\t */\n\tvalidator: StateSchemaValidator<T>;\n\t/**\n\t * An optional function that will be called at runtime to validate the presence\n\t * data key. A runtime validator is strongly recommended when key type is not\n\t * simply `string`.\n\t * @see {@link KeySchemaValidator}.\n\t */\n\tkeyValidator?: KeySchemaValidator<Keys>;\n}\n\n// #region factory function overloads\n// Overloads should be ordered from most specific to least specific when combined.\n\n/**\n * Factory for creating a {@link LatestMap} or {@link LatestMapRaw} State object.\n *\n * @beta\n * @sealed\n */\nexport interface LatestMapFactory {\n\t/**\n\t * Factory for creating a {@link LatestMap} State object.\n\t *\n\t * @remarks\n\t * This overload is used when called with {@link LatestMapArguments}.\n\t * That is, if a validator function is provided.\n\t */\n\t<T, Keys extends string = string, RegistrationKey extends string = string>(\n\t\targs: LatestMapArguments<T, Keys>,\n\t): InternalTypes.ManagerFactory<\n\t\tRegistrationKey,\n\t\tInternalTypes.MapValueState<T, Keys>,\n\t\tLatestMap<T, Keys>\n\t>;\n\n\t/**\n\t * Factory for creating a {@link LatestMapRaw} State object.\n\t *\n\t * @remarks\n\t * This overload is used when called with {@link LatestMapArgumentsRaw}.\n\t * That is, if a validator function is _not_ provided.\n\t */\n\t<T, Keys extends string = string, RegistrationKey extends string = string>(\n\t\targs?: LatestMapArgumentsRaw<T, Keys>,\n\t): InternalTypes.ManagerFactory<\n\t\tRegistrationKey,\n\t\tInternalTypes.MapValueState<T, Keys>,\n\t\tLatestMapRaw<T, Keys>\n\t>;\n}\n\n// #endregion\n\n/**\n * Factory for creating a {@link LatestMap} or {@link LatestMapRaw} State object.\n */\nexport const latestMap: LatestMapFactory = <\n\tT,\n\tKeys extends string = string,\n\tRegistrationKey extends string = string,\n>(\n\targs?: Partial<LatestMapArguments<T, Keys>>,\n): InternalTypes.ManagerFactory<\n\tRegistrationKey,\n\tInternalTypes.MapValueState<T, Keys>,\n\tLatestMapRaw<T, Keys> & LatestMap<T, Keys>\n> => {\n\tconst settings = args?.settings;\n\tconst initialValues = args?.local;\n\tconst validator = args?.validator;\n\tconst isKeyValid = args?.keyValidator ?? anyKeyIsValid;\n\n\tconst timestamp = Date.now();\n\tconst value: InternalTypes.MapValueState<\n\t\tT,\n\t\t// This should be `Keys`, but will only work if properties are optional.\n\t\tstring\n\t> = { rev: 0, items: {} };\n\t// LatestMapRaw takes ownership of values within initialValues.\n\tif (initialValues !== undefined) {\n\t\tfor (const [key, item] of objectEntries(initialValues)) {\n\t\t\t// TODO: AB#55932: try fixing typing of objectEntries to avoid this cast\n\t\t\tconst assumedValidKey = key as unknown as Keys;\n\t\t\tvalue.items[assumedValidKey] = {\n\t\t\t\trev: 0,\n\t\t\t\ttimestamp,\n\t\t\t\tvalue: toOpaqueJson(item),\n\t\t\t};\n\t\t}\n\t}\n\tconst factory = (\n\t\tkey: RegistrationKey,\n\t\tdatastoreHandle: InternalTypes.StateDatastoreHandle<\n\t\t\tRegistrationKey,\n\t\t\tInternalTypes.MapValueState<T, Keys>\n\t\t>,\n\t): {\n\t\tinitialData: { value: typeof value; allowableUpdateLatencyMs: number | undefined };\n\t\tmanager: InternalTypes.StateValue<LatestMapRaw<T, Keys> & LatestMap<T, Keys>>;\n\t} => ({\n\t\tinitialData: { value, allowableUpdateLatencyMs: settings?.allowableUpdateLatencyMs },\n\t\tmanager: brandIVM<\n\t\t\tLatestMapValueManagerImpl<T, RegistrationKey, Keys>,\n\t\t\tT,\n\t\t\tInternalTypes.MapValueState<T, Keys>\n\t\t>(\n\t\t\tnew LatestMapValueManagerImpl(\n\t\t\t\tkey,\n\t\t\t\tdatastoreFromHandle(datastoreHandle),\n\t\t\t\tvalue,\n\t\t\t\tsettings,\n\t\t\t\tvalidator,\n\t\t\t\tisKeyValid,\n\t\t\t),\n\t\t),\n\t});\n\treturn Object.assign(factory, { instanceBase: LatestMapValueManagerImpl });\n};\n"]}
@@ -27,6 +27,7 @@ export {
27
27
  BroadcastControls,
28
28
  ClientConnectionId,
29
29
  InternalTypes,
30
+ KeySchemaValidator,
30
31
  Latest,
31
32
  LatestArguments,
32
33
  LatestArgumentsRaw,
@@ -5,5 +5,5 @@
5
5
  * THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY
6
6
  */
7
7
  export declare const pkgName = "@fluidframework/presence";
8
- export declare const pkgVersion = "2.74.0-370705";
8
+ export declare const pkgVersion = "2.80.0";
9
9
  //# sourceMappingURL=packageVersion.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"packageVersion.d.ts","sourceRoot":"","sources":["../src/packageVersion.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,eAAO,MAAM,OAAO,6BAA6B,CAAC;AAClD,eAAO,MAAM,UAAU,kBAAkB,CAAC"}
1
+ {"version":3,"file":"packageVersion.d.ts","sourceRoot":"","sources":["../src/packageVersion.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,eAAO,MAAM,OAAO,6BAA6B,CAAC;AAClD,eAAO,MAAM,UAAU,WAAW,CAAC"}
@@ -8,5 +8,5 @@
8
8
  Object.defineProperty(exports, "__esModule", { value: true });
9
9
  exports.pkgVersion = exports.pkgName = void 0;
10
10
  exports.pkgName = "@fluidframework/presence";
11
- exports.pkgVersion = "2.74.0-370705";
11
+ exports.pkgVersion = "2.80.0";
12
12
  //# sourceMappingURL=packageVersion.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"packageVersion.js","sourceRoot":"","sources":["../src/packageVersion.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;AAEU,QAAA,OAAO,GAAG,0BAA0B,CAAC;AACrC,QAAA,UAAU,GAAG,eAAe,CAAC","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n *\n * THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY\n */\n\nexport const pkgName = \"@fluidframework/presence\";\nexport const pkgVersion = \"2.74.0-370705\";\n"]}
1
+ {"version":3,"file":"packageVersion.js","sourceRoot":"","sources":["../src/packageVersion.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;AAEU,QAAA,OAAO,GAAG,0BAA0B,CAAC;AACrC,QAAA,UAAU,GAAG,QAAQ,CAAC","sourcesContent":["/*!\n * Copyright (c) Microsoft Corporation and contributors. All rights reserved.\n * Licensed under the MIT License.\n *\n * THIS IS AN AUTOGENERATED FILE. DO NOT EDIT THIS FILE DIRECTLY\n */\n\nexport const pkgName = \"@fluidframework/presence\";\nexport const pkgVersion = \"2.80.0\";\n"]}
@@ -29,11 +29,13 @@ export declare function isValueDirectory<T>(obj: ValidatableValueDirectory<T> |
29
29
  * High-level contract for manager of singleton Presence datastore
30
30
  */
31
31
  export interface PresenceDatastoreManager {
32
- joinSession(clientId: ClientConnectionId): void;
32
+ joinSession(clientId: ClientConnectionId, alternateProvider: ClientConnectionId | undefined): void;
33
33
  onDisconnected(): void;
34
34
  getWorkspace<TSchema extends StatesWorkspaceSchema>(internalWorkspaceAddress: `s:${WorkspaceAddress}`, requestedContent: TSchema, controls?: BroadcastControlSettings): StatesWorkspace<TSchema>;
35
35
  getWorkspace<TSchema extends NotificationsWorkspaceSchema>(internalWorkspaceAddress: `n:${WorkspaceAddress}`, requestedContent: TSchema): NotificationsWorkspace<TSchema>;
36
- processSignal(message: InboundExtensionMessage<SignalMessages>, local: boolean, optional: boolean): void;
36
+ processSignal(message: InboundExtensionMessage<SignalMessages> & {
37
+ clientId: ClientConnectionId;
38
+ }, local: boolean, optional: boolean): void;
37
39
  }
38
40
  /**
39
41
  * Delays used for broadcasting join responses to clients.
@@ -71,12 +73,6 @@ export declare class PresenceDatastoreManagerImpl implements PresenceDatastoreMa
71
73
  private readonly sendMessageTimer;
72
74
  private readonly workspaces;
73
75
  private readonly targetedSignalSupport;
74
- /**
75
- * When defined, this client is not recognized in the session.
76
- * Call when no longer caring about that condition. That way listeners are
77
- * cleaned up.
78
- */
79
- private stopWaitingForSelfInAudience;
80
76
  /**
81
77
  * Tracks whether this client has complete snapshot level knowledge and
82
78
  * how that determination was reached.
@@ -110,8 +106,6 @@ export declare class PresenceDatastoreManagerImpl implements PresenceDatastoreMa
110
106
  constructor(attendeeId: AttendeeId, runtime: IEphemeralRuntime, logger: ITelemetryLoggerExt | undefined, events: IEmitter<PresenceEvents>, presence: Presence, systemWorkspaceDatastore: SystemWorkspaceDatastore, systemWorkspace: AnyWorkspaceEntry<StatesWorkspaceSchema>);
111
107
  private getAudienceInformation;
112
108
  joinSession(selfClientId: ClientConnectionId, alternateProvider?: ClientConnectionId | undefined): void;
113
- private listenForSelfInAudience;
114
- private stopWaitingAndJoin;
115
109
  onDisconnected(): void;
116
110
  getWorkspace<TSchema extends StatesWorkspaceSchema>(internalWorkspaceAddress: InternalWorkspaceAddress, requestedContent: TSchema, controls?: BroadcastControlSettings): AnyWorkspace<TSchema>;
117
111
  /**
@@ -138,7 +132,9 @@ export declare class PresenceDatastoreManagerImpl implements PresenceDatastoreMa
138
132
  */
139
133
  private stripValidationFromValueData;
140
134
  private broadcastAllKnownState;
141
- processSignal(message: InboundExtensionMessage<SignalMessages>, local: boolean, optional: boolean): void;
135
+ processSignal(message: InboundExtensionMessage<SignalMessages> & {
136
+ clientId: ClientConnectionId;
137
+ }, local: boolean, optional: boolean): void;
142
138
  /**
143
139
  * Broadcasts a join response (complete datastore update message)
144
140
  * if there is an outstanding join response request.
@@ -1 +1 @@
1
- {"version":3,"file":"presenceDatastoreManager.d.ts","sourceRoot":"","sources":["../src/presenceDatastoreManager.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"presenceDatastoreManager.d.ts","sourceRoot":"","sources":["../src/presenceDatastoreManager.ts"],"names":[],"mappings":"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"}
@@ -154,7 +154,6 @@ class PresenceDatastoreManagerImpl {
154
154
  }
155
155
  }
156
156
  return {
157
- audience,
158
157
  selfPresent,
159
158
  interactiveMembersExcludingSelf: {
160
159
  all,
@@ -171,9 +170,9 @@ class PresenceDatastoreManagerImpl {
171
170
  // Lack of anyone likely means that this client is very freshly joined
172
171
  // and has not received any Join Signals (type="join") from the service
173
172
  // yet.
174
- const { audience, selfPresent, interactiveMembersExcludingSelf } = this.getAudienceInformation(selfClientId);
175
- if (interactiveMembersExcludingSelf.all.size === 0 && alternateProvider !== undefined) {
176
- if (selfPresent) {
173
+ const { selfPresent, interactiveMembersExcludingSelf } = this.getAudienceInformation(selfClientId);
174
+ if (selfPresent) {
175
+ if (interactiveMembersExcludingSelf.all.size === 0) {
177
176
  // If there aren't any members connected except self, then this client
178
177
  // must have complete information.
179
178
  this.reasonForCompleteSnapshot = "alone";
@@ -184,12 +183,12 @@ class PresenceDatastoreManagerImpl {
184
183
  // ClientJoin soon rectifying that and covering for bad incomplete
185
184
  // responses this client sent in the meantime.
186
185
  }
187
- else {
188
- // No one is known. Not even self. Defer judgement on
189
- // complete snapshot until at least self is known to be present.
190
- this.listenForSelfInAudience(selfClientId, audience);
191
- return;
192
- }
186
+ }
187
+ else {
188
+ // When self is not represented, audience is an unreliable state,
189
+ // especially during a reconnect. An alternateProvider is expected
190
+ // to have been provided for this call to be useful (efficient).
191
+ (0, internal_1.assert)(alternateProvider !== undefined, "Self is not in audience and no alternateProvider given");
193
192
  }
194
193
  // Broadcast join message to all clients
195
194
  // Select primary update providers
@@ -228,46 +227,8 @@ class PresenceDatastoreManagerImpl {
228
227
  },
229
228
  });
230
229
  }
231
- listenForSelfInAudience(selfClientId, audience) {
232
- this.logger?.sendTelemetryEvent({
233
- eventName: "JoinDeferred",
234
- details: {
235
- attendeeId: this.attendeeId,
236
- connectionId: selfClientId,
237
- },
238
- });
239
- // Prepare to join once self audience member joins.
240
- // Alternatively, processSignal may force a join when a presence
241
- // signal is received even without audience members (assumes
242
- // audience signals were lost).
243
- const joinWhenSelfAudienceMemberAdded = (addedClientId) => {
244
- if (addedClientId !== selfClientId) {
245
- // Keep listening
246
- return;
247
- }
248
- // No need to force here by providing alternate provider as self is
249
- // now present.
250
- // Do avoid forcing so that reasonForCompleteSnapshot is set correctly
251
- // if no others have been added.
252
- this.stopWaitingAndJoin(selfClientId, /* alternateProvider */ undefined);
253
- };
254
- audience.on("addMember", joinWhenSelfAudienceMemberAdded);
255
- this.stopWaitingForSelfInAudience = () => {
256
- audience.off("addMember", joinWhenSelfAudienceMemberAdded);
257
- };
258
- }
259
- stopWaitingAndJoin(selfClientId, alternateProvider) {
260
- this.stopWaitingForSelfInAudience?.();
261
- this.stopWaitingForSelfInAudience = undefined;
262
- // Confirm not currently disconnected
263
- if (this.runtime.getJoinedStatus() !== "disconnected") {
264
- this.joinSession(selfClientId, alternateProvider);
265
- }
266
- }
267
230
  onDisconnected() {
268
231
  delete this.reasonForCompleteSnapshot;
269
- this.stopWaitingForSelfInAudience?.();
270
- this.stopWaitingForSelfInAudience = undefined;
271
232
  }
272
233
  getWorkspace(internalWorkspaceAddress, requestedContent, controls) {
273
234
  const existing = this.workspaces.get(internalWorkspaceAddress);
@@ -482,7 +443,6 @@ class PresenceDatastoreManagerImpl {
482
443
  }
483
444
  processSignal(message, local, optional) {
484
445
  const received = Date.now();
485
- (0, internal_1.assert)(message.clientId !== null, 0xa3a /* Map received signal without clientId */);
486
446
  if (!isPresenceMessage(message)) {
487
447
  (0, internal_1.assert)(optional, "Unrecognized message type in critical message");
488
448
  return;
@@ -499,19 +459,6 @@ class PresenceDatastoreManagerImpl {
499
459
  this.returnedMessages;
500
460
  return;
501
461
  }
502
- const selfClientId = this.runtime.getClientId();
503
- (0, internal_1.assert)(selfClientId !== undefined, "Received signal without clientId");
504
- // Check for undesired case of receiving a remote presence signal
505
- // without having been alerted to self audience join. (Perhaps join
506
- // signal was dropped.)
507
- // In practice it is commonly observed that local signals can be
508
- // returned ahead of audience join notification. So, it is reasonable
509
- // to expect that audience join notification may be delayed until after
510
- // other presence signals are received. One is enough to get things
511
- // rolling.
512
- if (this.stopWaitingForSelfInAudience !== undefined) {
513
- this.stopWaitingAndJoin(selfClientId, /* alternateProvider */ message.clientId);
514
- }
515
462
  const timeModifier = received -
516
463
  (this.averageLatency + message.content.avgLatency + message.content.sendTimestamp);
517
464
  const postUpdateActions = [];
@@ -529,6 +476,8 @@ class PresenceDatastoreManagerImpl {
529
476
  // Update join response requests that are now satisfied.
530
477
  const joinResponseFor = message.content.joinResponseFor;
531
478
  if (joinResponseFor) {
479
+ const selfClientId = this.runtime.getClientId();
480
+ (0, internal_1.assert)(selfClientId !== undefined, "Received signal without clientId");
532
481
  let justGainedCompleteSnapshot = false;
533
482
  if (joinResponseFor.includes(selfClientId)) {
534
483
  if (this.reasonForCompleteSnapshot) {