This is an automated email from the ASF dual-hosted git repository.

chaokunyang pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/fory-site.git


The following commit(s) were added to refs/heads/main by this push:
     new bf637f5a35 πŸ”„ synced local 'docs/guide/' with remote 'docs/guide/'
bf637f5a35 is described below

commit bf637f5a3525116072e505a68f1eb2f27b114bc0
Author: chaokunyang <[email protected]>
AuthorDate: Tue Apr 14 13:24:15 2026 +0000

    πŸ”„ synced local 'docs/guide/' with remote 'docs/guide/'
---
 docs/guide/cpp/_category_.json                 |   2 +-
 docs/guide/csharp/_category_.json              |   2 +-
 docs/guide/dart/_category_.json                |   2 +-
 docs/guide/dart/basic-serialization.md         |  38 +++++----
 docs/guide/dart/code-generation.md             |  45 +++++-----
 docs/guide/dart/configuration.md               |  67 ++++++++-------
 docs/guide/dart/cross-language.md              |  48 ++++++-----
 docs/guide/dart/custom-serializers.md          |  63 ++++++--------
 docs/guide/dart/field-configuration.md         |  73 ++++++++---------
 docs/guide/dart/index.md                       |  46 +++++------
 docs/guide/dart/schema-evolution.md            |  64 ++++++++-------
 docs/guide/dart/supported-types.md             |  92 ++++++++-------------
 docs/guide/dart/troubleshooting.md             |  60 +++++++-------
 docs/guide/dart/type-registration.md           |  54 ++++++------
 docs/guide/go/_category_.json                  |   2 +-
 docs/guide/java/_category_.json                |   2 +-
 docs/guide/{cpp => javascript}/_category_.json |   4 +-
 docs/guide/javascript/basic-serialization.md   |  18 ++--
 docs/guide/javascript/cross-language.md        |  85 +++++++++----------
 docs/guide/javascript/index.md                 |  79 +++++++-----------
 docs/guide/javascript/references.md            |  22 +++--
 docs/guide/javascript/schema-evolution.md      |  47 +++++------
 docs/guide/javascript/supported-types.md       |  99 ++++++++++------------
 docs/guide/javascript/troubleshooting.md       |  50 +++++-------
 docs/guide/javascript/type-registration.md     | 109 +++++++++++--------------
 docs/guide/kotlin/_category_.json              |   2 +-
 docs/guide/python/_category_.json              |   2 +-
 docs/guide/rust/_category_.json                |   2 +-
 docs/guide/scala/_category_.json               |   2 +-
 docs/guide/swift/_category_.json               |   2 +-
 docs/guide/xlang/_category_.json               |   2 +-
 31 files changed, 540 insertions(+), 645 deletions(-)

diff --git a/docs/guide/cpp/_category_.json b/docs/guide/cpp/_category_.json
index c543ab1388..9660bafa82 100644
--- a/docs/guide/cpp/_category_.json
+++ b/docs/guide/cpp/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "C++",
-  "position": 3,
+  "position": 4,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/csharp/_category_.json 
b/docs/guide/csharp/_category_.json
index 4ddedc6210..c5e03ee3c5 100644
--- a/docs/guide/csharp/_category_.json
+++ b/docs/guide/csharp/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "C#",
-  "position": 9,
+  "position": 7,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/dart/_category_.json b/docs/guide/dart/_category_.json
index 47b8891a2e..b2d06cfcd2 100644
--- a/docs/guide/dart/_category_.json
+++ b/docs/guide/dart/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Dart",
-  "position": 11,
+  "position": 9,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/dart/basic-serialization.md 
b/docs/guide/dart/basic-serialization.md
index e7fa79d95d..1f261937ed 100644
--- a/docs/guide/dart/basic-serialization.md
+++ b/docs/guide/dart/basic-serialization.md
@@ -19,9 +19,11 @@ license: |
   limitations under the License.
 ---
 
-This page covers the root serialization APIs in Apache Foryβ„’ Dart.
+This page shows how to serialize and deserialize values with Apache Foryβ„’ Dart.
 
-## Create and Reuse `Fory`
+## Create a `Fory` Instance
+
+Create one instance and reuse it β€” creating a new `Fory` for every call wastes 
resources.
 
 ```dart
 import 'package:fory/fory.dart';
@@ -29,8 +31,6 @@ import 'package:fory/fory.dart';
 final fory = Fory();
 ```
 
-Reuse the same runtime instance across calls. `Fory` owns the reusable 
`Buffer`, `WriteContext`, `ReadContext`, and `TypeResolver` services for that 
runtime.
-
 ## Serialize and Deserialize Annotated Types
 
 ```dart
@@ -65,11 +65,11 @@ void main() {
 }
 ```
 
-`deserialize<T>` uses the wire metadata first, then checks that the result is 
assignable to `T`.
+`deserialize<T>` returns the decoded value cast to `T`. If the payload 
describes a different type than `T`, it throws.
 
-## Null Root Values
+## Null Values
 
-The root xlang frame starts with a one-byte bitmap. A null root payload is 
encoded by the root header, so serializing `null` works directly:
+Serializing `null` is supported directly:
 
 ```dart
 final fory = Fory();
@@ -91,25 +91,27 @@ final bytes = fory.serialize(<Object?>[
 final value = fory.deserialize<List<Object?>>(bytes);
 ```
 
-For heterogeneous collections, deserialize to `Object?`, `List<Object?>`, 
`Map<Object?, Object?>`, or a generated struct type that matches the wire 
schema.
+For heterogeneous collections, deserialize to `Object?`, `List<Object?>`, or 
`Map<Object?, Object?>`.
+
+## Reference Tracking
 
-## Root Reference Tracking
+By default, Fory does not track object identity β€” if the same object appears 
twice in a list, it is serialized twice. Enable reference tracking when your 
data contains shared references or circular structures.
 
-Use `trackRef: true` only when the root value itself is a graph or container 
with repeated references and there is no field metadata to request reference 
tracking.
+For a top-level collection:
 
 ```dart
 final fory = Fory();
 final shared = String.fromCharCodes('shared'.codeUnits);
 final bytes = fory.serialize(<Object?>[shared, shared], trackRef: true);
 final roundTrip = fory.deserialize<List<Object?>>(bytes);
-print(identical(roundTrip[0], roundTrip[1]));
+print(identical(roundTrip[0], roundTrip[1])); // true
 ```
 
-Inside generated structs, prefer field-level reference metadata with 
`@ForyField(ref: true)`.
+For fields inside a generated struct, use `@ForyField(ref: true)` on that 
field instead.
 
-## Buffer-Based APIs
+## Reusing a Buffer
 
-Use `serializeTo` and `deserializeFrom` when you want explicit `Buffer` reuse.
+If you want to avoid allocating a new `Uint8List` on every call, use 
`serializeTo` and `deserializeFrom` with an explicit `Buffer`:
 
 ```dart
 final fory = Fory();
@@ -119,11 +121,11 @@ fory.serializeTo(Int32(42), buffer);
 final value = fory.deserializeFrom<Int32>(buffer);
 ```
 
-`serializeTo` clears the target buffer before writing. `deserializeFrom` 
consumes bytes from the buffer's current reader position.
+This is an optimization. For most applications the default 
`serialize`/`deserialize` pair is fine.
 
-## Generated Registration Before Use
+## Register Your Types Before Serializing
 
-Generated and manual user-defined types must be registered before use.
+Before you can serialize a custom class or enum, register it with `Fory`. The 
generated code makes this easy:
 
 ```dart
 PersonFory.register(
@@ -133,7 +135,7 @@ PersonFory.register(
 );
 ```
 
-See [Type Registration](type-registration.md) and [Code 
Generation](code-generation.md).
+If you skip registration, you will get a `Type ... is not registered` error at 
runtime. See [Type Registration](type-registration.md) and [Code 
Generation](code-generation.md).
 
 ## Related Topics
 
diff --git a/docs/guide/dart/code-generation.md 
b/docs/guide/dart/code-generation.md
index 5a65135a97..495a6dd898 100644
--- a/docs/guide/dart/code-generation.md
+++ b/docs/guide/dart/code-generation.md
@@ -19,11 +19,11 @@ license: |
   limitations under the License.
 ---
 
-Fory Dart uses source generation for structs and enums defined in your Dart 
libraries.
+Fory generates fast serializer code for your Dart classes at build time. You 
annotate your models, run `build_runner`, and Fory takes care of the rest.
 
-## Annotate Struct Types
+## Step 1 β€” Annotate Your Models
 
-Mark classes with `@ForyStruct()` and include the generated part file.
+Add `@ForyStruct()` to each class you want to serialize. Include the generated 
part directive at the top of the file.
 
 ```dart
 import 'package:fory/fory.dart';
@@ -48,21 +48,21 @@ class User {
 }
 ```
 
-Enums in the same library also participate in generated registration.
+Enums defined in the same file are automatically included in the generated 
registration.
 
-## Run the Generator
+## Step 2 β€” Run the Generator
 
-From `dart/packages/fory` or the package that depends on the generator:
+From the directory that contains your `pubspec.yaml`:
 
 ```bash
 dart run build_runner build --delete-conflicting-outputs
 ```
 
-The builder emits a `.fory.dart` part file next to the source library.
+This emits a `.fory.dart` file next to your source file. Re-run this command 
any time you add or rename annotated types.
 
-## Register Through the Generated Namespace
+## Step 3 β€” Register and Use
 
-Generated code exposes a library-level namespace that knows how to install 
generated metadata into `Fory`.
+The generator creates a namespace (named after your file) with a `register` 
function. Call it before serializing:
 
 ```dart
 final fory = Fory();
@@ -70,7 +70,7 @@ ModelsFory.register(fory, Address, id: 1);
 ModelsFory.register(fory, User, id: 2);
 ```
 
-Or use named registration:
+Or use a stable name instead of a numeric ID (useful for cross-language 
scenarios):
 
 ```dart
 ModelsFory.register(
@@ -81,16 +81,17 @@ ModelsFory.register(
 );
 ```
 
-Exactly one registration mode is required:
+See [Type Registration](type-registration.md) for guidance on choosing between 
IDs and names.
 
-- `id: ...`
-- `namespace: ...` plus `typeName: ...`
+## Schema Evolution: `evolving`
 
-## Choosing `evolving`
+`@ForyStruct()` defaults to `evolving: true`, which is the right choice for 
most applications.
 
-`@ForyStruct()` defaults to `evolving: true`.
+- `evolving: true` β€” Fory stores enough metadata so that if you add or remove 
fields later, old and new code can still exchange messages. Enable this 
whenever different versions of your app or service may be running at the same 
time.
+- `evolving: false` β€” No extra metadata; marginally smaller payloads. Safe 
only when both writer and reader are always updated together.
 
 ```dart
+// evolving: true is the default, you can omit it
 @ForyStruct(evolving: true)
 class Event {
   Event();
@@ -99,19 +100,11 @@ class Event {
 }
 ```
 
-Use `evolving: true` when you want compatible-mode field evolution. Use 
`evolving: false` for a fixed schema when you want schema-consistent behavior.
+When using evolving structs, also assign stable field IDs with `@ForyField(id: 
...)` before you ship your first payload β€” those IDs are how Fory matches 
fields after a schema change.
 
-## Generated Registration Design
+## When Not to Use Code Generation
 
-Generated registration keeps serializer metadata private to the defining 
library while exposing a public wrapper API. Applications should call the 
generated wrapper instead of private helper functions.
-
-## When to Use Customized Serializers Instead
-
-Use [Custom Serializers](custom-serializers.md) when:
-
-- the type is external and cannot be annotated
-- you need custom payload layout
-- you are implementing a union or extension type manually
+If you cannot annotate a type (e.g., it comes from a package you do not own), 
write a [Custom Serializer](custom-serializers.md) instead.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/configuration.md b/docs/guide/dart/configuration.md
index a213cca77d..2cd0a94c46 100644
--- a/docs/guide/dart/configuration.md
+++ b/docs/guide/dart/configuration.md
@@ -19,89 +19,100 @@ license: |
   limitations under the License.
 ---
 
-This page covers `Config` options and default runtime values for Apache Foryβ„’ 
Dart.
+This page explains the `Fory` constructor options.
 
-## Create a Runtime
+## Creating a `Fory` Instance
+
+Pass options directly to the constructor:
 
 ```dart
 import 'package:fory/fory.dart';
 
+// defaults β€” good for most single-service scenarios
+final fory = Fory();
+
+// cross-language service with schema evolution
 final fory = Fory(
   compatible: true,
   maxDepth: 512,
-  maxCollectionSize: 1 << 18,
-  maxBinarySize: 16 * 1024 * 1024,
 );
 ```
 
-The same `Fory` instance should be reused across many operations. `Fory` 
resets operation-local read and write state for each root call.
+Create one instance per application and reuse it; there is no benefit to 
creating a new `Fory` per request.
 
 ## Options
 
 ### `compatible`
 
-Enables compatible struct encoding and decoding.
+Set to `true` when your service needs to handle payloads from code that may 
have a different version of the same model β€” for example, when you deploy 
services independently and cannot guarantee that both sides update at the same 
time.
 
 ```dart
 final fory = Fory(compatible: true);
 ```
 
-In compatible mode, generated evolving structs exchange shared `TypeDef` 
metadata rather than relying on the schema-consistent struct hash checks used 
by fixed-schema mode.
+When `compatible: true`:
+
+- Adding or removing fields on one side does not break the other.
+- Peers must still use the same `namespace` + `typeName` (or numeric `id`) to 
identify types.
+
+When `compatible: false` (default):
+
+- Both sides must have exactly the same schema. This is slightly faster and is 
fine when you deploy Dart-only services or always update all sides together.
 
 ### `checkStructVersion`
 
-Controls struct schema-version validation in schema-consistent mode.
+Relevant only when `compatible: false`. When `true`, Fory validates that the 
schema version in the payload matches the one the receiver knows about, 
catching accidental schema mismatches at runtime.
 
 ```dart
 final fory = Fory(
   compatible: false,
-  checkStructVersion: true,
+  checkStructVersion: true, // default
 );
 ```
 
-This option is forced to `false` whenever `compatible` is `true`.
+This option has no effect when `compatible: true`.
 
 ### `maxDepth`
 
-Maximum nesting depth accepted during one serialization or deserialization 
operation.
+Limits how deeply nested an object graph can be. Increase this if you have 
legitimately deep trees; lower it to reject unexpectedly deep payloads fast.
 
 ```dart
-const config = Config(maxDepth: 128);
+final fory = Fory(maxDepth: 128);
 ```
 
-Use this to bound recursive payloads and fail fast on malformed or 
unexpectedly deep graphs.
-
 ### `maxCollectionSize`
 
-Maximum number of entries accepted for a single collection or map payload.
+Maximum number of elements accepted in any single list, set, or map field. 
Prevents runaway memory allocation from malformed messages.
 
 ```dart
-const config = Config(maxCollectionSize: 100000);
+final fory = Fory(maxCollectionSize: 100000);
 ```
 
 ### `maxBinarySize`
 
-Maximum number of bytes accepted for a single binary payload.
+Maximum number of bytes accepted for any single binary blob field.
 
 ```dart
-const config = Config(maxBinarySize: 8 * 1024 * 1024);
+final fory = Fory(maxBinarySize: 8 * 1024 * 1024);
 ```
 
 ## Defaults
 
-`Config()` defaults to:
-
-- `compatible: false`
-- `checkStructVersion: true`
-- `maxDepth: 256`
-- `maxCollectionSize: 1 << 20`
-- `maxBinarySize: 64 * 1024 * 1024`
+| Option               | Default   |
+| -------------------- | --------- |
+| `compatible`         | `false`   |
+| `checkStructVersion` | `true`    |
+| `maxDepth`           | 256       |
+| `maxCollectionSize`  | 1 048 576 |
+| `maxBinarySize`      | 64 MiB    |
 
 ## Cross-Language Notes
 
-- The Dart runtime always reads and writes xlang frames.
-- Match `compatible` mode across communicating services when you depend on 
schema evolution.
-- Registration choices still matter: use the same numeric IDs or the same 
`namespace + typeName` mapping across all runtimes.
+When Fory is used to communicate between services written in different 
languages:
+
+- Set `compatible: true` on **all** sides if any side needs schema evolution.
+- Use the same numeric IDs or `namespace + typeName` pairs on every side.
+- Match the `compatible` setting on both the writing and reading side β€” 
mismatching modes will fail.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/cross-language.md 
b/docs/guide/dart/cross-language.md
index 2c700865b2..fb83116929 100644
--- a/docs/guide/dart/cross-language.md
+++ b/docs/guide/dart/cross-language.md
@@ -19,31 +19,37 @@ license: |
   limitations under the License.
 ---
 
-Apache Foryβ„’ Dart supports cross-language serialization with other Fory 
runtimes.
+Apache Foryβ„’ Dart serializes to the same binary format as the Java, Go, C#, 
Python, Rust, and Swift Fory runtimes. You can write a message in Dart and read 
it in Java β€” or any other direction β€” without any conversion layer.
 
-## Cross-Language Runtime
+## Setup
 
-The Dart runtime only supports xlang payloads, so you do not enable a separate 
cross-language mode.
+Create a `Fory` instance as normal. There is no separate "cross-language mode" 
to enable in Dart:
 
 ```dart
-final fory = Fory();
+final fory = Fory(); // or Fory(compatible: true) for schema evolution
 ```
 
-Configure only the runtime behavior that still varies, such as compatible mode 
and safety limits.
+The key requirement is that both sides register the same type using the same 
identity.
+
+## Registration Identity
 
-## Use Stable Registration Identity
+The most important rule: **use the same type identity on every side**. You 
have two options:
 
-Choose one registration strategy and keep it stable across all peers.
+### Numeric ID
 
-### Numeric ID example
+Simpler for small, tightly-coordinated teams:
 
 ```dart
+// Dart
 ModelsFory.register(fory, Person, id: 100);
 ```
 
-### Name-based example
+### Namespace + Type Name
+
+Better when multiple teams define types independently:
 
 ```dart
+// Dart
 ModelsFory.register(
   fory,
   Person,
@@ -52,6 +58,8 @@ ModelsFory.register(
 );
 ```
 
+Do not mix the two strategies for the same type across runtimes.
+
 ## Dart to Java Example
 
 ### Dart
@@ -146,15 +154,14 @@ _ = f.Deserialize(bytesFromDart, &person)
 
 ## Field Matching Rules
 
-The xlang spec is the source of truth, but for application authors the 
practical rules are:
-
-1. Register the same logical type identity on every side.
-2. Keep field meaning aligned across languages.
-3. For evolving schemas, keep field IDs stable.
-4. Use compatible type mappings for numeric widths, timestamps, collections, 
and nullability.
-5. Validate real payload round trips.
+Fory matches fields by name or by stable field ID. For robust cross-language 
interop:
 
-Dart model fields often use lowerCamelCase. Go fields are exported PascalCase. 
C# commonly uses PascalCase properties. What matters is that the peer runtimes 
agree on the logical field mapping and wire schema. Stable field IDs are the 
safest option when models evolve independently.
+1. Use the same type identity on every side (same numeric ID or same 
`namespace + typeName`).
+2. Assign stable `@ForyField(id: ...)` values to all fields before shipping 
the first payload.
+3. Keep field names consistent or rely on IDs, since Dart typically uses 
`lowerCamelCase` while Go uses `PascalCase` for exported fields and C# often 
uses `PascalCase` properties.
+4. Use compatible numeric types: `Int32` in Dart for Java `int`, Go `int32`, 
and C# `int`; `double` in Dart for 64-bit floats; `Float32` for 32-bit.
+5. Use `Timestamp` and `LocalDate` for date/time fields rather than raw 
`DateTime`.
+6. Validate real round trips across all languages before shipping.
 
 ## Type Mapping Notes for Dart
 
@@ -167,14 +174,13 @@ Because Dart `int` is not itself a promise about the 
exact xlang wire width, pre
 
 See [Supported Types](supported-types.md) and [xlang type 
mapping](../../specification/xlang_type_mapping.md).
 
-## Validation Advice
+## Validation
 
-Before relying on an interop contract, test the same payload through every 
runtime you support.
+Before relying on a cross-language contract in production, test a payload 
end-to-end through every runtime you support.
 
-At minimum for Dart runtime work:
+Run the Dart side:
 
 ```bash
-cd dart
 dart run build_runner build --delete-conflicting-outputs
 dart analyze
 dart test
diff --git a/docs/guide/dart/custom-serializers.md 
b/docs/guide/dart/custom-serializers.md
index 91ddc69455..280eb1ed8f 100644
--- a/docs/guide/dart/custom-serializers.md
+++ b/docs/guide/dart/custom-serializers.md
@@ -19,19 +19,18 @@ license: |
   limitations under the License.
 ---
 
-Use customized serializers when generated struct support is not the right fit.
+A custom serializer lets you control exactly how a type is encoded and 
decoded. You only need one when:
 
-## When Customized Serializers Make Sense
+- the type comes from a package you cannot modify and cannot be annotated with 
`@ForyStruct()`
+- you need a completely custom binary layout
+- you are implementing a union/discriminated type
 
-Typical cases include:
-
-- external types you cannot annotate
-- custom payload layouts
-- customized extension types
-- unions built on the `UnionSerializer<T>` base class
+For your own models, `@ForyStruct()` with code generation is almost always the 
better choice.
 
 ## Implement `Serializer<T>`
 
+Subclass `Serializer<T>` and implement `write` and `read`. Use 
`context.buffer` to read and write raw bytes:
+
 ```dart
 import 'package:fory/fory.dart';
 
@@ -60,7 +59,7 @@ final class PersonSerializer extends Serializer<Person> {
 }
 ```
 
-Register it before use:
+Register the serializer before you use it:
 
 ```dart
 final fory = Fory();
@@ -72,11 +71,9 @@ fory.registerSerializer(
 );
 ```
 
-## Use `WriteContext` and `ReadContext`
-
-Manual serializers should do nested xlang work through the context rather than 
calling root APIs recursively.
+## Writing Nested Objects
 
-### Write nested values with reference handling
+When your serializer has a field that is itself a Fory-managed type, use 
`context.writeRef` and `context.readRef` rather than calling `fory.serialize` 
recursively. This keeps reference tracking correct and avoids writing a full 
root frame inside a nested payload.
 
 ```dart
 @override
@@ -90,27 +87,15 @@ Wrapper read(ReadContext context) {
 }
 ```
 
-### Write values without seeding references
-
-`writeNonRef` writes a non-reference payload and does not seed later 
back-references.
+If you do not need reference identity tracking for a nested value (i.e., you 
know the value will never appear more than once in a graph), use `writeNonRef`:
 
 ```dart
 context.writeNonRef(value.child);
 ```
 
-### Fine-grained ref/value control
-
-Use `writeRefValueFlag` when your serializer needs explicit control over 
whether payload bytes follow.
-
-```dart
-if (context.writeRefValueFlag(value.payload)) {
-  context.writeNonRef(value.payload);
-}
-```
-
 ## Unions
 
-Manual union serializers should extend `UnionSerializer<T>`.
+For a discriminated/tagged union, extend `UnionSerializer<T>` instead of 
`Serializer<T>`. Write a discriminant value first, then the active variant; 
read the discriminant and dispatch accordingly.
 
 ```dart
 final class ShapeSerializer extends UnionSerializer<Shape> {
@@ -118,36 +103,34 @@ final class ShapeSerializer extends 
UnionSerializer<Shape> {
 
   @override
   void write(WriteContext context, Shape value) {
-    // write active alternative
+    // write active variant
   }
 
   @override
   Shape read(ReadContext context) {
-    // read active alternative
+    // read discriminant, return correct variant
     throw UnimplementedError();
   }
 }
 ```
 
-The xlang spec defines `UNION`, `TYPED_UNION`, `NAMED_UNION`, and `NONE` wire 
types. Use registrations that match the peers you interoperate with.
-
-## Early Reference Binding During Reads
+## Circular References in Custom Serializers
 
-If your serializer allocates an object before all nested fields are read, bind 
it early so back-references can resolve to that instance.
+If your serializer can encounter circular object graphs, bind the object to 
the reference tracker **before** reading its nested fields:
 
 ```dart
 final value = Node.empty();
-context.reference(value);
-value.next = context.readRef() as Node?;
+context.reference(value);         // register the object first
+value.next = context.readRef() as Node?;  // now nested reads can refer back 
to it
 return value;
 ```
 
-## Best Practices
+Skipping this step causes back-references to that object to resolve to `null`.
+
+## Tips
 
-- Keep payload code focused on the payload only.
-- Let `Fory` own the root frame and top-level reset lifecycle.
-- Prefer direct buffer access for repeated primitive IO inside hot serializers.
-- Register serializers consistently across all peers.
+- Use `context.buffer` for direct byte reads/writes in hot paths.
+- Register the serializer with the same identity (`id` or `namespace + 
typeName`) on every side.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/field-configuration.md 
b/docs/guide/dart/field-configuration.md
index 8a9402de01..4f16f2b7ad 100644
--- a/docs/guide/dart/field-configuration.md
+++ b/docs/guide/dart/field-configuration.md
@@ -19,23 +19,23 @@ license: |
   limitations under the License.
 ---
 
-Use `@ForyField(...)` to override generated serializer behavior for individual 
fields.
+Add `@ForyField(...)` to a field inside a `@ForyStruct()` class to change how 
that field is serialized.
 
-## Options Overview
+## Quick Reference
 
 ```dart
 @ForyField(
-  skip: false,
-  id: 10,
-  nullable: true,
-  ref: true,
-  dynamic: false,
+  skip: false,      // exclude the field from serialization
+  id: 10,           // stable field ID for schema evolution
+  nullable: true,   // override nullability detection
+  ref: true,        // enable reference tracking for this field
+  dynamic: false,   // control whether the runtime type is written
 )
 ```
 
 ## `skip`
 
-Exclude a field from generated serialization.
+Exclude a field from serialization entirely. Useful for cached, computed, or 
UI-only values that should not land in a persisted or transmitted message.
 
 ```dart
 @ForyField(skip: true)
@@ -44,90 +44,81 @@ String cachedDisplayName = '';
 
 ## `id`
 
-Provides a stable field identifier for compatible structs.
+Assigns a stable identity to the field so that Fory can match it by ID after a 
schema change (a field rename or reorder). **If you plan to add, remove, or 
rename fields in the future, assign IDs to all fields now** β€” before you ship 
the first payload.
 
 ```dart
 @ForyField(id: 1)
 String name = '';
 ```
 
-In compatible mode, stable field IDs matter more than declaration order. Keep 
IDs fixed once payloads are shared.
+Once a payload is shared across services, never reuse an `id` for a different 
field.
 
 ## `nullable`
 
-Overrides inferred nullability.
+Explicitly marks a field as nullable or non-nullable, overriding what Fory 
infers from the Dart type. Use this when the Dart type is non-nullable but you 
want Fory to accept `null` on the wire (e.g., reading messages from an older 
producer that can omit the field).
 
 ```dart
 @ForyField(nullable: true)
 String nickname = '';
 ```
 
-`null` means "use the Dart type as written." In cross-language scenarios, make 
sure your nullability contract also matches peer runtimes.
+In cross-language scenarios, make sure the nullability contract also matches 
what peer runtimes expect.
 
 ## `ref`
 
-Enables reference tracking for that field.
+Enables reference tracking for a specific field. Use this when multiple 
objects in the graph can point to the same instance, or when the field type can 
be circular. Without `ref: true`, Fory serializes the same object value twice 
if it appears in two fields.
 
 ```dart
 @ForyField(ref: true)
 List<Object?> sharedNodes = <Object?>[];
 ```
 
-Basic scalar values never track references even if `ref` is set to `true`.
+Note: scalar types like `int`, `double`, and `bool` never benefit from 
reference tracking even if `ref: true` is set.
 
 ## `dynamic`
 
-Controls whether generated code writes runtime type metadata for the field.
+Controls whether Fory writes the concrete runtime type of the field value into 
the payload.
+
+- `null` (default) β€” Fory decides automatically based on the declared type.
+- `false` β€” always use the declared field type; more compact but the 
deserializer must know the exact type.
+- `true` β€” always write the actual runtime type; needed when the field is 
declared as `Object?` or a base class but can hold different concrete types at 
runtime (polymorphism).
 
 ```dart
 @ForyField(dynamic: true)
-Object? payload;
+Object? payload;  // can hold any registered type at runtime
 ```
 
-- `null`: auto
-- `false`: use the declared field type
-- `true`: write runtime type information
-
-This is the key knob for polymorphic fields and heterogeneous object payloads.
+## Numeric Field Annotations
 
-## Numeric Encoding Overrides
-
-Use numeric annotations to control the xlang wire type used for integer fields.
+Dart `int` is a 64-bit value at runtime. When exchanging messages with Java, 
Go, or C#, the receiving side may expect a narrower integer. Use a numeric 
annotation to pin the exact wire format:
 
 ```dart
 @ForyStruct()
 class Sample {
   Sample();
 
-  @Int32Type(compress: false)
+  @Int32Type(compress: false)   // always writes 4 bytes
   int fixedWidthInt = 0;
 
-  @Int64Type(encoding: LongEncoding.tagged)
+  @Int64Type(encoding: LongEncoding.tagged)  // variable-length encoding
   int compactLong = 0;
 
-  @Uint32Type(compress: true)
+  @Uint32Type(compress: true)   // variable-length unsigned
   int smallUnsigned = 0;
 }
 ```
 
-Available numeric annotations include:
-
-- `@Int32Type(...)`
-- `@Int64Type(...)`
-- `@Uint8Type()`
-- `@Uint16Type()`
-- `@Uint32Type(...)`
-- `@Uint64Type(...)`
+Available annotations: `@Int32Type`, `@Int64Type`, `@Uint8Type`, 
`@Uint16Type`, `@Uint32Type`, `@Uint64Type`.
 
-These should be chosen to match the intended xlang wire type and peer-language 
expectations.
+Alternatively, use the explicit wrapper types (`Int32`, `UInt32`, etc.) 
described in [Supported Types](supported-types.md).
 
-## Field Alignment Across Languages
+## Aligning Fields Across Languages
 
-Cross-language decoding depends on matching field names or stable field IDs. 
When models differ across languages:
+When the same model is defined in multiple languages:
 
-- keep equivalent logical fields aligned
-- prefer stable `id` values for evolving structs
-- use `dynamic: true` only when the field is genuinely polymorphic
+- Assign stable `id` values to every field that might change over time.
+- Use `dynamic: true` for fields that are genuinely polymorphic.
+- Keep the logical meaning of each field consistent across languages β€” Fory 
matches fields by name or ID, but cannot reconcile semantic differences.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/index.md b/docs/guide/dart/index.md
index e52ef5f187..b5517810e9 100644
--- a/docs/guide/dart/index.md
+++ b/docs/guide/dart/index.md
@@ -19,36 +19,30 @@ license: |
   limitations under the License.
 ---
 
-Apache Foryβ„’ Dart is a cross-language serialization runtime for Dart. It reads 
and writes the xlang wire format defined by the [xlang serialization 
specification](../../specification/xlang_serialization_spec.md) and is designed 
around generated serializers with an advanced customized serializer escape 
hatch.
+Apache Foryβ„’ Dart lets you serialize Dart objects to bytes and deserialize 
them back β€” including across services written in Java, Go, C#, Python, and 
other Fory-supported languages.
 
 ## Why Fory Dart?
 
-- Cross-language compatibility with other Fory xlang runtimes
-- Generated serializers for annotated Dart models
-- Compatible mode for schema evolution
-- Optional reference tracking for shared and circular object graphs
-- Manual serializer support for external types, custom wire behavior, and 
unions
-- A small public API centered on `Fory`, `Config`, annotations, and xlang 
value wrappers
-
-## Runtime Model
-
-The Dart runtime only supports xlang payloads. There is no separate 
native-mode builder. Root operations happen through `Fory`, while nested 
payload work stays in explicit `WriteContext` and `ReadContext` instances. This 
mirrors the ownership model described in the [xlang implementation 
guide](../../specification/xlang_implementation_guide.md).
+- **Cross-language**: serialize in Dart, deserialize in Java, Go, C#, and more 
without writing any glue code
+- **Fast**: generated serializer code replaces reflection at runtime
+- **Schema evolution**: add or remove fields without breaking existing messages
+- **Circular references**: optional reference tracking handles shared or 
recursive object graphs
+- **Escape hatch**: write a manual serializer for any type that cannot be 
annotated
 
 ## Quick Start
 
 ### Requirements
 
 - Dart SDK 3.6 or later
-- `build_runner` for generated serializers
+- `build_runner` (generates the serializer code)
 
 ### Install
 
-Add the package from your Dart workspace or package source. In this 
repository, the runtime lives under `dart/packages/fory`.
+Add the dependency to your `pubspec.yaml`:
 
 ```yaml
 dependencies:
-  fory:
-    path: packages/fory
+  fory: ^0.17.0
 
 dev_dependencies:
   build_runner: ^2.4.0
@@ -56,6 +50,8 @@ dev_dependencies:
 
 ### Basic Example
 
+Define your model, run the generator once, then serialize:
+
 ```dart
 import 'package:fory/fory.dart';
 
@@ -106,19 +102,21 @@ void main() {
 Generate the companion file before running the program:
 
 ```bash
-cd dart/packages/fory
 dart run build_runner build --delete-conflicting-outputs
 ```
 
-## Core API
+`PersonFory` is generated by `build_runner`. The `namespace` and `typeName` 
values are how peers in other languages identify the same type β€” keep them 
stable once your service is in production.
+
+## API Overview
 
-- `Fory({bool compatible = false, bool checkStructVersion = true, int maxDepth 
= Config.defaultMaxDepth, int maxCollectionSize = 
Config.defaultMaxCollectionSize, int maxBinarySize = 
Config.defaultMaxBinarySize})`
-- `serialize(Object? value, {bool trackRef = false})`
-- `deserialize<T>(Uint8List bytes)`
-- `register(Type type, {int? id, String? namespace, String? typeName})`
-- `registerSerializer(Type type, Serializer serializer, ...)`
-- `@ForyStruct()` and `@ForyField(...)` for generated serializers
-- xlang value wrappers such as `Int8`, `Int16`, `Int32`, `UInt8`, `UInt16`, 
`UInt32`, `Float16`, `Float32`, `LocalDate`, and `Timestamp`
+- `Fory(...)` β€” create a serializer instance; create once and reuse it
+- `fory.serialize(value)` β€” returns `Uint8List` bytes
+- `fory.deserialize<T>(bytes)` β€” returns a `T`
+- `@ForyStruct()` β€” marks a class for code generation
+- `@ForyField(...)` β€” per-field options (skip, ID, nullability, references)
+- Integer wrappers: `Int8`, `Int16`, `Int32`, `UInt8`, `UInt16`, `UInt32`
+- Float wrappers: `Float16`, `Float32`
+- Time wrappers: `LocalDate`, `Timestamp`
 
 ## Documentation
 
diff --git a/docs/guide/dart/schema-evolution.md 
b/docs/guide/dart/schema-evolution.md
index 778c39bce0..8d33297a91 100644
--- a/docs/guide/dart/schema-evolution.md
+++ b/docs/guide/dart/schema-evolution.md
@@ -19,36 +19,31 @@ license: |
   limitations under the License.
 ---
 
-Fory Dart supports schema evolution through compatible structs.
+Schema evolution lets different versions of your app exchange messages safely 
β€” a v2 writer can produce a message that a v1 reader can still decode, and vice 
versa.
 
-## Two Struct Modes
+## Two Modes
 
-### Schema-Consistent Mode
+### Compatible Mode (recommended for evolving services)
 
-This is the default when `Config.compatible` is `false`.
-
-- Structs use the schema-consistent path.
-- `checkStructVersion` can validate schema-version compatibility.
-- This mode is appropriate when both sides evolve in lockstep or when you want 
stricter validation.
-
-### Compatible Mode
-
-Enable compatible mode when you want evolving field metadata on the wire.
+Enable this when services may run different versions at the same time β€” for 
example, during a rolling deployment or when clients are not updated 
immediately.
 
 ```dart
 final fory = Fory(compatible: true);
 ```
 
-In compatible mode:
+In compatible mode, Fory includes enough field metadata in each message so 
that the reader can skip unknown fields and use defaults for missing ones. Use 
stable field IDs (see below) to anchor the schema across changes.
 
-- evolving structs use compatible struct encoding
-- `checkStructVersion` is disabled
-- field IDs become the stability anchor for changed schemas
-- TypeDef metadata is shared and reused across payloads
+### Schema-Consistent Mode (default)
 
-## Generated Struct Controls
+Both sides must have the same model. Fory validates that the schemas match and 
will reject messages from a different schema version. Use this when all 
services are always updated together and you want schema mismatches to be 
caught as fast errors.
 
-`@ForyStruct(evolving: true)` is the default and is the right choice when the 
type may evolve over time.
+```dart
+final fory = Fory(); // compatible: false by default
+```
+
+## Setting Up for Evolution
+
+To use compatible mode safely, mark your structs with `@ForyStruct(evolving: 
true)` (the default) and assign a stable `@ForyField(id: ...)` to every field 
**before you ship your first payload**:
 
 ```dart
 @ForyStruct(evolving: true)
@@ -63,25 +58,32 @@ class UserProfile {
 }
 ```
 
-Use explicit stable field IDs when a schema may change.
+If you add field IDs after payloads are already in production, existing stored 
messages won't have them and evolution won't work correctly.
+
+## What You Can Safely Change
+
+**Safe changes** (compatible on both sides):
 
-## Safe Evolution Practices
+- Add a new optional field with a new, unused field ID.
+- Rename a field β€” as long as the `@ForyField(id: ...)` stays the same.
+- Remove a field β€” the peer will just ignore the missing value and use the 
Dart default.
 
-Typical compatible changes include:
+**Unsafe changes** (may break existing messages):
 
-- adding a new optional field with a new field ID
-- keeping existing field IDs stable
-- widening consumer behavior to tolerate missing data
+- Reuse an existing field ID for a different field.
+- Change a field's type to an incompatible type (e.g., `Int32` β†’ `String`).
+- Change the registration identity (`id`, `namespace`, or `typeName`) of a 
type after messages are in production.
+- Change a field's logical meaning without changing its ID.
 
-Changes that require extra care include:
+## Cross-Language Notes
 
-- reusing an old field ID for different semantics
-- changing a field's logical cross-language meaning
-- changing registration identity for an existing type
+Evolution only works when **all** runtimes that exchange messages agree on:
 
-## Cross-Language Guidance
+1. The same `compatible` setting.
+2. The same type registration identity (numeric ID or `namespace + typeName`).
+3. The logical meaning of field IDs.
 
-Schema evolution only works when all runtimes agree on the type registration 
identity and the logical meaning of field IDs. Validate rolling upgrades with 
real round trips across the languages you support.
+Test rolling-upgrade scenarios with real round trips before deploying.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/supported-types.md 
b/docs/guide/dart/supported-types.md
index edf2f29f99..a6acc5f2d7 100644
--- a/docs/guide/dart/supported-types.md
+++ b/docs/guide/dart/supported-types.md
@@ -19,70 +19,61 @@ license: |
   limitations under the License.
 ---
 
-This page summarizes the main xlang-facing types in Apache Fory Dart.
+This page lists the Dart types you can use in Fory messages, and flags where 
you need to be careful for cross-language compatibility.
 
-## Primitive-Like Dart Values
+## Built-in Primitive Types
 
-The runtime supports common Dart values directly where they map cleanly to 
xlang types:
+The following Dart types serialize directly without any special handling:
 
-- `bool`
-- `int`
-- `double`
-- `String`
-- `Uint8List` and other supported typed byte containers
-- `List`, `Set`, and `Map`
-- `DateTime`-adjacent values through explicit wrappers such as `Timestamp` and 
`LocalDate`
-
-Because Dart `int` and `double` are broader runtime concepts than many xlang 
scalar types, wrapper types and field annotations are used when the exact wire 
type matters.
+| Dart type            | Cross-language notes                                  
                                                      |
+| -------------------- | 
-----------------------------------------------------------------------------------------------------------
 |
+| `bool`               | Direct mapping                                        
                                                      |
+| `int`                | Serialized as 64-bit by default. Use wrappers or 
`@Int32Type` etc. when the peer expects a narrower integer |
+| `double`             | Maps to 64-bit float. Use `Float32` wrapper when the 
peer expects 32-bit                                    |
+| `String`             | Direct mapping                                        
                                                      |
+| `Uint8List`          | Binary blob                                           
                                                      |
+| `List`, `Set`, `Map` | Supported; element types must also be supported       
                                                      |
+| `DateTime`           | Use `Timestamp` or `LocalDate` wrappers for explicit 
semantics                                              |
 
 ## Integer Wrappers
 
-Use wrapper classes when you need an exact xlang fixed-width integer type.
+Dart `int` is 64-bit at runtime. If the peer language expects a 32-bit integer 
(Java `int`, Go `int32`, C# `int`) and you send a Dart `int`, the 
deserialization may fail or silently truncate.
+
+Use an integer wrapper class to pin the exact wire width:
 
 ```dart
-final Int8 tiny = Int8(-1);
-final Int16 shortValue = Int16(7);
-final Int32 age = Int32(36);
-final UInt8 flags = UInt8(255);
-final UInt16 port = UInt16(65535);
-final UInt32 count = UInt32(4000000000);
+final Int8 tiny = Int8(-1);        // 8-bit signed
+final Int16 shortValue = Int16(7); // 16-bit signed
+final Int32 age = Int32(36);       // 32-bit signed β€” matches Java int, C# 
int, Go int32
+final UInt8 flags = UInt8(255);    // 8-bit unsigned
+final UInt16 port = UInt16(65535); // 16-bit unsigned
+final UInt32 count = UInt32(4000000000); // 32-bit unsigned
 ```
 
-Available wrappers:
-
-- `Int8`
-- `Int16`
-- `Int32`
-- `UInt8`
-- `UInt16`
-- `UInt32`
-
-Each wrapper normalizes the stored value to the target bit width.
+Each wrapper clamps the stored value to the target bit width.
 
 ## Floating-Point Wrappers
 
-Use explicit wrapper types when you need a precise non-`float64` wire type.
-
-- `Float16`
-- `Float32`
+Dart `double` maps to 64-bit float. If the peer uses a 32-bit float, use a 
wrapper:
 
-Dart `double` maps naturally to the xlang `float64` family.
+- `Float32` β€” 32-bit float (matches Java `float`, C# `float`, Go `float32`)
+- `Float16` β€” half-precision, for specialized numeric payloads
 
 ## Time and Date Types
 
-The runtime exposes explicit xlang-friendly temporal wrappers:
+Avoid sending raw `DateTime` across languages β€” time zone handling and epoch 
differences vary. Use the explicit wrappers instead:
 
-- `Timestamp` for seconds-plus-nanoseconds UTC instants
-- `LocalDate` for timezone-free calendar dates
+- `Timestamp` β€” a UTC instant with nanosecond precision (seconds + nanoseconds)
+- `LocalDate` β€” a calendar date without time or time zone
 
 ```dart
-final timestamp = Timestamp.fromDateTime(DateTime.now().toUtc());
+final now = Timestamp.fromDateTime(DateTime.now().toUtc());
 final birthday = LocalDate(1990, 12, 1);
 ```
 
 ## Structs and Enums
 
-User-defined structs and enums are supported through generated registration or 
customized serializers.
+Annotate classes with `@ForyStruct()` and run `build_runner` to make them 
serializable. Enums in the same file are included automatically.
 
 ```dart
 @ForyStruct()
@@ -90,30 +81,19 @@ class User {
   User();
 
   String name = '';
-  Int32 age = Int32(0);
+  Int32 age = Int32(0); // use Int32 when peers expect a 32-bit integer
 }
 ```
 
-## Collections
-
-Fory Dart supports the core xlang collection shapes:
-
-- `List<T>`
-- `Set<T>`
-- `Map<K, V>`
-
-Cross-language compatibility still depends on element and key types having 
compatible peer-language mappings. Avoid mutable collection keys.
+See [Code Generation](code-generation.md).
 
-## Typed Arrays and Binary Values
-
-The xlang spec defines dedicated wire types for binary payloads and numeric 
arrays. In Dart, use the typed values exported by the runtime and test the 
exact round trip you need with your peer languages.
+## Collections
 
-## Exact Mapping Rules
+Fory supports `List<T>`, `Set<T>`, and `Map<K, V>`. Element and key types must 
also be serializable types. Avoid using mutable objects as map keys.
 
-For the complete cross-language mapping, see:
+## Compatibility Tip
 
-- [Xlang type mapping](../../specification/xlang_type_mapping.md)
-- [Cross-Language](cross-language.md)
+When in doubt about whether a Dart type will match what the peer expects, use 
the explicit wrapper types. Guessing the wrong numeric width is one of the most 
common cross-language bugs.
 
 ## Related Topics
 
diff --git a/docs/guide/dart/troubleshooting.md 
b/docs/guide/dart/troubleshooting.md
index 1d9fd2fc2b..9266d05fb8 100644
--- a/docs/guide/dart/troubleshooting.md
+++ b/docs/guide/dart/troubleshooting.md
@@ -23,21 +23,19 @@ This page covers common Dart runtime issues and fixes.
 
 ## `Only xlang payloads are supported by the Dart runtime.`
 
-The Dart runtime only deserializes xlang frames. Make sure the peer runtime is 
writing xlang payloads rather than a language-native format.
+The writer is sending a native-mode (non-xlang) payload. Make sure every 
service uses the xlang-compatible path:
 
-- Java must use `withLanguage(Language.XLANG)`.
-- Go must enable `WithXlang(true)`.
-- Other peers must use their xlang-compatible path.
+- **Java**: add `.withLanguage(Language.XLANG)` to the Fory builder.
+- **Go**: use `WithXlang(true)` in the Fory options.
+- **Other runtimes**: check their respective guides for enabling 
cross-language mode.
 
 ## `Type ... is not registered.`
 
-Generated and manual user-defined types must be registered before reading or 
writing them.
+Fory does not know how to serialize or deserialize this type. Fix it by:
 
-Checklist:
-
-1. Run code generation.
-2. Register the type through the generated namespace or `registerSerializer`.
-3. Register all nested user-defined types, not only the root type.
+1. Running code generation if you haven't: `dart run build_runner build 
--delete-conflicting-outputs`
+2. Calling the generated `register` function (or `registerSerializer`) for the 
type **before** calling `serialize` or `deserialize`.
+3. Registering **all** types that appear in a message, not just the root type. 
For example, if `Order` contains an `Address`, register both.
 
 ## Generated part file is missing or stale
 
@@ -52,45 +50,45 @@ If you moved files or renamed types, rebuild before 
re-running analysis or tests
 
 ## `Deserialized value has type ..., expected ...`
 
-`deserialize<T>` validates the runtime result after decoding. This error 
usually means:
+The payload describes a different type than `T` in `deserialize<T>`. Common 
causes:
 
-- the payload describes a different root type than the requested `T`
-- registration points to a different logical type than expected
-- a dynamic payload should be decoded as `Object?` or a container type first
+- You registered the type on the writing side with a different ID or name than 
on the reading side.
+- The payload was produced by a different code path that serializes a 
different root object.
+- You are trying to deserialize a heterogeneous container β€” decode it as 
`Object?` or `List<Object?>` first, then cast.
 
-## Unexpected reference identity behavior
+## Objects aren't the same instance after deserialization
 
-Check whether reference tracking is enabled in the correct place:
+Fory does not track object identity by default, so two fields pointing to the 
same object will produce two independent copies after a round trip.
 
-- root graph or root container: `trackRef: true`
-- generated field graph: `@ForyField(ref: true)`
-- customized serializer: use `writeRef`, `readRef`, and 
`context.reference(...)` correctly
+To preserve identity:
 
-`writeNonRef` intentionally does not seed later back-references.
+- For fields inside a `@ForyStruct`, add `@ForyField(ref: true)` to those 
fields.
+- For a top-level collection, pass `trackRef: true` to `fory.serialize(...)`.
+- In a custom serializer, use `context.writeRef` / `context.readRef` and call 
`context.reference(obj)` before reading nested fields.
 
-## Cross-language field mismatch
+## Cross-language field mismatch (missing data or wrong values)
 
-Symptoms include missing data, default values, or type errors on peers.
+Symptoms: fields come back as default values or wrong types after a round trip 
to another language.
 
-Check:
+Checklist:
 
-- same registration identity on both sides
-- stable field IDs for evolving structs
-- matching logical field names and meanings
-- compatible numeric widths and temporal types
+1. Same registration identity on both sides (same numeric ID **or** same 
`namespace + typeName`).
+2. Stable `@ForyField(id: ...)` assigned before the first payload was produced.
+3. Compatible numeric widths β€” use `Int32` in Dart when the peer field is 
`int` (Java), `int32` (Go), or `int` (C#).
+4. `Timestamp` / `LocalDate` instead of raw `DateTime` for date/time fields.
+5. `compatible: true` on **both** sides if using schema evolution.
 
-## Validation Commands
+## Running Tests Locally
 
-For the main Dart workspace:
+Main Dart package:
 
 ```bash
-cd dart
 dart run build_runner build --delete-conflicting-outputs
 dart analyze
 dart test
 ```
 
-For the integration-style test package:
+Integration test package:
 
 ```bash
 cd dart/packages/fory-test
diff --git a/docs/guide/dart/type-registration.md 
b/docs/guide/dart/type-registration.md
index 5d74560251..a5f93e1c0e 100644
--- a/docs/guide/dart/type-registration.md
+++ b/docs/guide/dart/type-registration.md
@@ -19,25 +19,30 @@ license: |
   limitations under the License.
 ---
 
-This page covers how to register user-defined types in Apache Foryβ„’ Dart.
+Fory needs to know which class corresponds to which type in a serialized 
message. You do this by registering each class before you serialize or 
deserialize it.
 
-## Registration Modes
+## Choosing a Registration Strategy
 
-Fory Dart supports the same two registration styles used by other xlang 
runtimes.
+Fory offers two strategies. Pick one and use it consistently across every 
language that reads or writes the type.
 
-### Register by Numeric ID
+### Strategy 1: Numeric ID
 
-Numeric IDs are compact on the wire and fast to resolve.
+Compact and fast. Good when a small team can coordinate IDs across services.
 
 ```dart
 ModelsFory.register(fory, User, id: 100);
 ```
 
-Use the same numeric ID for the same logical type in every language.
+The same number must be used in every other language:
 
-### Register by Namespace and Type Name
+```java
+// Java side
+fory.register(User.class, 100);
+```
+
+### Strategy 2: Namespace + Type Name
 
-Name-based registration avoids global numeric ID coordination and is often 
easier across multiple teams.
+More self-describing. Good when multiple teams or packages define types 
independently and numeric ID coordination is impractical.
 
 ```dart
 ModelsFory.register(
@@ -48,21 +53,21 @@ ModelsFory.register(
 );
 ```
 
-The same `namespace + typeName` pair must be used by every runtime that reads 
or writes the type.
+Every runtime that reads or writes this type must use the same `namespace` and 
`typeName`.
 
-## Generated Type Registration
+> **Do not mix strategies for the same type.** If one side uses a numeric ID 
and the other uses a name, deserialization will fail.
 
-Generated types should normally be registered through the generated namespace 
wrapper:
+## Registering Generated Types
+
+Call the generated `register` function from the `.fory.dart` file. It installs 
all the serializer metadata for you:
 
 ```dart
 UserModelsFory.register(fory, User, id: 100);
 ```
 
-Internally, the wrapper installs generated metadata and then calls 
`Fory.register(...)`.
-
-## Register a Manual Serializer
+## Registering a Custom Serializer
 
-Customized serializers register through `registerSerializer`:
+For types that you cannot annotate with `@ForyStruct()`, pass a serializer 
instance directly:
 
 ```dart
 fory.registerSerializer(
@@ -73,21 +78,18 @@ fory.registerSerializer(
 );
 ```
 
-## Cross-Language Requirements
-
-Registration must match across runtimes:
+See [Custom Serializers](custom-serializers.md) for how to implement a 
serializer.
 
-- same numeric ID, or
-- same namespace and type name
+## Rules to Follow
 
-The wire format distinguishes built-in xlang type IDs from user-registered 
type IDs. The user ID is encoded separately as an unsigned varint32, as 
described in the [xlang serialization 
specification](../../specification/xlang_serialization_spec.md).
+- Register **before** the first `serialize` or `deserialize` call.
+- Register **every** class that can appear in a message, not only the root 
type.
+- Keep IDs (or names) **stable** once payloads are persisted or exchanged 
across services. Changing them will break deserialization of old messages.
+- Do not mix a numeric ID on one side with a name on the other for the same 
type.
 
-## Common Rules
+## Cross-Language Requirements
 
-- Register before the first serialize or deserialize call.
-- Register nested user-defined types as well as root types.
-- Keep IDs stable once payloads are persisted or exchanged across services.
-- Do not mix a numeric ID on one side with a name-based registration on the 
other side for the same type.
+The same numeric ID or `namespace + typeName` pair must be used in every 
runtime that reads or writes the type. See [Cross-Language](cross-language.md) 
for examples.
 
 ## Related Topics
 
diff --git a/docs/guide/go/_category_.json b/docs/guide/go/_category_.json
index 796c0a4dd6..e4d176a762 100644
--- a/docs/guide/go/_category_.json
+++ b/docs/guide/go/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Go",
-  "position": 4,
+  "position": 5,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/java/_category_.json b/docs/guide/java/_category_.json
index 3cb119d373..3508cf9008 100644
--- a/docs/guide/java/_category_.json
+++ b/docs/guide/java/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Java",
-  "position": 0,
+  "position": 1,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/cpp/_category_.json 
b/docs/guide/javascript/_category_.json
similarity index 52%
copy from docs/guide/cpp/_category_.json
copy to docs/guide/javascript/_category_.json
index c543ab1388..2434e92ab8 100644
--- a/docs/guide/cpp/_category_.json
+++ b/docs/guide/javascript/_category_.json
@@ -1,6 +1,6 @@
 {
-  "label": "C++",
-  "position": 3,
+  "label": "JavaScript",
+  "position": 6,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/javascript/basic-serialization.md 
b/docs/guide/javascript/basic-serialization.md
index 077ba9c541..ced490fd29 100644
--- a/docs/guide/javascript/basic-serialization.md
+++ b/docs/guide/javascript/basic-serialization.md
@@ -19,9 +19,9 @@ license: |
   limitations under the License.
 ---
 
-This guide covers the core serialization flow in Apache Fory JavaScript.
+This guide covers the core serialization APIs in Apache Fory JavaScript.
 
-## Create and Reuse a `Fory` Instance
+## Create a `Fory` Instance
 
 ```ts
 import Fory from "@apache-fory/core";
@@ -29,7 +29,7 @@ import Fory from "@apache-fory/core";
 const fory = new Fory();
 ```
 
-Create one instance, register your schemas, and reuse it. A `Fory` instance 
caches generated serializers and type metadata, so recreating it for every 
request adds unnecessary overhead.
+Create one instance, register your schemas, and reuse it. Fory caches the 
generated serializers after the first `register` call, so recreating it on 
every request wastes that work.
 
 ## Define a Schema with `Type.struct`
 
@@ -109,15 +109,15 @@ fory.deserialize(fory.serialize(new 
Date("2021-10-20T09:13:00Z")));
 // Date
 ```
 
-### Number and `bigint` behavior
+### Number and `bigint`
 
-JavaScript has both `number` and `bigint`, but xlang distinguishes between 
32-bit, 64-bit, floating-point, and tagged integer representations. For any 
cross-language or long-lived contract, prefer explicit field types in schemas 
instead of depending on dynamic root-type inference.
+JavaScript `number` is a 64-bit float, which cannot exactly represent all 
64-bit integers. For cross-language contracts or anywhere exact integer sizes 
matter, use explicit field types in your schema:
 
-- use `Type.int32()` for 32-bit integers
-- use `Type.int64()` for 64-bit integers and pass `bigint`
-- use `Type.float32()` or `Type.float64()` for floating-point values
+- `Type.int32()` β€” 32-bit integer; use JavaScript `number`
+- `Type.int64()` β€” 64-bit integer; use JavaScript `bigint`
+- `Type.float32()` / `Type.float64()` β€” floating-point
 
-Dynamic root serialization is convenient, but the exact heuristic for whether 
a value comes back as `number` or `bigint` should not be treated as a stable 
API contract.
+Dynamic root serialization (calling `fory.serialize(someNumber)` without a 
schema) will infer a type, but the inferred type is not guaranteed by the API. 
Use a schema for any stable contract.
 
 ## Arrays, Maps, and Sets
 
diff --git a/docs/guide/javascript/cross-language.md 
b/docs/guide/javascript/cross-language.md
index 06f5c3e2cc..d4fb159aa2 100644
--- a/docs/guide/javascript/cross-language.md
+++ b/docs/guide/javascript/cross-language.md
@@ -19,34 +19,31 @@ license: |
   limitations under the License.
 ---
 
-Apache Fory JavaScript always uses the xlang wire format. Interoperability 
depends on matching schemas and compatible type mappings rather than on 
enabling a separate mode switch.
+Fory JavaScript serializes to the same binary format as the Java, Python, Go, 
Rust, Swift, and C++ Fory runtimes. You can write a message in JavaScript and 
read it in Java β€” or any other direction β€” without any conversion layer.
 
-Current limits to keep in mind:
+Things to keep in mind:
 
-- JavaScript deserializes xlang payloads only
-- out-of-band mode is not currently supported in the JavaScript runtime
+- The Fory JavaScript runtime reads and writes cross-language payloads only 
(it does not support any language-native format).
+- Out-of-band mode is not currently supported.
 
-## Interop rules
+## Requirements for a Successful Round Trip
 
-For a payload to round-trip between JavaScript and another runtime:
+For a message to survive a round trip between JavaScript and another runtime:
 
-1. **Register the same logical type identity** on both sides.
-   - same numeric type ID, or
-   - same namespace + type name
-2. **Use compatible field types** according to the [type mapping 
spec](../../specification/xlang_type_mapping.md).
-3. **Match nullability and reference-tracking expectations** where object 
graphs require them.
-4. **Use compatible mode** when independent schema evolution is expected.
+1. **Same type identity** on both sides β€” same numeric ID, or same `namespace 
+ typeName`.
+2. **Compatible field types** β€” a `Type.int32()` field in JavaScript matches 
Java `int`, Go `int32`, C# `int`.
+3. **Same nullability** β€” if one side marks a field nullable, the other should 
too.
+4. **Same `compatible` mode** if using schema evolution.
+5. **Same reference tracking config** if your data has shared or circular 
references.
 
-## Interoperability workflow
+## Step-by-Step: JavaScript to Another Runtime
 
-When wiring JavaScript to another runtime in production code:
+1. Define the JavaScript schema with the same type name or numeric ID used by 
the other runtime.
+2. Register the schema in both runtimes.
+3. Match field types, nullability, and `compatible` settings.
+4. Test a real payload end-to-end before shipping.
 
-1. define the JavaScript schema with the same type identity used by the other 
runtime
-2. register the same type name or type ID in every participating runtime
-3. keep field types, nullability, enum layout, and schema-evolution settings 
aligned
-4. validate the end-to-end payload before relying on it in a shared contract
-
-Example JavaScript side:
+JavaScript side:
 
 ```ts
 import Fory, { Type } from "@apache-fory/core";
@@ -68,40 +65,36 @@ const bytes = serialize({
 });
 ```
 
-On the receiving side, register the same `example.message` type identity and 
compatible field types using that runtime's public API and guide:
+On the other side, register the same `example.message` type (same name or same 
numeric ID) using the peer runtime's API:
 
-- [Go guide](../go/index.md)
-- [Python guide](../python/index.md)
 - [Java guide](../java/index.md)
+- [Python guide](../python/index.md)
+- [Go guide](../go/index.md)
 - [Rust guide](../rust/index.md)
 
-## Field naming and ordering
-
-Cross-language matching depends on consistent field identity. When multiple 
runtimes model the same struct, use a naming scheme that maps cleanly across 
languages.
+## Field Naming
 
-Practical guidance:
+Fory matches fields by name. When models are defined in multiple languages, 
keep field names consistent β€” or at minimum use a naming scheme that maps 
unambiguously across languages (e.g. `snake_case` everywhere).
 
-- prefer stable snake_case or clearly corresponding names across runtimes
-- avoid accidental renames without updating every participating runtime
-- use compatible mode when fields may be added or removed over time
+When using `compatible: true` for schema evolution, field order differences 
are tolerated, but the names themselves must still match.
 
-## Numeric mapping guidance
+## Numeric Types
 
-JavaScript needs extra care because `number` is IEEE 754 double precision.
+JavaScript `number` is a 64-bit float, which does not map cleanly to every 
integer type in other languages. Use explicit schema types:
 
-- use `Type.int64()` with `bigint` for true 64-bit integers
-- use `Type.float32()` or `Type.float64()` for floating-point fields
-- avoid assuming that a dynamic JavaScript `number` maps cleanly to every 
integer width in another language
+- `Type.int32()` for 32-bit integers (Java `int`, Go `int32`, C# `int`)
+- `Type.int64()` with `bigint` values for 64-bit integers (Java `long`, Go 
`int64`)
+- `Type.float32()` or `Type.float64()` for floating-point values
 
-## Time mapping guidance
+## Date and Time
 
-- `Type.timestamp()` maps to a point in time and deserializes as `Date`
-- `Type.duration()` should be treated as a duration value, but JavaScript 
currently exposes typed duration fields as numeric time values rather than a 
dedicated duration class
-- `Type.date()` corresponds to a date-without-timezone type in the 
specification and deserializes as `Date`
+- `Type.timestamp()` β€” a point in time; round-trips as a JavaScript `Date`
+- `Type.date()` β€” a date without time; deserializes as `Date`
+- `Type.duration()` β€” exposed as a numeric millisecond value in JavaScript
 
-## Polymorphism and `Type.any()`
+## Polymorphic Fields
 
-Use `Type.any()` only when you genuinely need runtime-dispatched values.
+`Type.any()` lets a field hold different types at runtime, but it is harder to 
keep in sync across languages. Prefer explicit field schemas whenever possible.
 
 ```ts
 const wrapperType = Type.struct(
@@ -112,11 +105,9 @@ const wrapperType = Type.struct(
 );
 ```
 
-This works for polymorphic values, but explicit field schemas are easier to 
keep aligned across languages.
-
 ## Enums
 
-Enums must also be registered consistently across languages.
+Enum member **order** must match across languages. Fory encodes enums by 
ordinal position, not by value.
 
 ```ts
 const Color = { Red: 1, Green: 2, Blue: 3 };
@@ -124,11 +115,11 @@ const fory = new Fory();
 fory.register(Type.enum({ typeId: 210 }, Color));
 ```
 
-Use the same type ID or type name in Java, Python, Go, and other runtimes.
+Use the same type ID or type name in every peer runtime.
 
-## Limits and safety
+## Safety Limits
 
-Deserialization guardrails such as `maxDepth`, `maxBinarySize`, and 
`maxCollectionSize` are local runtime protections. They do not affect the wire 
format, but they can reject payloads that exceed local policy.
+The `maxDepth`, `maxBinarySize`, and `maxCollectionSize` options protect the 
JavaScript runtime from overly large payloads. They do not change the binary 
format β€” they only control what the local runtime is willing to accept.
 
 ## Related Topics
 
diff --git a/docs/guide/javascript/index.md b/docs/guide/javascript/index.md
index c715ad8cf1..170588baa4 100644
--- a/docs/guide/javascript/index.md
+++ b/docs/guide/javascript/index.md
@@ -19,18 +19,16 @@ license: |
   limitations under the License.
 ---
 
-Apache Fory JavaScript provides cross-language serialization for JavaScript 
and TypeScript applications. It uses the xlang wire format described in the 
[xlang serialization 
specification](../../specification/xlang_serialization_spec.md), so it is 
designed to interoperate with other Fory runtimes such as Java, Python, Go, 
Rust, Swift, and C++.
-
-The JavaScript runtime is schema-driven: you describe your data shape with 
`Type.*` builders or TypeScript decorators, register that schema with `Fory`, 
and then reuse the returned serializer pair for serialization and 
deserialization.
+Apache Fory JavaScript lets you serialize JavaScript and TypeScript objects to 
bytes and deserialize them back β€” including across services written in Java, 
Python, Go, Rust, Swift, and other Fory-supported languages.
 
 ## Why Fory JavaScript?
 
-- **Cross-language by design**: JavaScript uses the xlang wire format and 
interoperates with other Fory runtimes.
-- **Generated hot paths**: serializers are generated at runtime and cached per 
`Fory` instance.
-- **Reference-aware object graphs**: shared references and circular structures 
are supported when enabled.
-- **Explicit schemas**: field types, nullability, dynamic dispatch, and type 
identity are declared up front.
-- **Guardrails for untrusted data**: configurable depth, binary size, and 
collection size limits help bound deserialization work.
-- **Modern numeric support**: `bigint`, typed arrays, `Map`, `Set`, `Date`, 
`float16`, and `bfloat16` are supported.
+- **Cross-language**: serialize in JavaScript, deserialize in Java, Python, 
Go, and more without writing glue code
+- **Fast**: serializer code is generated and cached the first time you 
register a schema, not on every call
+- **Reference-aware**: shared references and circular object graphs are 
supported when enabled
+- **Explicit schemas**: field types, nullability, and polymorphism are 
declared once with `Type.*` builders or TypeScript decorators
+- **Safe defaults**: configurable depth, binary size, and collection size 
limits reject unexpectedly large or deep payloads
+- **Modern types**: `bigint`, typed arrays, `Map`, `Set`, `Date`, `float16`, 
and `bfloat16` are supported
 
 ## Installation
 
@@ -76,49 +74,29 @@ console.log(user);
 // { id: 1n, name: 'Alice', age: 30 }
 ```
 
-## Core Model
-
-### `Fory`
-
-A `Fory` instance owns:
-
-- the type registry
-- generated serializers
-- read/write contexts
-- configuration such as reference tracking and guardrails
-
-Reuse the same `Fory` instance across many operations. Registration is per 
instance.
-
-### `Type`
-
-`Type` is the schema DSL. It is used to describe:
+## How it works
 
-- primitive fields such as `Type.int32()` and `Type.string()`
-- collections such as `Type.array(...)`, `Type.map(...)`, and `Type.set(...)`
-- user types such as `Type.struct(...)` and `Type.enum(...)`
-- field-level metadata such as nullability, reference tracking, and dynamic 
dispatch
-
-### Registration
-
-`fory.register(...)` compiles and registers a serializer. It returns:
-
-- `serializer`: the generated serializer object
-- `serialize(value)`: serialize using that schema
-- `deserialize(bytes)`: deserialize using that schema
+Fory is schema-driven. You describe the shape of your data once with `Type.*` 
builders (or TypeScript decorators), then call `fory.register(schema)`. This 
returns a `{ serialize, deserialize }` pair that is fast to call repeatedly.
 
 ```ts
+// 1. Define the schema
 const personType = Type.struct("example.person", {
   name: Type.string(),
   email: Type.string().setNullable(true),
 });
 
+// 2. Register once
 const fory = new Fory();
-const personSerde = fory.register(personType);
+const { serialize, deserialize } = fory.register(personType);
+
+// 3. Use as many times as needed
+const bytes = serialize({ name: "Alice", email: null });
+const person = deserialize(bytes);
 ```
 
-## Configuration
+Create one `Fory` instance per application and reuse it β€” creating a new one 
for every request wastes the work of schema registration.
 
-The JavaScript runtime always uses xlang serialization. The most important 
options are:
+## Configuration
 
 ```ts
 import Fory from "@apache-fory/core";
@@ -130,21 +108,20 @@ const fory = new Fory({
   maxDepth: 100,
   maxBinarySize: 64 * 1024 * 1024,
   maxCollectionSize: 1_000_000,
-  useSliceString: false,
   hps,
 });
 ```
 
-| Option                     | Default            | Meaning                    
                                                                                
                       |
-| -------------------------- | ------------------ | 
---------------------------------------------------------------------------------------------------------------------------------
 |
-| `ref`                      | `false`            | Enables reference tracking 
for graphs with shared or circular references.                                  
                       |
-| `compatible`               | `false`            | Uses compatible struct 
encoding for schema evolution.                                                  
                           |
-| `maxDepth`                 | `50`               | Maximum nesting depth 
accepted during deserialization. Must be `>= 2`.                                
                            |
-| `maxBinarySize`            | `64 * 1024 * 1024` | Maximum allowed binary 
payload for guarded binary reads.                                               
                           |
-| `maxCollectionSize`        | `1_000_000`        | Maximum number of elements 
accepted for lists, sets, and maps.                                             
                       |
-| `useSliceString`           | `false`            | Optional string-reading 
mode for Node.js environments. Leave it at the default unless you have 
benchmarked a reason to change it. |
-| `hps`                      | unset              | Optional Node.js string 
fast-path helper from `@apache-fory/hps`.                                       
                          |
-| `hooks.afterCodeGenerated` | unset              | Callback to inspect or 
transform generated serializer code. Useful for debugging.                      
                           |
+| Option                     | Default     | Description                       
                                                    |
+| -------------------------- | ----------- | 
-------------------------------------------------------------------------------------
 |
+| `ref`                      | `false`     | Enable reference tracking for 
shared or circular object graphs                        |
+| `compatible`               | `false`     | Allow field additions/removals 
without breaking existing messages                     |
+| `maxDepth`                 | `50`        | Maximum nesting depth. Must be 
`>= 2`. Increase for deeply nested structures          |
+| `maxBinarySize`            | 64 MiB      | Maximum bytes accepted for any 
single binary field                                    |
+| `maxCollectionSize`        | `1_000_000` | Maximum elements accepted in any 
list, set, or map                                    |
+| `useSliceString`           | `false`     | Optional string-reading 
optimization for Node.js. Leave at default unless benchmarked |
+| `hps`                      | unset       | Optional fast string helper from 
`@apache-fory/hps` (Node.js 20+)                     |
+| `hooks.afterCodeGenerated` | unset       | Callback to inspect the generated 
serializer code β€” useful for debugging              |
 
 ## Documentation
 
diff --git a/docs/guide/javascript/references.md 
b/docs/guide/javascript/references.md
index 583dcc52c9..258e83a643 100644
--- a/docs/guide/javascript/references.md
+++ b/docs/guide/javascript/references.md
@@ -19,19 +19,23 @@ license: |
   limitations under the License.
 ---
 
-Fory can preserve shared references and circular object graphs, but in 
JavaScript you should enable reference tracking globally and mark the specific 
struct fields that participate in shared or circular references.
+By default Fory treats every value as a separate copy β€” if the same object 
appears in two fields it gets serialized twice, and after deserialization you 
get two independent copies. Enable reference tracking when:
 
-## Enable reference tracking globally
+- the same object instance is referenced from multiple places in the graph
+- your data contains a circular structure (e.g. a node that points to itself)
+- object identity must be preserved after a round trip
+
+Leave reference tracking off for plain tree-shaped data; it adds a small 
overhead.
+
+## Step 1: Enable Reference Tracking on the `Fory` Instance
 
 ```ts
 const fory = new Fory({ ref: true });
 ```
 
-Without `ref: true`, Fory treats values as ordinary tree-shaped data.
+## Step 2: Mark the Fields That Can Have Shared or Circular References
 
-## Mark reference-capable fields
-
-For schema-based structs, mark fields that can hold shared or circular 
references with `.setTrackingRef(true)`.
+For each field whose value may be shared or circular, call 
`.setTrackingRef(true)` on the field's schema:
 
 ```ts
 const nodeType = Type.struct("example.node", {
@@ -40,6 +44,8 @@ const nodeType = Type.struct("example.node", {
 });
 ```
 
+You need **both** the global flag and the field-level flag. Missing either one 
results in values being copied rather than referenced.
+
 ## Circular self-reference example
 
 ```ts
@@ -94,9 +100,9 @@ Leave it disabled when:
 - you want the lowest overhead
 - object identity does not matter
 
-## Cross-language note
+## Cross-Language Note
 
-Reference tracking is part of the xlang protocol, but every participating 
runtime still needs compatible schema and configuration. If one side models a 
graph as plain values and the other depends on object identity, behavior may 
not match your expectations.
+Reference tracking is part of the Fory binary protocol and works across 
runtimes. Both sides must enable reference tracking and mark the same fields as 
reference-tracked for the behavior to be consistent.
 
 ## Related Topics
 
diff --git a/docs/guide/javascript/schema-evolution.md 
b/docs/guide/javascript/schema-evolution.md
index 7956e7a074..4387e7cc3d 100644
--- a/docs/guide/javascript/schema-evolution.md
+++ b/docs/guide/javascript/schema-evolution.md
@@ -19,22 +19,24 @@ license: |
   limitations under the License.
 ---
 
-Fory JavaScript supports two struct encodings:
+Schema evolution lets different versions of your service exchange messages 
safely β€” a v2 writer can produce a message a v1 reader still understands, and 
vice versa.
 
-- **schema-consistent mode**: more compact, assumes the schema matches exactly
-- **compatible mode**: writes extra metadata so readers can tolerate added or 
missing fields
+## Two Modes
 
-## Enable compatible mode
+- **Schema-consistent mode** (default): more compact, but both sides must have 
exactly the same schema. Good when all services update together.
+- **Compatible mode**: writes extra field metadata so readers can skip unknown 
fields and tolerate missing ones. Good for independent deployments or rolling 
upgrades.
+
+## Enable Compatible Mode
 
 ```ts
 const fory = new Fory({ compatible: true });
 ```
 
-Compatible mode is the right choice when:
+Use this when:
 
-- multiple services roll out schema changes independently
+- services deploy schema changes independently
 - older readers may see newer payloads
-- newer readers may see older payloads
+- newer readers may see older payloads from before a field was added
 
 ## Example
 
@@ -61,11 +63,11 @@ const readerType = Type.struct(
 );
 ```
 
-With `compatible: true`, the reader can ignore fields it does not know about.
+With `compatible: true`, the reader ignores fields it does not know about, and 
fills unknown fields with default values.
 
-## Per-struct evolving override
+## Opting Out of Evolution for One Struct
 
-In JavaScript, struct schemas can explicitly disable evolving metadata even 
when type identity is otherwise compatible.
+You can disable evolution metadata for a specific struct even inside a 
`compatible: true` instance:
 
 ```ts
 const fixedType = Type.struct(
@@ -76,25 +78,20 @@ const fixedType = Type.struct(
 );
 ```
 
-This produces a smaller payload than an otherwise evolving-compatible struct, 
but the reader must then assume the schema matches. In cross-language use, both 
sides must agree on whether that struct is evolving; if one side treats the 
type as compatible and the other uses `evolving: false`, the on-wire type kind 
no longer matches.
-
-## Practical guidance
-
-Choose **schema-consistent mode** when:
-
-- both ends deploy together
-- size and throughput matter most
-- schema drift is tightly controlled
+`evolving: false` produces smaller messages for that struct, but **both the 
writer and reader must agree** on this setting. If one side writes with 
`evolving: false` and the other reads expecting compatible metadata, 
deserialization will fail.
 
-Choose **compatible mode** when:
+## When to Use Each Mode
 
-- services evolve independently
-- you need forward/backward tolerance
-- operational safety is more important than the last bytes of payload size
+|                                 | Schema-consistent | Compatible          |
+| ------------------------------- | ----------------- | ------------------- |
+| Services always update together | βœ” best choice     | works, but wasteful |
+| Independent deployments         | will break        | βœ” best choice       |
+| Smallest possible messages      | βœ”                 | slightly larger     |
+| Rolling upgrades                | risky             | βœ” safe              |
 
-## Cross-language requirement
+## Cross-Language Requirement
 
-Compatible mode only helps when the logical type identity still matches across 
runtimes. The same struct must still be registered with the same numeric ID or 
name across languages.
+Compatible mode only protects you from schema differences in the _fields_ of a 
type. You still need the same type identity (same numeric ID or same `namespace 
+ typeName`) on every side. See [Cross-Language](cross-language.md).
 
 ## Related Topics
 
diff --git a/docs/guide/javascript/supported-types.md 
b/docs/guide/javascript/supported-types.md
index 0186a18726..d61f135e5b 100644
--- a/docs/guide/javascript/supported-types.md
+++ b/docs/guide/javascript/supported-types.md
@@ -19,49 +19,45 @@ license: |
   limitations under the License.
 ---
 
-This page summarizes the main JavaScript and TypeScript values supported by 
Fory JavaScript.
+This page lists the JavaScript and TypeScript types supported by Fory, and 
explains when you need to be deliberate about type choices for cross-language 
compatibility.
 
 ## Primitive and Scalar Types
 
-| JavaScript/TypeScript    | Fory schema                                       
                                                        | Notes                 
                                                            |
-| ------------------------ | 
---------------------------------------------------------------------------------------------------------
 | 
---------------------------------------------------------------------------------
 |
-| `boolean`                | `Type.bool()`                                     
                                                        | Boolean value         
                                                            |
-| `number`                 | `Type.int8()` / `Type.int16()` / `Type.int32()` / 
`Type.float32()` / `Type.float64()` / unsigned variants | Pick explicit numeric 
width/encoding in schemas                                   |
-| `bigint`                 | `Type.int64()` / `Type.varInt64()` / 
`Type.uint64()` / tagged variants                                    | Use for 
64-bit integer fields                                                     |
-| `string`                 | `Type.string()`                                   
                                                        | Encoded as Latin1, 
UTF-16, or UTF-8 depending on content/runtime path             |
-| `Uint8Array`             | `Type.binary()`                                   
                                                        | Variable-length 
binary payload                                                    |
-| `Date`                   | `Type.timestamp()` / dynamic root date            
                                                        | Timestamps round-trip 
as `Date`                                                   |
-| `Date` or day count      | `Type.date()`                                     
                                                        | Date values 
deserialize as `Date`; some typed APIs also accept numeric day counts |
-| duration in milliseconds | `Type.duration()`                                 
                                                        | JavaScript currently 
exposes duration fields as numeric millisecond values        |
-| `BFloat16` or `number`   | `Type.bfloat16()`                                 
                                                        | Deserializes to 
`BFloat16`                                                        |
-| `number`                 | `Type.float16()`                                  
                                                        | Half-precision 
floating-point support                                             |
+| JavaScript value      | Fory schema                                          
                                 | Notes                                        
        |
+| --------------------- | 
-------------------------------------------------------------------------------------
 | ---------------------------------------------------- |
+| `boolean`             | `Type.bool()`                                        
                                 |                                              
        |
+| `number`              | `Type.int8()` / `Type.int16()` / `Type.int32()` / 
`Type.float32()` / `Type.float64()` | Pick the width that matches the peer 
language        |
+| `bigint`              | `Type.int64()` / `Type.varInt64()` / `Type.uint64()` 
                                 | Use `bigint` for 64-bit integers             
        |
+| `string`              | `Type.string()`                                      
                                 |                                              
        |
+| `Uint8Array`          | `Type.binary()`                                      
                                 | Binary blob                                  
        |
+| `Date`                | `Type.timestamp()`                                   
                                 | Serializes/deserializes as `Date`            
        |
+| `Date`                | `Type.date()`                                        
                                 | Date without time; deserializes as `Date`    
        |
+| duration (ms)         | `Type.duration()`                                    
                                 | Exposed as a numeric millisecond value in 
JavaScript |
+| `number`              | `Type.float16()`                                     
                                 | Half-precision float                         
        |
+| `BFloat16` / `number` | `Type.bfloat16()`                                    
                                 | Deserializes to `BFloat16`                   
        |
 
 ## Integer Types
 
-Use explicit integer schema helpers when the wire contract matters.
+JavaScript `number` is a 64-bit float. It cannot safely represent all 64-bit 
integers (integers above `Number.MAX_SAFE_INTEGER` lose precision). Use 
explicit schemas to match the width expected by the peer language:
 
 ```ts
-Type.int8();
-Type.int16();
-Type.int32();
-Type.varInt32();
-Type.int64();
+Type.int8(); // -128 to 127
+Type.int16(); // -32,768 to 32,767
+Type.int32(); // matches Java int, Go int32, C# int
+Type.varInt32(); // variable-length encoding; smaller for small values
+Type.int64(); // use with bigint; matches Java long, Go int64
 Type.varInt64();
 Type.sliInt64();
 Type.uint8();
 Type.uint16();
 Type.uint32();
 Type.varUInt32();
-Type.uint64();
+Type.uint64(); // use with bigint
 Type.varUInt64();
 Type.taggedUInt64();
 ```
 
-### Important JavaScript notes
-
-- `number` cannot safely represent all 64-bit integers.
-- For 64-bit integer fields, prefer `bigint` values in application code.
-- Dynamic root deserialization may return `bigint` for integer values that 
exceed JavaScript's safe integer range.
+**Rule of thumb**: anything that maps to a 64-bit integer in another language 
should use `Type.int64()` or `Type.uint64()` on the JavaScript side and be 
passed as a `bigint` value.
 
 ## Floating-Point Types
 
@@ -89,33 +85,22 @@ Type.array(
 
 These map to JavaScript arrays.
 
-### Optimized typed arrays
+## Optimized Numeric Arrays
 
-Fory JavaScript supports specialized array schemas for compact numeric and 
boolean arrays.
+For arrays of numbers, use the specialized typed array schemas. They are more 
compact and map to native typed arrays:
 
 ```ts
-Type.boolArray();
-Type.int16Array();
-Type.int32Array();
-Type.int64Array();
-Type.float16Array();
-Type.bfloat16Array();
-Type.float32Array();
-Type.float64Array();
+Type.boolArray(); // boolean[] in JS
+Type.int16Array(); // Int16Array
+Type.int32Array(); // Int32Array
+Type.int64Array(); // BigInt64Array
+Type.float32Array(); // Float32Array
+Type.float64Array(); // Float64Array
+Type.float16Array(); // number[]
+Type.bfloat16Array(); // BFloat16[]
 ```
 
-Typical runtime values are:
-
-| Schema                 | Typical JavaScript value                            
                 |
-| ---------------------- | 
-------------------------------------------------------------------- |
-| `Type.boolArray()`     | `boolean[]`                                         
                 |
-| `Type.int16Array()`    | `Int16Array`                                        
                 |
-| `Type.int32Array()`    | `Int32Array`                                        
                 |
-| `Type.int64Array()`    | `BigInt64Array`                                     
                 |
-| `Type.float32Array()`  | `Float32Array`                                      
                 |
-| `Type.float64Array()`  | `Float64Array`                                      
                 |
-| `Type.float16Array()`  | `number[]`                                          
                 |
-| `Type.bfloat16Array()` | `BFloat16Array` or `number[]` as input; 
deserializes to `BFloat16[]` |
+For non-numeric or struct arrays, use `Type.array(elementType)` instead.
 
 ## Maps and Sets
 
@@ -148,7 +133,7 @@ Type.enum("example.color", {
 });
 ```
 
-Both numeric and string enum values are supported. JavaScript encodes enum 
members by ordinal position in the declared enum object order and maps that 
ordinal back to the corresponding JavaScript value on read, so cross-language 
peers must agree on the enum member order and shape, not only the literal 
values.
+Fory encodes enum values by their ordinal position in the object (not their 
value). Both sides must declare enum members in the same order. When 
interoperating with another language, make sure the member order matches, not 
just the values.
 
 ## Nullable fields
 
@@ -158,9 +143,9 @@ Use `.setNullable(true)` when a field may be `null`.
 Type.string().setNullable(true);
 ```
 
-## Dynamic fields
+## Dynamic Fields
 
-Use `Type.any()` for dynamically typed content.
+Use `Type.any()` when a field can hold values of different types at runtime.
 
 ```ts
 const eventType = Type.struct("example.event", {
@@ -169,23 +154,21 @@ const eventType = Type.struct("example.event", {
 });
 ```
 
-This is useful for polymorphic payload slots, but more explicit field types 
are preferable when the schema is stable.
+Explicit field schemas are preferable when the type is known β€” `Type.any()` is 
harder to keep aligned across languages.
 
-## Reference-tracked fields
+## Reference-Tracked Fields
 
-Fields that can participate in shared or circular graphs should opt in:
+When the same object instance can appear in multiple fields, or when your 
graph is circular, opt individual fields into reference tracking:
 
 ```ts
 Type.struct("example.node").setTrackingRef(true).setNullable(true);
 ```
 
-This requires `new Fory({ ref: true })` at the instance level.
-
-## Extension types and advanced areas
+This requires `new Fory({ ref: true })`. See [References](references.md).
 
-JavaScript supports extension types through `Type.ext(...)` plus a custom 
serializer passed to `fory.register(...)`.
+## Extension Types
 
-The xlang specification also includes additional kinds such as unions. If you 
plan to depend on advanced features beyond the documented JavaScript surface, 
validate the exact API and interoperability behavior in your target runtime 
versions before committing to a shared wire contract.
+For types that need completely custom encoding, use `Type.ext(...)` and pass a 
custom serializer to `fory.register(...)`. This is an advanced use case; the 
standard `Type.struct` covers most scenarios.
 
 ## Related Topics
 
diff --git a/docs/guide/javascript/troubleshooting.md 
b/docs/guide/javascript/troubleshooting.md
index fa2dc61358..275780d7b7 100644
--- a/docs/guide/javascript/troubleshooting.md
+++ b/docs/guide/javascript/troubleshooting.md
@@ -21,90 +21,82 @@ license: |
 
 This page covers common problems when using Fory JavaScript.
 
-## Non-xlang payloads cannot be deserialized
+## Cannot deserialize a non-cross-language payload
 
-The JavaScript runtime reads xlang payloads only. If you try to deserialize a 
non-xlang payload, deserialization fails.
+The Fory JavaScript runtime only reads Fory cross-language payloads. If the 
producer is a Java or Go service using a language-native format, the JavaScript 
side cannot decode it.
 
-Make sure the producer is writing Fory xlang data.
+Fix: switch the producer to the cross-language mode. For Java, use 
`.withLanguage(Language.XLANG)`; for Go, use `WithXlang(true)`.
 
 ## `maxDepth must be an integer >= 2`
 
-`maxDepth` protects the deserializer from excessive nesting.
+This means you passed an invalid `maxDepth` value. It must be a positive 
integer of at least 2.
 
 ```ts
 new Fory({ maxDepth: 100 });
 ```
 
-Use a larger value only when your payloads genuinely need it.
+Increase this only if your data is legitimately deeply nested.
 
 ## `Binary size ... exceeds maxBinarySize`
 
-A binary field or payload exceeded the configured safety limit.
+A binary field or the overall message exceeded the safety limit. If the size 
is expected and the source is trusted, increase the limit:
 
 ```ts
 new Fory({ maxBinarySize: 128 * 1024 * 1024 });
 ```
 
-Increase the limit only if the input size is expected and trusted.
-
 ## `Collection size ... exceeds maxCollectionSize`
 
-A list, set, or map exceeded the configured collection limit.
+A list, set, or map has more elements than the configured limit. This often 
means the data is unexpectedly large. If it is legitimate, increase the limit:
 
 ```ts
 new Fory({ maxCollectionSize: 2_000_000 });
 ```
 
-This is commonly hit when a producer sends unexpectedly large arrays or maps.
-
 ## `Field "..." is not nullable`
 
-A schema field was written as `null` but was not marked nullable.
+You are passing `null` to a field that was not declared nullable. Fix: add 
`.setNullable(true)` to the field schema:
 
 ```ts
 const userType = Type.struct("example.user", {
   name: Type.string(),
-  email: Type.string().setNullable(true),
+  email: Type.string().setNullable(true), // ← this field can be null
 });
 ```
 
-Mark nullable fields explicitly.
+## Objects are not the same instance after deserialization
 
-## Reference graphs do not preserve identity
+Fory does not preserve object identity by default. Two fields pointing to the 
same object will become two independent copies.
 
-Check both conditions:
+Fix: enable **both** of these:
 
-1. `new Fory({ ref: true })` is enabled
-2. the relevant schema fields use `.setTrackingRef(true)`
+1. `new Fory({ ref: true })` on the instance
+2. `.setTrackingRef(true)` on the specific fields
 
-Missing either one will usually turn the graph into ordinary value-based 
serialization.
+See [References](references.md).
 
 ## Large integers come back as `bigint`
 
-This is expected for 64-bit integer values or for dynamic numbers that exceed 
JavaScript's safe integer range. Use explicit numeric schemas and `bigint` in 
your application when exact 64-bit integer semantics matter.
+This is expected. Fory uses `bigint` for any 64-bit integer field 
(`Type.int64()`, `Type.uint64()`). If you need a `number`, use a smaller 
integer type like `Type.int32()` β€” but only if the value actually fits in 32 
bits.
 
-## Debugging generated serializers
+## Inspecting Generated Serializer Code
 
-Use `hooks.afterCodeGenerated` to inspect generated code.
+If you need to debug what Fory is doing under the hood, inspect the generated 
serializer code with a hook:
 
 ```ts
 const fory = new Fory({
   hooks: {
     afterCodeGenerated(code) {
-      console.error(code);
+      console.log(code);
       return code;
     },
   },
 });
 ```
 
-## Optional `@apache-fory/hps` install issues
-
-`@apache-fory/hps` is optional and Node-specific. If installation fails, 
remove it from your config and continue with `@apache-fory/core` alone.
+## `@apache-fory/hps` Install Fails
 
-```ts
-const fory = new Fory();
-```
+`@apache-fory/hps` is an optional Node.js accelerator. If it fails to install 
(e.g. on a platform without native module support), just remove it from your 
dependencies. Fory still works correctly without it.
 
 ## Related Topics
 
diff --git a/docs/guide/javascript/type-registration.md 
b/docs/guide/javascript/type-registration.md
index 07e908aec8..e922e8ff30 100644
--- a/docs/guide/javascript/type-registration.md
+++ b/docs/guide/javascript/type-registration.md
@@ -19,13 +19,15 @@ license: |
   limitations under the License.
 ---
 
-Type registration tells Fory JavaScript how to identify and encode 
user-defined structs and enums.
+Every struct and enum you serialize must be registered with the `Fory` 
instance before use. Registration tells Fory how to identify the type in a 
message and how to encode and decode it.
 
 ## Registering Structs
 
-You can register a struct by numeric ID or by name.
+You can identify a struct with a numeric ID or with a name. Pick one strategy 
and use it consistently across all languages that share the same messages.
 
-### Register by numeric type ID
+### Register by numeric ID
+
+Smaller wire representation. Good when a small team can coordinate IDs.
 
 ```ts
 const userType = Type.struct(
@@ -37,17 +39,15 @@ const userType = Type.struct(
 );
 
 const fory = new Fory();
-const userSerde = fory.register(userType);
+const { serialize, deserialize } = fory.register(userType);
 ```
 
-Use numeric IDs when:
-
-- you want compact metadata on the wire
-- you control IDs across all participating languages
-- the same logical type is registered everywhere with the same ID
+The same number must be used in every runtime that reads or writes this type.
 
 ### Register by name
 
+Easier to coordinate across teams. Slightly larger metadata in the message.
+
 ```ts
 const userType = Type.struct(
   { typeName: "example.user" },
@@ -58,19 +58,14 @@ const userType = Type.struct(
 );
 
 const fory = new Fory();
-const userSerde = fory.register(userType);
+const { serialize, deserialize } = fory.register(userType);
 ```
 
-Named registration is usually easier to evolve operationally because it avoids 
central numeric ID allocation, but it writes more metadata than numeric IDs.
-
-### Explicit namespace and type name
+You can also split namespace and type name explicitly:
 
 ```ts
 const userType = Type.struct(
-  {
-    namespace: "example",
-    typeName: "user",
-  },
+  { namespace: "example", typeName: "user" },
   {
     id: Type.int64(),
     name: Type.string(),
@@ -78,7 +73,7 @@ const userType = Type.struct(
 );
 ```
 
-This corresponds to the named xlang type identity carried in metadata.
+> **Do not mix strategies for the same type across runtimes.** If one side 
uses a numeric ID and the other uses a name, deserialization will fail.
 
 ## Registering with Decorators
 
@@ -129,41 +124,29 @@ fory.register(Type.enum("example.status", Status));
 
 ## Registration Scope
 
-Registration is per `Fory` instance.
+Registration is per `Fory` instance. If you create two instances, you need to 
register schemas in both.
 
-```ts
-const fory1 = new Fory();
-const fory2 = new Fory();
+## What `register` Returns
 
-fory1.register(
-  Type.struct("example.user", {
-    id: Type.int64(),
-  }),
-);
-
-// fory2 does not know that schema until you register it again there.
-```
-
-## Schema Handles Returned by `register`
-
-`register` returns a bound serializer pair:
+`fory.register(schema)` returns a bound serializer pair:
 
 ```ts
-const orderType = Type.struct("example.order", {
-  id: Type.int64(),
-  total: Type.float64(),
-});
+const { serialize, deserialize } = fory.register(orderType);
 
-const { serializer, serialize, deserialize } = new Fory().register(orderType);
+// serialize returns Uint8Array bytes
+const bytes = serialize({ id: 1n, total: 99.99 });
+
+// deserialize returns the decoded value
+const order = deserialize(bytes);
 ```
 
-Use these bound functions for repeated operations on the same type.
+Store and reuse this pair β€” it is the fast path.
 
-## Field Metadata
+## Field Options
 
-Each field type can be refined with schema metadata.
+### Nullable fields
 
-### Nullability
+If a field can be `null`, mark it explicitly. Passing `null` to a non-nullable 
field throws.
 
 ```ts
 Type.string().setNullable(true);
@@ -171,44 +154,44 @@ Type.string().setNullable(true);
 
 ### Reference tracking on a field
 
+Needed when the same object instance can appear in multiple fields (see 
[References](references.md)):
+
 ```ts
 Type.struct("example.node").setTrackingRef(true);
 ```
 
-This matters only when `new Fory({ ref: true })` is also enabled globally.
+This only has an effect when `new Fory({ ref: true })` is also set.
 
-### Dynamic dispatch
+### Polymorphic fields
 
-```ts
-import { Dynamic, Type } from "@apache-fory/core";
+Use `Type.any()` when a field can hold different types at runtime:
 
-Type.struct("example.child").setDynamic(Dynamic.FALSE);
+```ts
+const eventType = Type.struct("example.event", {
+  kind: Type.string(),
+  payload: Type.any(),
+});
 ```
 
-Use `dynamic` when the runtime type behavior must be controlled explicitly. In 
this implementation, `Dynamic.FALSE` forces monomorphic handling, 
`Dynamic.TRUE` forces polymorphic handling, and `Dynamic.AUTO` leaves the 
decision to the runtime. This is especially relevant for polymorphic fields in 
xlang payloads, while most users should keep the default behavior unless they 
are tuning a specific schema edge case.
+For fine-grained control over how a specific struct field handles its runtime 
type, you can call `.setDynamic(Dynamic.FALSE)` (always treat as the declared 
type) or `.setDynamic(Dynamic.TRUE)` (always write the runtime type). The 
default (`Dynamic.AUTO`) is correct for the vast majority of cases.
 
-## Choosing IDs vs names
+## Choosing IDs vs Names
 
 Use **numeric IDs** when:
 
-- you want the smallest wire representation
-- your organization can keep IDs stable and unique
-- multiple runtimes are coordinated tightly
+- you want the smallest possible message size
+- your organization can keep IDs stable and globally unique
+- services are tightly coordinated
 
 Use **names** when:
 
-- you want easier decentralized coordination
-- schemas are shared by package/module name already
-- slightly larger metadata is acceptable
-
-## Cross-language requirement
-
-For xlang interoperability, the serializer and deserializer must agree on the 
same type identity:
+- teams define types independently
+- schemas are already identified by package/module name
+- slightly larger metadata overhead is acceptable
 
-- same numeric ID, or
-- same namespace + type name
+## Cross-Language
 
-The field schema must also match in a cross-language-compatible way. See 
[Cross-Language](cross-language.md).
+For a message to round-trip between JavaScript and another runtime, both sides 
must use the same identity for a given type: same numeric ID, or same 
`namespace + typeName`. See [Cross-Language](cross-language.md).
 
 ## Related Topics
 
diff --git a/docs/guide/kotlin/_category_.json 
b/docs/guide/kotlin/_category_.json
index c20ca242fa..18540b4801 100644
--- a/docs/guide/kotlin/_category_.json
+++ b/docs/guide/kotlin/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Kotlin",
-  "position": 12,
+  "position": 11,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/python/_category_.json 
b/docs/guide/python/_category_.json
index a964bce6e9..b37a319075 100644
--- a/docs/guide/python/_category_.json
+++ b/docs/guide/python/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Python",
-  "position": 1,
+  "position": 2,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/rust/_category_.json b/docs/guide/rust/_category_.json
index 845d58f46c..e891086214 100644
--- a/docs/guide/rust/_category_.json
+++ b/docs/guide/rust/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Rust",
-  "position": 2,
+  "position": 3,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/scala/_category_.json b/docs/guide/scala/_category_.json
index 7e42919800..a0191e2873 100644
--- a/docs/guide/scala/_category_.json
+++ b/docs/guide/scala/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Scala",
-  "position": 11,
+  "position": 10,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/swift/_category_.json b/docs/guide/swift/_category_.json
index 1e17c92270..dfdaf59968 100644
--- a/docs/guide/swift/_category_.json
+++ b/docs/guide/swift/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Swift",
-  "position": 10,
+  "position": 8,
   "collapsible": true,
   "collapsed": true
 }
diff --git a/docs/guide/xlang/_category_.json b/docs/guide/xlang/_category_.json
index c356a9b915..ab2d183de0 100644
--- a/docs/guide/xlang/_category_.json
+++ b/docs/guide/xlang/_category_.json
@@ -1,6 +1,6 @@
 {
   "label": "Cross Language",
-  "position": 15,
+  "position": 12,
   "collapsible": true,
   "collapsed": true
 }


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to