qubit_datatype/datatype/data_type.rs
1/*******************************************************************************
2 *
3 * Copyright (c) 2025 - 2026 Haixing Hu.
4 *
5 * SPDX-License-Identifier: Apache-2.0
6 *
7 * Licensed under the Apache License, Version 2.0.
8 *
9 ******************************************************************************/
10//! # Data Type Definitions (Language Layer)
11//!
12//! Provides cross-module reusable common data type enum `DataType` and type mapping `DataTypeOf`.
13//!
14
15use std::fmt;
16use std::str::FromStr;
17
18use super::data_type_parse_error::DataTypeParseError;
19
20use serde::{
21 Deserialize,
22 Serialize,
23};
24
25/// Universal data type enumeration for cross-module type representation
26///
27/// Defines all basic data types and composite types supported by the system.
28/// This enum provides a unified way to represent and work with different data types
29/// across various modules and components.
30///
31/// `DataType` serves as a bridge between Rust's type system and runtime type
32/// information, enabling dynamic type handling, serialization, validation,
33/// and other type-aware operations.
34///
35/// # Features
36///
37/// - **Comprehensive Coverage**: Supports all basic Rust types plus common third-party types
38/// - **String Representation**: Each variant has a consistent string representation
39/// - **Serialization Support**: Implements `Serialize` and `Deserialize` for JSON/YAML support
40/// - **Type Mapping**: Works with `DataTypeOf` trait for compile-time type mapping
41///
42/// # Use Cases
43///
44/// - **Dynamic Type Handling**: Runtime type checking and conversion
45/// - **Serialization/Deserialization**: Type-aware data format conversion
46/// - **Validation Systems**: Type-based input validation
47/// - **Generic Programming**: Type-safe generic operations
48/// - **API Documentation**: Automatic type information generation
49///
50/// # Examples
51///
52/// ## Basic Usage
53///
54/// ```rust
55/// use qubit_datatype::DataType;
56///
57/// let data_type = DataType::Int32;
58/// assert_eq!(data_type.to_string(), "int32");
59/// assert_eq!(data_type.as_str(), "int32");
60/// ```
61///
62/// ## Type Checking
63///
64/// ```rust
65/// use qubit_datatype::DataType;
66///
67/// fn is_numeric(data_type: DataType) -> bool {
68/// matches!(data_type,
69/// DataType::Int8 | DataType::Int16 | DataType::Int32 | DataType::Int64 | DataType::Int128 |
70/// DataType::UInt8 | DataType::UInt16 | DataType::UInt32 | DataType::UInt64 | DataType::UInt128 |
71/// DataType::Float32 | DataType::Float64 | DataType::BigInteger | DataType::BigDecimal
72/// )
73/// }
74///
75/// assert!(is_numeric(DataType::Int32));
76/// assert!(!is_numeric(DataType::String));
77/// ```
78///
79/// ## Serialization
80///
81/// ```rust
82/// use qubit_datatype::DataType;
83/// use serde_json;
84///
85/// let data_type = DataType::Float64;
86/// let json = serde_json::to_string(&data_type).unwrap();
87/// assert_eq!(json, "\"float64\"");
88///
89/// let deserialized: DataType = serde_json::from_str(&json).unwrap();
90/// assert_eq!(deserialized, DataType::Float64);
91/// ```
92///
93///
94#[derive(Debug, Clone, Copy, PartialEq, Eq, Hash, Serialize, Deserialize)]
95#[serde(rename_all = "lowercase")]
96pub enum DataType {
97 /// Boolean type
98 Bool,
99 /// Character type
100 Char,
101 /// 8-bit signed integer
102 Int8,
103 /// 16-bit signed integer
104 Int16,
105 /// 32-bit signed integer
106 Int32,
107 /// 64-bit signed integer
108 Int64,
109 /// 128-bit signed integer
110 Int128,
111 /// 8-bit unsigned integer
112 UInt8,
113 /// 16-bit unsigned integer
114 UInt16,
115 /// 32-bit unsigned integer
116 UInt32,
117 /// 64-bit unsigned integer
118 UInt64,
119 /// 128-bit unsigned integer
120 UInt128,
121 /// 32-bit floating point number
122 Float32,
123 /// 64-bit floating point number
124 Float64,
125 /// String type
126 String,
127 /// Date type (NaiveDate)
128 Date,
129 /// Time type (NaiveTime)
130 Time,
131 /// DateTime type (NaiveDateTime)
132 DateTime,
133 /// UTC time point (equivalent to Java Instant) (`DateTime<Utc>`)
134 Instant,
135 /// Big integer type (BigInt)
136 BigInteger,
137 /// Big decimal type (BigDecimal)
138 BigDecimal,
139 /// Platform-dependent signed integer (isize)
140 IntSize,
141 /// Platform-dependent unsigned integer (usize)
142 UIntSize,
143 /// Duration type (std::time::Duration)
144 Duration,
145 /// URL type (url::Url)
146 Url,
147 /// String map type (HashMap<String, String>)
148 StringMap,
149 /// JSON value type (serde_json::Value)
150 Json,
151}
152
153impl fmt::Display for DataType {
154 fn fmt(&self, formatter: &mut fmt::Formatter<'_>) -> fmt::Result {
155 formatter.write_str(self.as_str())
156 }
157}
158
159impl FromStr for DataType {
160 type Err = DataTypeParseError;
161
162 fn from_str(value: &str) -> Result<Self, Self::Err> {
163 match value.to_ascii_lowercase().as_str() {
164 "bool" => Ok(DataType::Bool),
165 "char" => Ok(DataType::Char),
166 "int8" => Ok(DataType::Int8),
167 "int16" => Ok(DataType::Int16),
168 "int32" => Ok(DataType::Int32),
169 "int64" => Ok(DataType::Int64),
170 "int128" => Ok(DataType::Int128),
171 "uint8" => Ok(DataType::UInt8),
172 "uint16" => Ok(DataType::UInt16),
173 "uint32" => Ok(DataType::UInt32),
174 "uint64" => Ok(DataType::UInt64),
175 "uint128" => Ok(DataType::UInt128),
176 "float32" => Ok(DataType::Float32),
177 "float64" => Ok(DataType::Float64),
178 "string" => Ok(DataType::String),
179 "date" => Ok(DataType::Date),
180 "time" => Ok(DataType::Time),
181 "datetime" => Ok(DataType::DateTime),
182 "instant" => Ok(DataType::Instant),
183 "biginteger" => Ok(DataType::BigInteger),
184 "bigdecimal" => Ok(DataType::BigDecimal),
185 "intsize" => Ok(DataType::IntSize),
186 "uintsize" => Ok(DataType::UIntSize),
187 "duration" => Ok(DataType::Duration),
188 "url" => Ok(DataType::Url),
189 "stringmap" => Ok(DataType::StringMap),
190 "json" => Ok(DataType::Json),
191 _ => Err(DataTypeParseError::new(value)),
192 }
193 }
194}
195
196impl DataType {
197 // Keep explicit conversion helper for existing call-sites and API parity with
198 // current serialized/configuration text values.
199 /// Get the string representation of the data type.
200 ///
201 /// # Returns
202 ///
203 /// Returns the name string of the data type.
204 #[inline]
205 pub const fn as_str(&self) -> &'static str {
206 match self {
207 DataType::Bool => "bool",
208 DataType::Char => "char",
209 DataType::Int8 => "int8",
210 DataType::Int16 => "int16",
211 DataType::Int32 => "int32",
212 DataType::Int64 => "int64",
213 DataType::Int128 => "int128",
214 DataType::UInt8 => "uint8",
215 DataType::UInt16 => "uint16",
216 DataType::UInt32 => "uint32",
217 DataType::UInt64 => "uint64",
218 DataType::UInt128 => "uint128",
219 DataType::Float32 => "float32",
220 DataType::Float64 => "float64",
221 DataType::String => "string",
222 DataType::Date => "date",
223 DataType::Time => "time",
224 DataType::DateTime => "datetime",
225 DataType::Instant => "instant",
226 DataType::BigInteger => "biginteger",
227 DataType::BigDecimal => "bigdecimal",
228 DataType::IntSize => "intsize",
229 DataType::UIntSize => "uintsize",
230 DataType::Duration => "duration",
231 DataType::Url => "url",
232 DataType::StringMap => "stringmap",
233 DataType::Json => "json",
234 }
235 }
236}