1use std::fmt::{self, Display, Formatter};
2
3use crate::protocol::text::{ColumnDefinition, ColumnFlags, ColumnType};
4use cdbc::type_info::TypeInfo;
5
6#[derive(Debug, Clone)]
8#[derive(serde::Serialize, serde::Deserialize)]
9pub struct MySqlTypeInfo {
10 pub(crate) r#type: ColumnType,
11 pub(crate) flags: ColumnFlags,
12 pub(crate) char_set: u16,
13
14 #[serde(default)]
16 pub(crate) max_size: Option<u32>,
17}
18
19impl MySqlTypeInfo {
20 pub(crate) const fn binary(ty: ColumnType) -> Self {
21 Self {
22 r#type: ty,
23 flags: ColumnFlags::BINARY,
24 char_set: 63,
25 max_size: None,
26 }
27 }
28
29 #[doc(hidden)]
30 pub const fn __enum() -> Self {
31 Self {
32 r#type: ColumnType::Enum,
33 flags: ColumnFlags::BINARY,
34 char_set: 63,
35 max_size: None,
36 }
37 }
38
39 #[doc(hidden)]
40 pub fn __type_feature_gate(&self) -> Option<&'static str> {
41 match self.r#type {
42 ColumnType::Date | ColumnType::Time | ColumnType::Timestamp | ColumnType::Datetime => {
43 Some("time")
44 }
45
46 ColumnType::Json => Some("json"),
47 ColumnType::NewDecimal => Some("bigdecimal"),
48
49 _ => None,
50 }
51 }
52
53 pub(crate) fn from_column(column: &ColumnDefinition) -> Self {
54 Self {
55 r#type: column.r#type,
56 flags: column.flags,
57 char_set: column.char_set,
58 max_size: Some(column.max_size),
59 }
60 }
61}
62
63impl Display for MySqlTypeInfo {
64 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
65 f.pad(self.name())
66 }
67}
68
69impl TypeInfo for MySqlTypeInfo {
70 fn is_null(&self) -> bool {
71 matches!(self.r#type, ColumnType::Null)
72 }
73
74 fn name(&self) -> &str {
75 self.r#type.name(self.char_set, self.flags, self.max_size)
76 }
77}
78
79impl PartialEq<MySqlTypeInfo> for MySqlTypeInfo {
80 fn eq(&self, other: &MySqlTypeInfo) -> bool {
81 if self.r#type != other.r#type {
82 return false;
83 }
84
85 match self.r#type {
86 ColumnType::Tiny
87 | ColumnType::Short
88 | ColumnType::Long
89 | ColumnType::Int24
90 | ColumnType::LongLong => {
91 return self.flags.contains(ColumnFlags::UNSIGNED)
92 == other.flags.contains(ColumnFlags::UNSIGNED);
93 }
94
95 ColumnType::VarChar
97 | ColumnType::Blob
98 | ColumnType::TinyBlob
99 | ColumnType::MediumBlob
100 | ColumnType::LongBlob
101 | ColumnType::String
102 | ColumnType::VarString
103 | ColumnType::Enum => {
104 return self.char_set == other.char_set;
105 }
106
107 _ => {}
108 }
109
110 true
111 }
112}
113
114impl Eq for MySqlTypeInfo {}