Releases: microsoft/FluidFramework
Fluid Framework v2.51.0 (minor)
Contents
🚨 Breaking Changes
@fluid-experimental/attributable-map package removed (#25019)
The @fluid-experimental/attributable-map package has been removed without replacement.
Change details
Commit: c8bbd6d
Affected packages:
- @fluid-experimental/attributable-map
🌳 SharedTree DDS Changes
Fix adaptEnum's handling of numeric enums (#24957)
Enum entries whose values are numeric get additional properties on TypeScript's generated Enum object. These values were getting treated like enum entries at runtime by adaptEnum (@beta). This has been fixed and the runtime behavior now matches the types in this case.
If any documents were created with this API which were impacted by this bug and keeping them openable is required, they will need a workaround. Impacted schema using the union from adaptEnum can need to be updated to explicitly include the previously erroneously generated schema.
Before:
enum Mode {
a = 1,
}
const ModeNodes = adaptEnum(schemaFactory, Mode);
const union = ModeNodes.schema;After:
enum Mode {
a = 1,
}
const ModeNodes = adaptEnum(schemaFactory, Mode);
// Bugged version of adaptEnum used to include this: it should not be used but must be included in the schema for legacy document compatibility.
class Workaround extends schemaFactory.object("a", {}) {}
const union = [...ModeNodes.schema, Workaround] as const;To help detect when schema contain unexpected content, and to ensure workarounds like this are implemented properly, applications should include tests which check the schema for compatibility. See tree-cli-app's schema tests for an example of how to do this.
The schema returned by adaptEnum have also been updated to toString to include the value of the particular enum entry: this has no effect on the nodes, just the schema.
Change details
Commit: 7535d31
Affected packages:
- @fluidframework/tree
- fluid-framework
"rootChanged" event is no longer skipped if first change is setting the root to undefined (#24994)
A bug has been fixed where rootChanged would not be fired if the change is the first change since the TreeView became in-schema, and the change was setting the document root to undefined.
Change details
Commit: e6f2587
Affected packages:
- @fluidframework/tree
- fluid-framework
Make POJO mode TreeArrayNodes report the array constructor as their constructor (#24988)
Make POJO mode TreeArrayNode's inherited constructor property report Array instead of the TreeNodeSchema class. This is necessary to make TreeArrayNodes appear equal to arrays according to NodeJS's assert.strict.deepEqual in NodeJS 22.
Change details
Commit: 7b4d0ab
Affected packages:
- @fluidframework/tree
- fluid-framework
Legacy API Changes
New "getSnapshotTree" API on "IChannelStorageService" (#24970)
A new API, getSnapshotTree has been added to IChannelStorageService. It should return the snapshot tree for a channel. This will help channels examine their snapshot when it consists of dynamic trees and blobs, i.e., when the number of tree and blobs and / or their keys are not known in advance. This is optional for backwards compatibility, and will become required in the future.
Change details
Commit: d1241a4
Affected packages:
- @fluidframework/datastore-definitions
New "PureDataObject" implementation "TreeDataObject" added (#25025)
A new implementation of PureDataObject has been added: TreeDataObject. Where DataObject stores its contents in a SharedDirectory, TreeDataObject stores its contents in a SharedTree.
Change details
Commit: f4fbd2f
Affected packages:
- @fluidframework/aqueduct
Add API for tree-based root data object (#25030)
Adds createTreeContainerRuntimeFactory which can be used to create runtime factories which construct containers with an entry point containing a single tree-based root data object.
Change details
Commit: 30a0d7e
Affected packages:
- @fluidframework/fluid-static
🛠️ Start Building Today!
Please continue to engage with us on GitHub Discussion and Issue pages as you adopt Fluid Framework!
Fluid Framework v2.50.0 (minor)
Contents
🚨 Breaking Changes
IFluidHandleInternal.bind (deprecated) has been removed (#24974)
IFluidHandleInternal.bind was deprecated in 2.40 and has now been removed. See release notes entry for more details.
Change details
Commit: 07e1837
Affected packages:
- @fluidframework/core-interfaces
- @fluidframework/datastore
- @fluidframework/runtime-utils
- @fluidframework/test-runtime-utils
🌳 SharedTree DDS Changes
Record node kind was added (alpha) (#24908)
Adds a new kind of node to SharedTree that models a TypeScript record. As is the case with map nodes, record nodes only support string keys.
class MyRecord extends schemaFactory.record("my-record", [
schemaFactory.number,
schemaFactory.string,
]) {}
const myRecord = new MyRecord({
foo: 42,
bar: "Hello world!",
});
const foo = myRecord.foo; // 42
delete myRecord.foo;
myRecord.baz = 37;
const keys = Object.keys(myRecord); // ["bar", "baz"]
const values = Object.values(myRecord); // ["Hello world!", 37]
const entries = Object.entries(myRecord); // [["bar", "Hello world!"], ["baz", 37]]NodeKind enum update
This change includes the addition of a new flag to the NodeKind enum. This API notes in its documentation that users should not treat its flags as an exhaustive set.
This change may break code that treats it that way. We recommend updating your code to be more tolerant of unknown node kinds going forward.
Also see alternative options for schema-agnostic tree traversal if needed:
Additional features
In addition to the operations afforded by TypeScript records, SharedTree record nodes can be iterated (equivalent to Object.entries).
class MyRecord extends schemaFactory.record("my-record", [schemaFactory.number, schemaFactory.string]) {}
const myRecord = new MyRecord({
foo: 42,
bar: "Hello world!"
});
for (const [key, value] of myRecord) {
...
}
const a = { ...myRecord }; // { foo: 42, bar: "Hello world!" }
const b = [...myRecord]; // [["foo", 42], ["bar, "Hello world!"]]Recursive records
Recursive record schema can be defined using recordRecursive on SchemaFactoryAlpha.
class MyRecord extends schemaFactory.recordRecursive("my-record", [
schemaFactory.string,
() => MyRecord,
]) {}
const myRecord = new MyRecord({
foo: "Hello world!",
bar: new MyRecord({
x: "foo",
y: new MyRecord({}),
}),
});TableSchema update (alpha)
The TableSchema APIs have been updated to use record nodes in the schema they generate. Specifically, the Row representation now uses a record to store its column-cell pairs, rather than a map.
The node types derived from these APIs model their data in a row-major format. That is, each row in the table contains the set of cells that belong to that row, where each cell is indexed by its corresponding column.
Previously, this was modeled using a MapNode. This format proved cumbersome to interop with popular table rendering libraries like tanstack, which expect a record-like format.
The persisted format of documents containing trees derived from these APIs is the same, so this change is forward and backward compatible.
JsonDomainSchema update (alpha)
JsonObject has been updated to a record rather than a map.
The persisted format of documents containing trees derived from these APIs is the same, so this change is forward and backward compatible.
Change details
Commit: b25667b
Affected packages:
- @fluidframework/tree
- fluid-framework
Other Changes
StateFactory.latest now accepts a validator parameter (#24432)
The StateFactory.latest API now accepts a validator argument. The validator is a function that will be called at runtime to verify that the data is valid. This is especially useful when changing the schema of presence data.
See the presence documentation for more details.
Change details
Commit: ffe5d0b
Affected packages:
- @fluidframework/presence
🛠️ Start Building Today!
Please continue to engage with us on GitHub Discussion and Issue pages as you adopt Fluid Framework!
Fluid Framework v2.43.0 (minor)
Contents
🚨 Breaking Changes
The reason parameter on the disconnect event now accepts undefined to allow for clean, non-error disconnections (#24840)
To enable better handling of intentional disconnects (for example Container.dispose()), the reason parameter of the disconnect event on IDocumentDeltaConnectionEvents now accepts undefined as a valid value.
Old signature:
listener: (reason: IAnyDriverError) => voidNew signature:
listener: (reason: IAnyDriverError | undefined) => voidDevelopers with listeners for the disconnect event should update their implementations to handle cases where the reason parameter is undefined.
This indicates a clean disconnect, which should not be treated as an error.
The breaking change is scheduled to be released in version 2.60.
Change details
Commit: 82a1c5a
Affected packages:
- @fluidframework/container-loader
- @fluidframework/driver-base
- @fluidframework/driver-definitions
✨ New Features
Persisted metadata for Shared Tree schemas (Alpha) (#24812)
The persisted metadata feature for Shared Tree allows an application author to write document-persisted metadata along with the schema. This feature is supported for both node and field schemas.
Using the persisted metadata feature
As of now, persisted metadata support is available via the SchemaFactoryAlpha API:
// Construct a schema factory with alpha APIs
const schemaFactory = new SchemaFactoryAlpha("com.example");Persisted metadata can take the shape of any JSON-serializable object, e.g.:
const persistedMetadata = { a: 2 };Feature flag
To enable persisted metadata, use configuredSharedTree to specify the format version. The tree that is returned can be substituted in place of the default SharedTree object exported by the Fluid Framework. For example:
const tree = configuredSharedTree({
formatVersion: SharedTreeFormatVersion.v5,
}).create(runtime);
export const MyContainerSchema = {
initialObjects: {
appData: tree,
},
} satisfies ContainerSchema;Examples
Field schemas with persisted metadata
// Construct a schema factory with alpha APIs
const schemaFactory = new SchemaFactoryAlpha("com.example");
// Define metadata. This can take the shape of any JSON-serializable object.
const persistedMetadata = { a: 2 };
// Foo is an object type with metadata
class Foo extends schemaFactory.objectAlpha(
"Foo",
{
// Metadata for a required number field
bar: schemaFactory.required(schemaFactory.number, { persistedMetadata }),
// Metadata for an optional string field
baz: schemaFactory.optional(schemaFactory.string, { persistedMetadata }),
// Metadata for the object type Foo
},
{ persistedMetadata },
) {}Recursive field schemas
// Construct a schema factory with alpha APIs
const schemaFactory = new SchemaFactoryAlpha("com.example");
// Define metadata. This can take the shape of any JSON-serializable object.
const persistedMetadata = { a: 2 };
// Recursive object schema with persisted metadata
class RecursiveObject extends schemaFactory.objectRecursive(
"RecursiveObject",
{
x: [() => RecursiveObject, schemaFactory.number],
},
{ persistedMetadata },
) {}
// Recursive field schema with metadata
const recursiveField = schemaFactory.optionalRecursive(
[() => RecursiveObject, schemaFactory.number],
{ persistedMetadata },
);Recursive object schemas
// Construct a schema factory with alpha APIs
const schemaFactory = new SchemaFactoryAlpha("com.example");
// Define metadata. This can take the shape of any JSON-serializable object.
const persistedMetadata = { a: 2 };
// Recursive array schema
class Foos extends schemaFactory.arrayRecursive("FooList", [() => Foo], {
persistedMetadata,
}) {}
// Recursive object schema
class Foo extends schemaFactory.objectRecursive(
"Foo",
{ fooList: Foos },
{ persistedMetadata },
) {}
// Recursive map schema
class FooMap extends schemaFactory.mapRecursive("FooMap", [() => Foo], {
persistedMetadata,
}) {}Change details
Commit: 3f81ab5
Affected packages:
- fluid-framework
- @fluidframework/tree
🌳 SharedTree DDS Changes
Tree's enum schema utility are now beta (#24749)
The functions singletonSchema, adaptEnum and enumFromStrings are now @beta instead of @alpha.
Change details
Commit: a23bc9e
Affected packages:
- fluid-framework
- @fluidframework/tree
Add TreeAlpha.child and TreeAlpha.children APIs for generic tree traversal (#24723)
TreeAlpha.child
Access a child node or value of a TreeNode by its property key.
class MyObject extends schemaFactory.object("MyObject", {
foo: schemaFactory.string;
bar: schemaFactory.optional(schemaFactory.string);
}) {}
const myObject = new MyObject({
foo: "Hello world!"
});
const foo = TreeAlpha.child(myObject, "foo"); // "Hello world!"
const bar = TreeAlpha.child(myObject, "bar"); // undefined
const baz = TreeAlpha.child(myObject, "baz"); // undefinedclass MyArray extends schemaFactory.array("MyArray", schemaFactory.string) {}
const myArray = new MyArray("Hello", "World");
const child0 = TreeAlpha.child(myArray, 0); // "Hello"
const child1 = TreeAlpha.child(myArray, 1); // "World
const child2 = TreeAlpha.child(myArray, 2); // undefinedTreeAlpha.children
Get all child nodes / values of a TreeNode, keyed by their property keys.
class MyObject extends schemaFactory.object("MyObject", {
foo: schemaFactory.string;
bar: schemaFactory.optional(schemaFactory.string);
baz: schemaFactory.optional(schemaFactory.number);
}) {}
const myObject = new MyObject({
foo: "Hello world!",
baz: 42,
});
const children = TreeAlpha.children(myObject); // [["foo", "Hello world!"], ["baz", 42]]class MyArray extends schemaFactory.array("MyArray", schemaFactory.string) {}
const myArray = new MyArray("Hello", "World");
const children ...Fluid Framework v2.42.0 (minor)
Contents
🌳 SharedTree DDS Changes
Fix Tree.key and Tree.parent for Unhydrated nodes after edits (#24708)
In some cases, editing Unhydrated nodes could result in incorrect results being returned from Tree.key and Tree.parent. This has been fixed.
Change details
Commit: 8aa5c23
Affected packages:
- @fluidframework/tree
- fluid-framework
Name collisions from structurally named schema now error (#24707)
It is legal to have multiple TreeNodeSchema with the same name so long as they are not used together in the same tree. Using different schema with the same name when building otherwise identical structurally named in the same SchemaFactory is not valid, however. Previously doing this would not error, and instead return the first structurally named schema with that name. Now this case throws an informative error:
const factory = new SchemaFactory(undefined);
class Child1 extends factory.object("Child", {}) {}
class Child2 extends factory.object("Child", {}) {}
const a = factory.map(Child1);
// Throws a UsageError with the message:
// "Structurally named schema collision: two schema named "Array<["Child"]>" were defined with different input schema."
const b = factory.array(Child2);Change details
Commit: a343f04
Affected packages:
- @fluidframework/tree
- fluid-framework
Defaulted identifier fields on unhydrated nodes are now enumerable (#24739)
Previously, there was a special case for defaulted identifier fields on unhydrated nodes where they were not enumerable. This special case has been removed: they are now enumerable independent of hydration status and defaulting.
Change details
Commit: 3a5d0ac
Affected packages:
- @fluidframework/tree
- fluid-framework
🛠️ Start Building Today!
Please continue to engage with us on GitHub Discussion and Issue pages as you adopt Fluid Framework!
Fluid Framework v2.41.0 (minor)
Contents
- ✨ New Features
- 🌳 SharedTree DDS Changes
- The comparePersistedSchema function (alpha) has had its canInitialize parameter removed (#24606)
- TreeAlpha.create now accepts unhydrated nodes (#24629)
- New TableSchema (alpha) APIs (#24579)
- SharedTrees's FluidClientVersion enum (alpha) has been redesigned (#24638)
- ForestTypeExpensiveDebug now validates content against schema (#24658)
- TreeNodes now implicitly generate identifiers on access instead of throwing (#24665)
✨ New Features
Presence APIs promoted to beta (#24710)
Presence APIs are now beta and can be imported via @fluidframework/presence/beta.
Note: Notifications are only supported via /alpha imports. To access notifications-only workspace support, cast Presence to PresenceWithNotifications.
Change details
Commit: 6fce410
Affected packages:
- @fluidframework/presence
New experimental objectIdNumber API (#21115)
A new objectIdNumber has been added, which is useful when you need an identifier which corresponds to an object identity. For example: when specifying a React "key" that corresponds to a TreeNode.
Change details
Commit: df2f139
Affected packages:
- @fluid-experimental/tree-react-api
New TreeAlpha.key2 API (#24623)
The TreeAlpha.key2 method is meant to eventually replace the public Tree.key method. This new method returns undefined in the case where there is a root node.
Change details
Commit: 0ddd6b0
Affected packages:
- @fluidframework/tree
New TreeAlpha identifier APIs for converting, retrieving, and generating identifiers (#24218)
TreeAlpha.identifier
You can retrieve the long identifier with TreeAlpha.identifier(node), where node is a TreeNode. The long identifier is a stable, compressible UUID generated by the tree. In cases where the node does not yet have an identifier assigned, this will return undefined. These cases include:
- The node does not contain an identifier field.
- The node is a non-hydrated node with a user provided identifier. Note that if it is a non-hydrated node without an identifier provided, it will throw an error.
TreeAlpha.identifier.shorten
You can shorten a long identifier with TreeAlpha.identifier.shorten(branch, identifier), where branch is a TreeBranch, and identifier is a string. If the method returns a valid short identifier, this identifier can be passed into TreeAlpha.identifier.lengthen to get the original valid long identifier back. In the cases where it's not possible to shorten the identifier, it will return undefined. These cases include:
- A compressible long identifier, but it is unrecognized by the tree that the node belongs to. This can occur if the identifier is not generated from the tree.
- An identifier which is not compressible by the tree. This can occur if the node's identifier was a user provided string.
TreeAlpha.identifier.lengthen
You can lengthen a short identifier with TreeAlpha.identifier.lengthen(branch, identifier), where branch is a TreeBranch, and identifier is a number. If the method returns a valid long identifier, this identifier can be passed into TreeAlpha.identifier.shorten to get the original identifier back. In the cases where it's not possible to lengthen the identifier, this method will throw an error. These cases include:
- An unrecognized short identifier. This can occur if the identifier is not generated from the tree.
TreeAlpha.identifier.getShort
You can retrieve the short identifier from a node with TreeAlpha.identifier.getShort(node) where node is a TreeNode. If it is not possible to retrieve the short identifier, it will return undefined
Example for a node with valid identifier
// This will retrieve the short identifier from the node.
const shortIdentifier = TreeAlpha.identifier.getShort(nodeWithValidIdentifier);Examples for when you get undefined
In cases where the node provided does not contain an identifier that is recognized or compressible by the tree that the node belongs to, this method will return undefined. This will occur in the following cases:
- The node is an non-hydrated node with a user provided identifier. Note that if it is an non-hydrated node without an identifier provided, it will throw an error.
- The node does not contain an identifier field.
- The node contains a compressible long identifier, but it is unrecognized by the tree that the node belongs to. This can occur if the identifier is not generated from the tree.
- The node contains an identifier which is not compressible by its id compressor. This can occur if the node's identifier was a user provided string.
// This will return undefined
const shortIdentifier = TreeAlpha.identifier.getShort(node);TreeAlpha.identifier.create
You can create a long identifier from a branch with TreeAlpha.identifier.create(branch) where branch is a TreeBranch.
const createdIdentifier = TreeAlpha.identifier.create(branch);Change details
Commit: e5b2882
Affected packages:
- fluid-framework
- @fluidframework/tree
"getPresence(container: IFluidContainer): Presence" now supported (#24399)
You can now use the getPresence function to directly acquire Presence. In previous releases, you were required to use ExperimentalPresenceManager in container schema and calling getPresenceViaDataObject, but that is no longer required. Both ExperimentalPresenceManager and getPresenceViaDataObject are now deprecated.
Change details
Commit: 5c6824a
Affected packages:
- @fluidframework/presence
🌳 SharedTree DDS Changes
The comparePersistedSchema function (alpha) has had its canInitialize parameter removed (#24606)
comparePersistedSchema has had its canInitialize parameter removed. This parameter was only used to add to the output SchemaCompatibilityStatus. If a full SchemaCompatibilityStatus is still desired, the canInitialize value can be added to the result:
// old
const result = comparePersistedSchema(a, b, canInitialize);
// new
const result = { ...comparePersistedSchema(a, b), canInitialize };Change details
Commit: d083a17
Affected packages:
- fluid-framework
- @fluidframework/tr...
Fluid Framework v2.40.0 (minor)
Contents
- 🚨 Breaking Changes
- 🌳 SharedTree DDS Changes
- AllowedTypes array handling has been updated (#24484)
- SchemaFactoryAlpha.object has been renamed to SchemaFactoryAlpha.objectAlpha (#24478)
- SchemaFactoryAlpha supports adding metadata to AllowedTypes (#24478)
- A SharedTree document corruption bug has been fixed (#24565)
- The extractPersistedSchema (alpha) API has had its arguments adjusted (#24562)
⚠️ Deprecations- Legacy API Changes
🚨 Breaking Changes
ITokenClaims and ScopeType re-exports have been removed (#24530)
Import from @fluidframework/driver-definitions/legacy as needed. See issue #23702.
Change details
Commit: 665a9f4
Affected packages:
- @fluidframework/azure-client
IContainer.getContainerPackageInfo has been removed (#24525)
IContainer.getContainerPackageInfo() was set to be removed in release 2.40.0. To access the package name getContainerPackageInfo() provided, use IFluidCodeDetails.package returned by IContainer.getLoadedCodeDetails().
See issue #23898 for more information.
Change details
Commit: 15a5412
Affected packages:
- @fluidframework/container-definitions
- @fluidframework/container-loader
- fluid-framework
🌳 SharedTree DDS Changes
AllowedTypes array handling has been updated (#24484)
As an optimization, how AllowedTypes arrays are processed has changed. Now much larger arrays can be provided without hitting:
"Type instantiation is excessively deep and possibly infinite.ts"
Previously, arrays of around 43 schema would start having this issue, but now arrays of hundreds work correctly.
This optimization has resulted in a small change in behavior for how input types are computed. When the AllowedTypes array has a type that is a union of two arrays, and the two arrays start with the same subsequence of types, previously this would allow the types from the common prefix of the arrays. For example [typeof A] | [typeof A, typeof B] would permit inserting content compatible with A. Now all such unions produce never for their insertable node types (just like this example would if the order of the second array were reversed). This case was not intentionally supported, and as documented in input types, non-exact types, like these unions, are not guaranteed to produce anything other than never.
If providing exact schema is impractical and the previous behavior is required, convert the union of arrays to an array of unions. The above example can be turned into [typeof A, typeof B | typeof A].
This is also fix for a case where AllowedTypes was order dependent, which violates its documented order independence.
Change details
Commit: f0a71cc
Affected packages:
- fluid-framework
- @fluidframework/tree
SchemaFactoryAlpha.object has been renamed to SchemaFactoryAlpha.objectAlpha (#24478)
This rename was done so that changes can be made to the signature of the class. This is a breaking change and uses of SchemaFactoryAlpha.object may need to be changed to SchemaFactoryAlpha.objectAlpha.
Change details
Commit: 12e5ab3
Affected packages:
- fluid-framework
- @fluidframework/tree
SchemaFactoryAlpha supports adding metadata to AllowedTypes (#24478)
This change allows metadata to be added to AllowedTypes as well as individual types in a set of AllowedTypes. Users can define custom metadata by putting their AllowedTypes in an object with metadata and types properties:
schemaFactoryAlpha.arrayAlpha({
metadata: {
custom: "these allowed types are annotated",
},
types: [SchemaFactory.string, SchemaFactory.number],
});This annotation system will also be used to implement future schema features.
Change details
Commit: 12e5ab3
Affected packages:
- fluid-framework
- @fluidframework/tree
A SharedTree document corruption bug has been fixed (#24565)
There was a bug where local changes were not correctly sent to peers. This could lead to a permanent loss of consistency and ultimately document corruption. See PR24561 for details.
Change details
Commit: 6b3e150
Affected packages:
- fluid-framework
- @fluidframework/tree
The extractPersistedSchema (alpha) API has had its arguments adjusted (#24562)
The extractPersistedSchema function has been updated to take in SimpleTreeSchema. This makes it possible to use with simple schema derived from stored schema, like those returned from ITreeAlpha.exportSimpleSchema. Like TreeAlpha.exportCompressed, extractPersistedSchema now takes in FluidClientVersion to make it possible to opt into newer formats when they become available.
Additionally, persistedToSimpleSchema has been added to fill in a gap in the API. Without persistedToSimpleSchema it would be impossible to parse the persisted format without a valid compressed tree to provide to independentInitializedView.
Change details
Commit: 2e6b0cf
Affected packages:
- fluid-framework
- @fluidframework/tree
⚠️ Deprecations
IFluidHandleInternal.bind has been deprecated (#24553)
Handle binding is an internal concept used to make sure objects attach to the Container graph when their handle is sto...
Fluid Framework v2.33.2 (patch)
What's Changed
- perf(client-container-runtime): reduce
semverbundle regression#24486 - build(client): Bump version to 2.33.2
#24496
Full Changelog: client_v2.33.1...client_v2.33.2
Fluid Framework v2.33.1 (patch)
What's Changed
- Bump patch version and type tests
#24475
Full Changelog: client_v2.33.0...client_v2.33.1
Fluid Framework v2.33.0 (minor)
Contents
- ✨ New Features
- 🌳 SharedTree DDS Changes
- Improve handling of deleted nodes (#24345)
- allowUnused utility function (#24076)
- Typing derived from unions of AllowedTypes arrays is fixed (#24441)
- Remote edits to nodes which have never been accessed locally correctly trigger "treeChanged" events (#24421)
- "Unsafe" @system types moved to System_Unsafe namespace (#24443)
⚠️ Deprecations- Other Changes
✨ New Features
Latest and LatestMap support more types (#24417)
Latest(StateFactory.latest) permitsnullso that nullable types may be used.LatestMap(StateFactory.latestMap) permitsboolean,number,string, andnull.
Change details
Commit: 619af0b
Affected packages:
- @fluidframework/presence
🌳 SharedTree DDS Changes
Improve handling of deleted nodes (#24345)
TreeNodes which are deleted were not handled correctly. This has been improved in two ways:
- Accessing fields of deleted nodes now consistently throws a usage error indicating that doing so is invalid. Previously, this would throw an assertion error, which was a bug.
- When a
TreeNodeis deleted, but that node still exists within theITree, then becomes accessible again later, a newTreeNodeis now allocated instead of trying to reuse the deleted one. Note that this can only happen when the entire view of theITreeis disposed then recreated. This happens when disposing and recreating a TreeView or when the contents of the view are disposed due to being out of schema (another client did a schema upgrade), then brought back into schema (the schema upgrade was undone).
Change details
Commit: 0ab3e51
Affected packages:
- @fluidframework/tree
- fluid-framework
allowUnused utility function (#24076)
A new allowUnused utility function has been added, which discards its type or runtime argument. When TypeScript is configured to reject code with unused locals, this function can be used to suppress that error, enabling use of ValidateRecursiveSchema to compile.
class Test extends sf.arrayRecursive("Test", () => Test) {} // Bad
allowUnused<ValidateRecursiveSchema<typeof Test>>(); // Reports compile error due to invalid schema above.Change details
Commit: 13c62b6
Affected packages:
- @fluidframework/tree
- fluid-framework
Typing derived from unions of AllowedTypes arrays is fixed (#24441)
Unions of array types provided as an AllowedTypes used to result in incorrectly computed insertable content types. This happened because InsertableTreeNodeFromAllowedTypes distributed over the union, violating the policy documented in Input for how schema-derived input types should be computed. This has been fixed. To get usable Input types, SharedTree schema's types should always capture the exact schema provided at runtime and not unions of possible different schema. Any code impacted by this change should be updated to replace any such unions with more specific types.
Change details
Commit: a27ef0a
Affected packages:
- fluid-framework
- @fluidframework/tree
Remote edits to nodes which have never been accessed locally correctly trigger "treeChanged" events (#24421)
There was a bug where "treeChanged" events would not always trigger if the node that was edited had never been accessed in the current view. This has been fixed.
Change details
Commit: 916ad05
Affected packages:
- @fluidframework/tree
- fluid-framework
"Unsafe" @System types moved to System_Unsafe namespace (#24443)
Working code conforming to the rules regarding API Support Levels should be unaffected, but this resolves an issue which required violating these rules and directly referencing @system types.
Sometimes packages exporting SharedTree schema related types for recursive schema could yield errors like:
error TS2742: The inferred type of 'YourSchema' cannot be named without a reference to '../node_modules/@fluidframework/tree/lib/internalTypes.js'. This is likely not portable. A type annotation is necessary.
Mitigating this error could require explicitly referencing these @system types from internalTypes. Any such references to the moved types should be able to be deleted, as TypeScript will now be able to find them in the new namespace without assistance.
This does not migrate all types out of internalTypes, so some occurrences of this issue may remain.
Change details
Commit: dd4abfc
Affected packages:
- fluid-framework
- @fluidframework/tree
⚠️ Deprecations
Generic types for IntervalCollections have been replaced with non-generic types (#24164)
This change deprecates the following generic types and provides non-generic alternatives where necessary:
IIntervalCollectionis replaced byISequenceIntervalCollectionIIntervalCollectionEventis replaced byISequenceIntervalCollectionEventsIntervalIndexis replaced bySequenceIntervalIndexIOverlappingIntervalsIndexis replaced byISequenceOverlappingIntervalsIndexISharedIntervalCollectionis deprecated without replacement
These types are no longer required to be generic, and replacing them with non-generic alternatives keeps our typing less complex.
Change details
Commit: 280e2bc
Affected packages:
- fluid-framework
- @fluidframework/sequence
Other Changes
Presence APIs have been renamed (#24384)
The following API changes have been made to improve clarity and consistency:
| Before 2.33.0 | 2.33.0 |
|---|---|
acquirePresence ... |
build-tools v0.56.0 (minor)
This is a minor release.