fory_core/lib.rs
1// Licensed to the Apache Software Foundation (ASF) under one
2// or more contributor license agreements. See the NOTICE file
3// distributed with this work for additional information
4// regarding copyright ownership. The ASF licenses this file
5// to you under the Apache License, Version 2.0 (the
6// "License"); you may not use this file except in compliance
7// with the License. You may obtain a copy of the License at
8//
9// http://www.apache.org/licenses/LICENSE-2.0
10//
11// Unless required by applicable law or agreed to in writing,
12// software distributed under the License is distributed on an
13// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14// KIND, either express or implied. See the License for the
15// specific language governing permissions and limitations
16// under the License.
17
18//! # Fory Core
19//!
20//! This is the core implementation of the Fory serialization framework.
21//! It provides the fundamental building blocks for high-performance serialization
22//! and deserialization in Rust.
23//!
24//! ## Architecture
25//!
26//! The core library is organized into several key modules:
27//!
28//! - **`fory`**: Main serialization engine and public API
29//! - **`buffer`**: Efficient binary buffer management with Reader/Writer
30//! - **`context`**: Per-operation read/write state and context pooling types
31//! - **`row`**: Row-based serialization for zero-copy operations
32//! - **`serializer`**: Type-specific serialization implementations
33//! - **`resolver`**: Type resolution and metadata management
34//! - **`meta`**: Metadata handling for schema evolution
35//! - **`types`**: Runtime value carriers such as temporal values, decimal, Float16, BFloat16, and weak refs
36//! - **`type_id`**: Type IDs and protocol header helpers
37//! - **`error`**: Error handling and result types
38//! - **`util`**: Utility functions and helpers
39//!
40//! ## Key Concepts
41//!
42//! ### Wire Modes And Schema Evolution
43//!
44//! Fory supports two wire modes:
45//!
46//! - **Xlang mode**: the default cross-language wire format, selected with
47//! `.xlang(true)` and compatible schema evolution when `compatible` is
48//! omitted.
49//! - **Native mode**: the Rust-only wire format, selected with `.xlang(false)`
50//! and schema-consistent payloads when `compatible` is omitted. Add
51//! `.compatible(true)` only when Rust-only deployments need schema evolution.
52//!
53//! ### Type System
54//!
55//! The framework uses a comprehensive type system that supports:
56//! - Primitive types (bool, integers, floats, strings)
57//! - Collections (Vec, HashMap, BTreeMap)
58//! - Optional types (`Option<T>`)
59//! - Date/time carriers with optional chrono integration
60//! - Custom structs and enums
61//! - Trait objects (Box, Rc, Arc)
62//!
63//! ### Performance Optimizations
64//!
65//! - **Zero-copy deserialization** in row mode
66//! - **Buffer pre-allocation** to minimize allocations
67//! - **Variable-length encoding** for compact representation
68//! - **Little-endian byte order** for cross-platform compatibility
69//!
70//! ### Trait Object Serialization
71//!
72//! Fory supports polymorphic serialization through trait objects:
73//!
74//! #### Box-Based Trait Objects
75//!
76//! Define custom traits and register implementations:
77//!
78//! ```rust,ignore
79//! use fory_core::{Fory, register_trait_type, Serializer};
80//! use fory_derive::{ForyEnum, ForyStruct, ForyUnion};
81//!
82//! trait Animal: Serializer {
83//! fn speak(&self) -> String;
84//! }
85//!
86//! #[derive(ForyStruct, Debug)]
87//! struct Dog { name: String }
88//!
89//! #[derive(ForyStruct, Debug)]
90//! struct Cat { name: String }
91//!
92//! impl Animal for Dog {
93//! fn speak(&self) -> String { "Woof!".to_string() }
94//! }
95//!
96//! impl Animal for Cat {
97//! fn speak(&self) -> String { "Meow!".to_string() }
98//! }
99//!
100//! register_trait_type!(Animal, Dog, Cat);
101//!
102//! #[derive(ForyStruct)]
103//! struct Zoo {
104//! star_animal: Box<dyn Animal>,
105//! }
106//!
107//! # fn main() {
108//! let mut fory = Fory::builder().xlang(false).compatible(true).build();
109//! fory.register::<Dog>(100).unwrap();
110//! fory.register::<Cat>(101).unwrap();
111//! fory.register::<Zoo>(102).unwrap();
112//!
113//! let zoo = Zoo {
114//! star_animal: Box::new(Dog { name: "Buddy".to_string() }),
115//! };
116//!
117//! let bytes = fory.serialize(&zoo).unwrap();
118//! let decoded: Zoo = fory.deserialize(&bytes).unwrap();
119//! assert_eq!(decoded.star_animal.speak(), "Woof!");
120//! # }
121//! ```
122//!
123//! #### Rc/Arc-Based Trait Objects
124//!
125//! For reference-counted trait objects, use them directly in struct fields:
126//!
127//! ```rust,ignore
128//! # use fory_core::Serializer;
129//! # use fory_derive::{ForyEnum, ForyStruct, ForyUnion};
130//! # use std::rc::Rc;
131//! # use std::sync::Arc;
132//! # trait Animal: Serializer { fn speak(&self) -> String; }
133//! #[derive(ForyStruct)]
134//! struct Shelter {
135//! animals_rc: Vec<Rc<dyn Animal>>,
136//! animals_arc: Vec<Arc<dyn Animal>>,
137//! }
138//! ```
139//!
140//! For standalone serialization, use auto-generated wrapper types (e.g., `AnimalRc`, `AnimalArc`)
141//! created by `register_trait_type!` due to Rust's orphan rule limitations.
142//!
143//! ## Usage
144//!
145//! This crate is typically used through the higher-level `fory` crate,
146//! which provides derive macros and a more convenient API. However,
147//! you can use the core types directly for advanced use cases.
148//!
149//! ```rust
150//! use fory_core::fory::Fory;
151//! use fory_core::error::Error;
152//! use fory_core::row::{to_row, from_row};
153//! use std::collections::HashMap;
154//!
155//! // Create a Fory instance
156//! let mut fory = Fory::builder().xlang(false).compatible(true).build();
157//!
158//! // Serialize String
159//! let text = String::from("Hello, Fory!");
160//! let serialized_str = fory.serialize(&text).unwrap();
161//! let deserialized_str: String = fory.deserialize(&serialized_str).unwrap();
162//! assert_eq!(text, deserialized_str);
163//!
164//! // Serialize Vec
165//! let vec_data = vec![1, 2, 3, 4, 5];
166//! let serialized_vec = fory.serialize(&vec_data).unwrap();
167//! let deserialized_vec: Vec<i32> = fory.deserialize(&serialized_vec).unwrap();
168//! assert_eq!(vec_data, deserialized_vec);
169//!
170//! // Serialize HashMap
171//! let mut map = HashMap::new();
172//! map.insert("key1".to_string(), 100);
173//! map.insert("key2".to_string(), 200);
174//! let serialized_map = fory.serialize(&map).unwrap();
175//! let deserialized_map: HashMap<String, i32> = fory.deserialize(&serialized_map).unwrap();
176//! assert_eq!(map, deserialized_map);
177//! // Register types for object serialization
178//! // fory.register::<MyStruct>(type_id);
179//!
180//! // Use row-based serialization for zero-copy operations
181//! // let row_data = to_row(&my_data);
182//! // let row = from_row::<MyStruct>(&row_data);
183//! ```
184
185pub mod buffer;
186pub mod config;
187pub mod context;
188pub mod error;
189pub mod fory;
190pub mod meta;
191pub mod resolver;
192pub mod row;
193pub mod serializer;
194pub mod type_id;
195pub mod types;
196pub mod util;
197
198// Re-export paste for use in macros
199pub use paste;
200
201pub use crate::buffer::{Reader, Writer};
202pub use crate::config::Config;
203pub use crate::context::{ReadContext, WriteContext};
204pub use crate::error::Error;
205pub use crate::fory::{Fory, ForyBuilder};
206pub use crate::meta::{compute_field_hash, compute_struct_hash};
207pub use crate::resolver::{RefFlag, RefMode, TypeInfo, TypeResolver};
208pub use crate::serializer::{read_data, write_data, ForyDefault, Serializer, StructSerializer};
209pub use crate::type_id::TypeId;
210pub use crate::types::bfloat16::bfloat16 as BFloat16;
211pub use crate::types::float16::float16 as Float16;
212pub use crate::types::{ArcWeak, Date, Decimal, Duration, RcWeak, Timestamp};